mongodb/node-mongodb-native · error · MongoInvalidArgumentError

Argument "operations" must be an array of documents

Error message

Argument "operations" must be an array of documents

What it means

Thrown by Collection.bulkWrite when its first argument is not an array. The method requires ReadonlyArray<AnyBulkWriteOperation<TSchema>>; a non-array is a programming error and raises a MongoInvalidArgumentError before constructing the bulk operation.

Solutions

  1. Wrap operations in an array: bulkWrite([{ insertOne: {...} }]).
  2. If you have a single operation, still pass it as a one-element array.
  3. Guard dynamic inputs with Array.isArray before calling.
  4. Type the operations variable explicitly so TS flags misuse.

Example fix

// before
await collection.bulkWrite({ insertOne: { document: { a: 1 } } });

// after
await collection.bulkWrite([{ insertOne: { document: { a: 1 } } }]);
Defensive patterns

Strategy: validation

Validate before calling

if (!Array.isArray(operations)) {
  throw new TypeError('operations must be an array');
}
await collection.bulkWrite(operations);

Type guard

function isBulkOpArray(v: unknown): v is Record<string, unknown>[] {
  return Array.isArray(v) && v.every(o => o != null && typeof o === 'object');
}

Prevention

When it happens

Trigger: Fires at src/collection.ts:367 when `!Array.isArray(operations)`. Occurs when a caller passes a single operation object, undefined, null, or a non-array iterable to bulkWrite.

Common situations: Passing one operation without wrapping in an array; passing undefined from an optional param; feeding a generator/Set; refactoring that lost the array literal; dynamic building that never wrapped results.

Related errors


AI-assisted analysis of mongodb/node-mongodb-native@dce7939f86 (2026-08-11). Data as JSON: /api/errors/982206892efff534. Report an issue: GitHub.

Appendix: source

Thrown at src/collection.ts:367

   * - `updateOne`
   * - `updateMany`
   * - `deleteOne`
   * - `deleteMany`
   *
   * If documents passed in do not contain the **_id** field,
   * one will be added to each of the documents missing it by the driver, mutating the document. This behavior
   * can be overridden by setting the **forceServerObjectId** flag.
   *
   * @param operations - Bulk operations to perform
   * @param options - Optional settings for the command
   * @throws MongoDriverError if operations is not an array
   */
  async bulkWrite(
    operations: ReadonlyArray<AnyBulkWriteOperation<TSchema>>,
    options?: BulkWriteOptions
  ): Promise<BulkWriteResult> {
    if (!Array.isArray(operations)) {
      throw new MongoInvalidArgumentError('Argument "operations" must be an array of documents');
    }

    options = resolveOptions(this, options ?? {});

    // TODO(NODE-7071): remove once the client doesn't need to be connected to construct
    // bulk operations
    const isConnected = this.client.topology != null;
    if (!isConnected) {
      await autoConnect(this.client);
    }

    // Create the bulk operation
    const bulk: BulkOperationBase =
      options.ordered === false
        ? this.initializeUnorderedBulkOp(options)
        : this.initializeOrderedBulkOp(options);

    // for each op go through and add to the bulk

View on GitHub (pinned to dce7939f86)