sidorares/node-mysql2 · error · Error
You have tried to call .then(), .catch(), or invoked await…
Error message
You have tried to call .then(), .catch(), or invoked await on the result of query that is not a promise, which is a programming error. Try calling con.promise().query(), or require('mysql2/promise') instead of 'mysql2' for a promise-compatible version of the query interface. To learn how to use async/await or Promises check out documentation at https://sidorares.github.io/node-mysql2/docs#using-promise-wrapper, or the mysql2 documentation at https://sidorares.github.io/node-mysql2/docs/documentation/promise-wrapper What it means
The callback-mode Query object defines a then() trap (lib/commands/query.js:44-50) that logs and throws this message when the developer treats the return value of connection.query() as a thenable or awaits it. The callback API returns a Query (a EventEmitter/Readable stream), not a Promise; awaiting it is a programming error. The trap exists to produce a clear message instead of silent misbehavior.
Solutions
- Use the promise API: const conn = require('mysql2/promise').createConnection(...), then await conn.query(sql).
- Or call the promise wrapper on an existing callback connection: await conn.promise().query(sql).
- For streams, consume the Query as a Readable (query.on('result', ...)) instead of awaiting.
Example fix
// before
const mysql = require('mysql2');
const conn = mysql.createConnection({});
const rows = await conn.query('SELECT 1'); // throws
// after
const conn = require('mysql2/promise').createConnection({});
const [rows] = await conn.query('SELECT 1'); Defensive patterns
Strategy: type-guard
Type guard
// promise API: return value is a Promise
import type { Pool as PromisePool } from 'mysql2/promise';
function isPromiseQuery<T>(r: Promise<[T]> | unknown): r is Promise<[T]> {
return r instanceof Promise;
} Prevention
- Standardize one import path per codebase: either 'mysql2' (callback) or 'mysql2/promise'.
- Always use .promise() on callback connections inside async functions.
- Lint for await on non-Promise return values (typescriptAwaitThenableType).
When it happens
Trigger: await connection.query(sql) on a callback-mode connection; const rows = await conn.query(sql) where conn came from require('mysql2'); chaining .then() on the Query object; using the callback API inside an async function and forgetting .promise().
Common situations: Mixing require('mysql2') and require('mysql2/promise') in the same codebase; copy-paste from a promise-style example into a callback-style connection; refactoring a callback handler to async/await without switching the API.
Related errors
- Bind parameters must be array if namedPlaceholders…
- Bind parameters must not contain function(s). To pass the…
- Bind parameters must not contain undefined. To pass SQL…
AI-assisted analysis of sidorares/node-mysql2@8b1f829d37 (2026-08-11).
Data as JSON: /api/errors/9563707f9a26077b.
Report an issue: GitHub.
Appendix: source
Thrown at lib/commands/query.js:49
this.queryTimeout = null;
this._fieldCount = 0;
this._rowParser = null;
this._fields = [];
this._rows = [];
this._receivedFieldsCount = 0;
this._resultIndex = 0;
this._localStream = null;
this._unpipeStream = function () {};
this._streamFactory = options.infileStreamFactory;
this._connection = null;
}
then() {
const err =
"You have tried to call .then(), .catch(), or invoked await on the result of query that is not a promise, which is a programming error. Try calling con.promise().query(), or require('mysql2/promise') instead of 'mysql2' for a promise-compatible version of the query interface. To learn how to use async/await or Promises check out documentation at https://sidorares.github.io/node-mysql2/docs#using-promise-wrapper, or the mysql2 documentation at https://sidorares.github.io/node-mysql2/docs/documentation/promise-wrapper";
console.log(err);
throw new Error(err);
}
start(_packet, connection) {
if (connection.config.debug) {
console.log(' Sending query command: %s', this.sql);
}
this._connection = connection;
this.options = Object.assign({}, connection.config, this._queryOptions);
this._setTimeout();
const clientFlags =
connection.config.clientFlags & (connection.serverCapabilityFlags || 0);
const cmdPacket = new Packets.Query(
this.sql,
connection.config.charsetNumber,
this._queryOptions.attributes,
clientFlags
);View on GitHub (pinned to 8b1f829d37)