diff --git a/examples/node-mysql2/src/db/query_sql.ts b/examples/node-mysql2/src/db/query_sql.ts index 1673007..c79988f 100644 --- a/examples/node-mysql2/src/db/query_sql.ts +++ b/examples/node-mysql2/src/db/query_sql.ts @@ -9,11 +9,11 @@ SELECT id, name, bio FROM authors WHERE id = ? LIMIT 1`; export interface GetAuthorArgs { - id: number; + id: string; } export interface GetAuthorRow { - id: number; + id: string; name: string; bio: string | null; } @@ -40,7 +40,7 @@ SELECT id, name, bio FROM authors ORDER BY name`; export interface ListAuthorsRow { - id: number; + id: string; name: string; bio: string | null; } @@ -104,7 +104,7 @@ DELETE FROM authors WHERE id = ?`; export interface DeleteAuthorArgs { - id: number; + id: string; } export async function deleteAuthor(client: Client, args: DeleteAuthorArgs): Promise { @@ -127,8 +127,8 @@ export interface TestRow { cMediumint: number | null; cInt: number | null; cInteger: number | null; - cBigint: number | null; - cSerial: number; + cBigint: string | null; + cSerial: string; cDecimal: string | null; cDec: string | null; cNumeric: string | null; diff --git a/examples/node-mysql2/src/main.ts b/examples/node-mysql2/src/main.ts index fcf7596..d8576e3 100644 --- a/examples/node-mysql2/src/main.ts +++ b/examples/node-mysql2/src/main.ts @@ -22,6 +22,8 @@ async function main() { user: url.username, password: url.password, database: url.pathname.substring(1), + supportBigNumbers: true, + bigNumberStrings: true, ssl: { // TODO: FIXME rejectUnauthorized: false, diff --git a/examples/sqlc.dev.yaml b/examples/sqlc.dev.yaml index d2a69a0..f622ec1 100644 --- a/examples/sqlc.dev.yaml +++ b/examples/sqlc.dev.yaml @@ -49,6 +49,9 @@ sql: options: runtime: node driver: mysql2 + mysql2: + big_number_strings: true + support_big_numbers: true - schema: "authors/mysql/schema.sql" queries: "authors/mysql/query.sql" engine: "mysql" diff --git a/src/app.ts b/src/app.ts index e1dec6f..e3a077c 100644 --- a/src/app.ts +++ b/src/app.ts @@ -31,7 +31,7 @@ import { argName, colName } from "./drivers/utlis"; import { Driver as Sqlite3Driver } from "./drivers/better-sqlite3"; import { Driver as PgDriver } from "./drivers/pg"; import { Driver as PostgresDriver } from "./drivers/postgres"; -import { Driver as MysqlDriver } from "./drivers/mysql2"; +import { Mysql2Options, Driver as MysqlDriver } from "./drivers/mysql2"; // Read input from stdin const input = readInput(); @@ -43,6 +43,7 @@ writeOutput(result); interface Options { runtime?: string; driver?: string; + mysql2?: Mysql2Options } interface Driver { @@ -78,10 +79,10 @@ interface Driver { ) => Node; } -function createNodeGenerator(driver?: string): Driver { - switch (driver) { +function createNodeGenerator(options: Options): Driver { + switch (options.driver) { case "mysql2": { - return new MysqlDriver(); + return new MysqlDriver(options.mysql2); } case "pg": { return new PgDriver(); @@ -93,7 +94,7 @@ function createNodeGenerator(driver?: string): Driver { return new Sqlite3Driver(); } } - throw new Error(`unknown driver: ${driver}`); + throw new Error(`unknown driver: ${options.driver}`); } function codegen(input: GenerateRequest): GenerateResponse { @@ -105,7 +106,7 @@ function codegen(input: GenerateRequest): GenerateResponse { options = JSON.parse(text) as Options; } - const driver = createNodeGenerator(options.driver); + const driver = createNodeGenerator(options); // TODO: Verify options, parse them from protobuf honestly @@ -146,17 +147,15 @@ ${query.text}` ) ); - const ctype = driver.columnType; - let argIface = undefined; let returnIface = undefined; if (query.params.length > 0) { argIface = `${query.name}Args`; - nodes.push(argsDecl(argIface, ctype, query.params)); + nodes.push(argsDecl(argIface, driver, query.params)); } if (query.columns.length > 0) { returnIface = `${query.name}Row`; - nodes.push(rowDecl(returnIface, ctype, query.columns)); + nodes.push(rowDecl(returnIface, driver, query.columns)); } switch (query.cmd) { @@ -240,7 +239,7 @@ function queryDecl(name: string, sql: string) { function argsDecl( name: string, - ctype: (c?: Column) => TypeNode, + driver: Driver, params: Parameter[] ) { return factory.createInterfaceDeclaration( @@ -253,7 +252,7 @@ function argsDecl( undefined, factory.createIdentifier(argName(i, param.column)), undefined, - ctype(param.column) + driver.columnType(param.column) ) ) ); @@ -261,7 +260,7 @@ function argsDecl( function rowDecl( name: string, - ctype: (c?: Column) => TypeNode, + driver: Driver, columns: Column[] ) { return factory.createInterfaceDeclaration( @@ -274,7 +273,7 @@ function rowDecl( undefined, factory.createIdentifier(colName(i, column)), undefined, - ctype(column) + driver.columnType(column) ) ) ); diff --git a/src/drivers/mysql2.ts b/src/drivers/mysql2.ts index 731db8d..7859ade 100644 --- a/src/drivers/mysql2.ts +++ b/src/drivers/mysql2.ts @@ -5,6 +5,11 @@ import { SyntaxKind, NodeFlags, TypeNode, factory } from "typescript"; import { Parameter, Column, Query } from "../gen/plugin/codegen_pb"; import { argName, colName } from "./utlis"; +export interface Mysql2Options { + support_big_numbers?: boolean; + big_number_strings?: boolean; +} + function funcParamsDecl(iface: string | undefined, params: Parameter[]) { let funcParams = [ factory.createParameterDeclaration( @@ -40,6 +45,12 @@ function funcParamsDecl(iface: string | undefined, params: Parameter[]) { } export class Driver { + private readonly options: Mysql2Options + + constructor(options?: Mysql2Options) { + this.options = options ?? {} + } + columnType(column?: Column): TypeNode { if (column === undefined || column.type === undefined) { return factory.createKeywordTypeNode(SyntaxKind.AnyKeyword); @@ -49,6 +60,18 @@ export class Driver { switch (column.type.name) { case "bigint": { typ = factory.createKeywordTypeNode(SyntaxKind.NumberKeyword); + + if (this.options.support_big_numbers) { + if (this.options.big_number_strings) { + typ = factory.createKeywordTypeNode(SyntaxKind.StringKeyword) + } else { + typ = factory.createUnionTypeNode([ + factory.createKeywordTypeNode(SyntaxKind.NumberKeyword), + factory.createKeywordTypeNode(SyntaxKind.StringKeyword) + ]) + } + } + break; } case "binary": {