types
Fix a TypeScript error in a `.mts` test file, remove an `any` or a `!`, decide between `@ts-expect-error: internal access` and `@ts-expect-error: TODO: implement typings`, or change a `.d.ts` file under `/typings`. Carries the public type inventory, the decision tree, the type architecture, and every known typing gap.
소스 정보
- 저장소
- sidorares/node-mysql2
- 최근 소스 활동
- 2026년 8월 9일 07:37
- 감지된 SKILL.md 언어
- 영어
- 스타
- 4,389
- 포크
- 680
설치 방법
기본적으로 소스를 먼저 확인하는 Prompt가 선택됩니다. 직접 명령으로 전환하거나 로컬 사본을 다운로드할 수도 있습니다.
소스 파일 검토
설치 여부를 결정하기 전에 SKILL.md와 SkillsMP에 표시된 보조 파일을 읽어 보세요.
파일 탐색기
3 개 파일SKILL.md 표시 중
SKILL.md
소스 지침 · 읽기 전용 미리보기- name
- types
- description
- Fix a TypeScript error in a `.mts` test file, remove an `any` or a `!`, decide between `@ts-expect-error: internal access` and `@ts-expect-error: TODO: implement typings`, or change a `.d.ts` file under `/typings`. Carries the public type inventory, the decision tree, the type architecture, and every known typing gap.
- argument-hint
- Optionally name the test file or the type to fix, or leave empty
- user-invocable
- true
# MySQL2 — Typings Skill
Reference for fixing TypeScript types in `.mts` test files, and for guiding the conversion of `/lib` to TypeScript.
For how the types are organized, connected, and composed, see [`rules/architecture.md`](rules/architecture.md).
For the categorized list of known type gaps, see [`rules/gaps.md`](rules/gaps.md).
---
## 1. Public type inventory
Every type below is importable from the library. Check this inventory before reaching for `@ts-expect-error`.
### From `index.js` (callback API)
| Category | Types | Source (relative to `typings/mysql/`) |
| ----------- | --------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------- |
| Packets | `RowDataPacket`, `ResultSetHeader`, `FieldPacket`, `OkPacket` _(deprecated)_, `Field` _(deprecated, now `TypeCastField`)_, `ProcedureCallPacket<T>` | `lib/protocol/packets/*.d.ts` |
| Connection | `Connection`, `ConnectionOptions` (40+ props), `ConnectionState`, `SslOptions` | `lib/Connection.d.ts` |
| Pool | `Pool`, `PoolOptions` (extends ConnectionOptions), `PoolConnection` | `lib/Pool.d.ts`, `lib/PoolConnection.d.ts` |
| Cluster | `PoolCluster`, `PoolClusterOptions`, `PoolNamespace` | `lib/PoolCluster.d.ts` |
| Query | `Query`, `QueryOptions`, `QueryError`, `QueryValues`, `ExecuteValues`, `StreamOptions` | `lib/protocol/sequences/Query.d.ts` |
| Prepare | `Prepare`, `PrepareStatementInfo` | `lib/protocol/sequences/Prepare.d.ts` |
| Parsers | `TypeCast`, `TypeCastField`, `TypeCastGeometry`, `TypeCastNext`, `TypeCastType` | `lib/parsers/typeCast.d.ts` |
| Constants | `Types`, `Charsets`, `CharsetToEncoding` | `lib/constants/*.d.ts` |
| Auth | `AuthPlugin`, `authPlugins` | `lib/Auth.d.ts` |
| Server | `Server`, `OkPacketParams`, `ErrorPacketParams` | `lib/Server.d.ts`, `lib/protocol/packets/params/*.d.ts` |
| Tracing | `QueryTraceContext`, `ExecuteTraceContext`, `ConnectTraceContext`, `PoolConnectTraceContext` | `lib/Tracing.d.ts` |
| Utilities | `escape()`, `escapeId()`, `format()`, `raw()`, `setMaxParserCache()`, `clearParserCache()` | `index.d.ts` |
| SQL escaper | `Raw`, `SqlValue`, `Timezone` | re-export from `sql-escaper` |
| Factory | `createConnection()`, `createPool()`, `createPoolCluster()`, `createServer()` | `index.d.ts` |
| Config | `ConnectionConfig` (interface with static methods: `mergeFlags`, `getDefaultFlags`, `getCharsetNumber`, `getSSLProfile`, `parseUrl`) | `index.d.ts` |
### From `promise.js`
Re-exports everything above, with these differences:
| Type | Difference vs callback |
| ---------------------------------------------- | -------------------------------------------------------------------------------------- |
| `Connection` | `.query()`/`.execute()` return `Promise<[T, FieldPacket[]]>` instead of `Query` |
| `Pool` (interface extends Connection) | `.getConnection()` returns `Promise<PoolConnection>` |
| `PoolConnection` (extends Connection) | has `release()` and `Symbol.asyncDispose` |
| `PoolCluster` (interface extends EventEmitter) | `.getConnection()` returns `Promise<PoolConnection>`, `.end()` returns `Promise<void>` |
| `PoolNamespace` (interface) | `.getConnection()` returns `Promise<PoolConnection>` |
| `PreparedStatementInfo` | `.execute()` returns `Promise<[T, FieldPacket[]]>`, `.close()` returns `Promise<void>` |
| `createConnection()` | returns `Promise<Connection>`, against a synchronous `Connection` in the callback API |
| `createPool()` | returns `Pool` synchronously, same as the callback API |
| `createPoolCluster()` | returns `PoolCluster` synchronously, same as the callback API |
### Connection methods (callback-based)
- `.query(sql)`, `.query(sql, values)`, `.query(options)`, `.query(options, values)` return `Query`.
- `.execute(sql)`, `.execute(sql, values)`, `.execute(options)`, `.execute(options, values)` return `Query`.
- `.prepare(sql, callback?)` returns `Prepare`.
- `.unprepare(sql)` returns `PrepareStatementInfo`.
- `.promise(promiseImpl?)` returns the promise-wrapped connection.
- `.connect(cb?)`, `.end(cb?)`, `.destroy()`, `.pause()`, `.resume()`, `.ping(cb?)`.
- `.beginTransaction(cb)`, `.commit(cb?)`, `.rollback(cb)`, `.changeUser(options, cb?)`.
- `.escape(value)`, `.escapeId(value)`, `.format(sql, values?)`.
### Connection methods (server-side, on incoming connections)
- `.serverHandshake(args)` initiates the server handshake.
- `.writeOk(params?: OkPacketParams)` sends an OK packet.
- `.writeError(params?: ErrorPacketParams)` sends an error packet.
- `.writeEof(warnings?, statusFlags?)` sends an EOF packet.
- `.writeTextResult(rows?, columns?)` sends a result set.
- `.writePacket(packet)` sends a raw packet.
### Union types
- `QueryResult` = `OkPacket | ResultSetHeader | ResultSetHeader[] | RowDataPacket[] | RowDataPacket[][] | OkPacket[] | ProcedureCallPacket`
- `ConnectionState` = `'disconnected' | 'protocol_handshake' | 'connected' | 'authenticated' | 'error'`
---
## 2. Decision tree for type errors
Classify the error before fixing it.
### 2.1. The library type exists
When the calling function already declares the callback signature, let TypeScript infer the parameter types instead of annotating them again.
```ts
// ✅ Correct: the types flow from the .query() signature
connection.query('SELECT 1', (err, rows, fields) => { ... });
// ❌ Wrong: annotations that duplicate what inference already provides
connection.query('SELECT 1', (err: QueryError | null, rows: RowDataPacket[]) => { ... });
```
This is the fix for every `any` on a callback parameter. Remove the annotation, do not replace it:
| Pattern with `any` | Fix |
| ------------------------------------ | --------------------- |
| `(err: any, result: any)` | `(err, result)` |
| `(err: any, rows: any)` | `(err, rows)` |
| `(err: any, rows: any, fields: any)` | `(err, rows, fields)` |
| `(err: any, connection: any)` | `(err, connection)` |
| `(err: any)` | `(err)` |
Annotate explicitly only where inference cannot reach, such as a standalone callback or a calling function without typings:
```ts
import type { TypeCastField } from '../../index.js';
const conn = createConnection({
typeCast: (field: TypeCastField) => field.string(),
});
```
Query and execute results in the promise API still need their generic:
```ts
import type { RowDataPacket } from '../../promise.js';
const [rows] = await connection.query<RowDataPacket[]>('SELECT 1');
```
### 2.2. The API exists at runtime, the types do not
The call works, but `/typings` declares it incompletely or not at all. Mark it with `@ts-expect-error: TODO: implement typings`, which flags the work for a later typings fix.
Working runtime code that TypeScript rejects is a typings gap, never a code bug. Wrong arity, a missing overload, an unrecognized property: all of them mean the declaration is behind the implementation. Add the comment and leave the call exactly as it was. Never rewrite working code to satisfy a wrong type definition.
```ts
// @ts-expect-error: TODO: implement typings
const server = mysql.createServer();
// @ts-expect-error: TODO: implement typings
server.listen(3307, () => {
/* ... */
});
```
Every known gap is categorized in [`rules/gaps.md`](rules/gaps.md).
### 2.3. The property is internal
The test deliberately reaches for an implementation detail that sits outside the public API and will never be typed. Mark it with `@ts-expect-error: internal access`.
Anything starting with `_` qualifies: `connection._protocol`, `connection._statements`, `connection._handshakePacket`, `pool._freeConnections`, `pool._allConnections`, `packet._buf`. So does `connection.stream`, the raw socket, despite the missing underscore.
```ts
// @ts-expect-error: internal access
const protocol = connection._protocol;
// @ts-expect-error: internal access
assert.equal(pool._freeConnections.length, 0);
```
### 2.4. The shape belongs to the test
A structure the test invents, with no library type behind it. Declare a `type` alias, never an `interface`, or annotate it inline.
```ts
type DateTimeRow = RowDataPacket & {
date: string | null;
time: string | null;
datetime: string | null;
};
const [rows] = await connection.query<DateTimeRow[]>(
'SELECT date, time, datetime FROM test_table'
);
// A one-off shape intersects RowDataPacket inline
const [rows] = await connection.query<(RowDataPacket & { count: number })[]>(
'SELECT COUNT(*) as count FROM test_table'
);
```
---
## 3. Import conventions
1. **`import type`** for type-only imports:
```ts
import type { RowDataPacket, FieldPacket } from '../../promise.js';
import type { TypeCastField, ConnectionOptions } from '../../index.js';
```
GitHub에서 보기이 SKILL.md는 매우 커서 SkillsMP가 여기에는 첫 섹션만 미리 보여줍니다. GitHub에서 보기