mongodb/node-mongodb-native · error · MongoNotConnectedError
Client must be connected before running operations
Error message
Client must be connected before running operations
What it means
autoConnect (src/operations/execute_operation.ts:147) throws a MongoNotConnectedError when an operation is attempted and the client has been closed (client.s.hasBeenClosed is true). Once close() is called, the client cannot be reused — this guard prevents silent no-ops against a dead topology.
Source
Thrown at src/operations/execute_operation.ts:147
timeoutContext,
session,
readPreference
});
} finally {
if (session?.owner != null && session.owner === owner) {
await session.endSession();
}
}
}
/**
* Connects a client if it has not yet been connected
* @internal
*/
export async function autoConnect(client: MongoClient): Promise<Topology> {
if (client.topology == null) {
if (client.s.hasBeenClosed) {
throw new MongoNotConnectedError('Client must be connected before running operations');
}
client.s.options.__skipPingOnConnect = true;
try {
await client.connect();
if (client.topology == null) {
throw new MongoRuntimeError(
'client.connect did not create a topology but also did not throw'
);
}
return client.topology;
} finally {
delete client.s.options.__skipPingOnConnect;
}
}
return client.topology;
}
/** @internal */View on GitHub (pinned to 3366c21a63)
Solutions
- Ensure all in-flight operations complete before calling client.close().
- If you need to resume work, create a new MongoClient rather than reusing the closed one.
- Review shutdown hooks to guarantee ordering: drain queries → close client.
- Avoid closing the client in middleware that runs per-request.
Example fix
// before
await client.close();
await collection.insertOne({ a: 1 }); // throws
// after
await collection.insertOne({ a: 1 });
await client.close();
// if more work is needed later, create a new client:
// const client2 = new MongoClient(uri); await client2.connect(); Defensive patterns
Strategy: try-catch
Validate before calling
function isClientOpen(client: MongoClient): boolean {
return !client.s.hasBeenClosed; // internal access; prefer tracking close() in app code
}
// better: track lifecycle explicitly in application state Try / catch
try {
await collection.insertOne(doc);
} catch (err) {
if (err instanceof MongoNotConnectedError) {
// client was closed; create a new client to continue
} else throw err;
} Prevention
- Call client.close() only after all in-flight operations have drained.
- Never reuse a closed MongoClient; create a new instance instead.
- Avoid closing clients in per-request middleware.
When it happens
Trigger: Calling any collection/db operation after client.close() has resolved, or after close() was initiated and an operation races in.
Common situations: Application shutdown ordering where close() fires before pending async operations drain, request-scoped clients that close prematurely, or accidental double-use of a client in a graceful-shutdown handler.
Related errors
- MongoClient must be connected to perform this operation
- This batch has already been executed, create new batch to ex
- ChangeStream is closed
- Option "hostAddress" is required
- Unexpected HostAddress ${JSON.stringify(hostAddress)}
AI-assisted analysis of mongodb/node-mongodb-native@3366c21a63 (2026-08-04).
Data as JSON: /data/errors/4c1f3cd79176ca4f.json.
Report an issue: GitHub.