mongodb/node-mongodb-native · error · MongoParseError

Text record may only set any of: ${VALID_TXT_RECORDS.join(',

Error message

Text record may only set any of: ${VALID_TXT_RECORDS.join(', ')}

What it means

Thrown by resolveSRVRecord() when a TXT record (for a mongodb+srv:// URI) contains a key that is not in the allowed set. The driver only honors authSource, replicaSet, and loadBalanced from the TXT record. Any other key produces a MongoParseError listing the valid options.

Source

Thrown at src/connection_string.ts:123

  // Use the result of resolving the TXT record and add options from there if they exist.
  let record;
  try {
    record = await txtResolutionPromise;
  } catch (error) {
    if (error.code !== 'ENODATA' && error.code !== 'ENOTFOUND') {
      throw error;
    }
    return hostAddresses;
  }

  if (record.length > 1) {
    throw new MongoParseError('Multiple text records not allowed');
  }

  const txtRecordOptions = new URLSearchParams(record[0].join(''));
  const txtRecordOptionKeys = [...txtRecordOptions.keys()];
  if (txtRecordOptionKeys.some(key => !VALID_TXT_RECORDS.includes(key))) {
    throw new MongoParseError(`Text record may only set any of: ${VALID_TXT_RECORDS.join(', ')}`);
  }

  if (VALID_TXT_RECORDS.some(option => txtRecordOptions.get(option) === '')) {
    throw new MongoParseError('Cannot have empty URI params in DNS TXT Record');
  }

  const source = txtRecordOptions.get('authSource') ?? undefined;
  const replicaSet = txtRecordOptions.get('replicaSet') ?? undefined;
  const loadBalanced = txtRecordOptions.get('loadBalanced') ?? undefined;

  if (
    !options.userSpecifiedAuthSource &&
    source &&
    options.credentials &&
    !AUTH_MECHS_AUTH_SRC_EXTERNAL.has(options.credentials.mechanism)
  ) {
    options.credentials = MongoCredentials.merge(options.credentials, { source });
  }

View on GitHub (pinned to 3366c21a63)

Solutions

  1. Inspect the TXT record: dig <host> TXT and read the keys.
  2. Keep only authSource, replicaSet, and/or loadBalanced in the TXT record.
  3. Move disallowed options (retryWrites, appName, tls, etc.) into the URI query string instead.
  4. Re-query DNS after the change to confirm propagation.

Example fix

// DNS TXT before: "authSource=admin&retryWrites=true"
// DNS TXT after:  "authSource=admin"
// URI: mongodb+srv://host/db?retryWrites=true
Defensive patterns

Strategy: validation

Validate before calling

import { promises as dns } from 'dns';
const ALLOWED = ['authSource', 'replicaSet', 'loadBalanced'];
async function validateTxtKeys(host: string): Promise<void> {
  const records = await dns.resolveTxt(host);
  if (!records.length) return;
  const params = new URLSearchParams(records[0].join(''));
  for (const key of params.keys()) {
    if (!ALLOWED.includes(key)) {
      throw new Error(`TXT record key '${key}' is not allowed by the driver`);
    }
  }
}

Try / catch

try {
  await client.connect();
} catch (e) {
  if (e instanceof MongoParseError && /Text record may only set/.test(e.message)) {
    throw new Error('Move non-allowed options out of the DNS TXT record into the URI');
  }
  throw e;
}

Prevention

When it happens

Trigger: A TXT record carrying keys like retryWrites, ssl, appName, or tls that the driver does not permit via DNS; a stale TXT record from an older driver expectation; an admin who assumed all URI options are allowed in TXT.

Common situations: Atlas or self-managed DNS where someone added retryWrites=true to the TXT record; migrating options into DNS that belong only in the URI query string; copying full connection-string options into the TXT record.

Related errors


AI-assisted analysis of mongodb/node-mongodb-native@3366c21a63 (2026-08-04). Data as JSON: /data/errors/421ca4083d62bf18.json. Report an issue: GitHub.