From c6e08e076c6dcfedc90aec0bdba0aa29c8602065 Mon Sep 17 00:00:00 2001 From: Ryan Rasti Date: Sat, 15 Aug 2026 16:30:43 -0700 Subject: [PATCH] feat: generate reviewed Oracle types and functions from catalogs --- bin/startora | 4 +- package.json | 5 + src/drivers/oracle-url.ts | 33 ++ src/drivers/oracle.test.ts | 11 +- src/drivers/oracle.ts | 24 +- src/types/emission/emit.ts | 21 +- src/types/oracle/common.test.ts | 117 ++++++ src/types/oracle/config.test.ts | 21 + src/types/oracle/emit.ts | 264 +++++++++++++ src/types/oracle/generated/any.ts | 54 +++ src/types/oracle/generated/binary_double.ts | 106 +++++ src/types/oracle/generated/binary_float.ts | 78 ++++ src/types/oracle/generated/blob.ts | 22 ++ src/types/oracle/generated/bool.ts | 30 ++ src/types/oracle/generated/char.ts | 23 ++ src/types/oracle/generated/clob.ts | 23 ++ src/types/oracle/generated/date.ts | 87 +++++ src/types/oracle/generated/intervalds.ts | 46 +++ src/types/oracle/generated/intervalym.ts | 46 +++ src/types/oracle/generated/json.ts | 27 ++ src/types/oracle/generated/nclob.ts | 23 ++ src/types/oracle/generated/number.ts | 155 ++++++++ src/types/oracle/generated/nvarchar2.ts | 25 ++ src/types/oracle/generated/raw.ts | 26 ++ src/types/oracle/generated/rowid.ts | 23 ++ src/types/oracle/generated/time.ts | 28 ++ src/types/oracle/generated/timestamp.ts | 50 +++ src/types/oracle/generated/timestampltz.ts | 38 ++ src/types/oracle/generated/timestamptz.ts | 36 ++ src/types/oracle/generated/timetz.ts | 28 ++ src/types/oracle/generated/urowid.ts | 23 ++ src/types/oracle/generated/varchar2.ts | 164 ++++++++ src/types/oracle/generated/vector.ts | 23 ++ src/types/oracle/generated/xmltype.ts | 23 ++ src/types/oracle/index.ts | 28 ++ src/types/oracle/introspect.test.ts | 67 ++++ src/types/oracle/introspect.ts | 412 ++++++++++++++++++++ src/types/oracle/overrides/any.ts | 41 ++ src/types/oracle/overrides/binary_double.ts | 6 + src/types/oracle/overrides/binary_float.ts | 6 + src/types/oracle/overrides/blob.ts | 7 + src/types/oracle/overrides/bool.ts | 21 + src/types/oracle/overrides/number.ts | 8 + src/types/oracle/overrides/raw.ts | 7 + src/types/oracle/smoke.test.ts | 112 ++++++ src/types/postgres/overrides/any.ts | 17 +- src/types/sql-value.ts | 21 + src/types/sqlite/generated/any.ts | 20 +- src/types/sqlite/generated/blob.ts | 8 +- src/types/sqlite/generated/integer.ts | 2 +- src/types/sqlite/generated/text.ts | 16 +- src/types/sqlite/overrides/any.ts | 20 +- src/types/sqlite/overrides/blob.ts | 4 +- src/util.ts | 10 + tsconfig.json | 1 + tsdown.config.ts | 2 +- vitest.config.ts | 1 + 57 files changed, 2462 insertions(+), 82 deletions(-) create mode 100644 src/drivers/oracle-url.ts create mode 100644 src/types/oracle/common.test.ts create mode 100644 src/types/oracle/config.test.ts create mode 100644 src/types/oracle/emit.ts create mode 100644 src/types/oracle/generated/any.ts create mode 100644 src/types/oracle/generated/binary_double.ts create mode 100644 src/types/oracle/generated/binary_float.ts create mode 100644 src/types/oracle/generated/blob.ts create mode 100644 src/types/oracle/generated/bool.ts create mode 100644 src/types/oracle/generated/char.ts create mode 100644 src/types/oracle/generated/clob.ts create mode 100644 src/types/oracle/generated/date.ts create mode 100644 src/types/oracle/generated/intervalds.ts create mode 100644 src/types/oracle/generated/intervalym.ts create mode 100644 src/types/oracle/generated/json.ts create mode 100644 src/types/oracle/generated/nclob.ts create mode 100644 src/types/oracle/generated/number.ts create mode 100644 src/types/oracle/generated/nvarchar2.ts create mode 100644 src/types/oracle/generated/raw.ts create mode 100644 src/types/oracle/generated/rowid.ts create mode 100644 src/types/oracle/generated/time.ts create mode 100644 src/types/oracle/generated/timestamp.ts create mode 100644 src/types/oracle/generated/timestampltz.ts create mode 100644 src/types/oracle/generated/timestamptz.ts create mode 100644 src/types/oracle/generated/timetz.ts create mode 100644 src/types/oracle/generated/urowid.ts create mode 100644 src/types/oracle/generated/varchar2.ts create mode 100644 src/types/oracle/generated/vector.ts create mode 100644 src/types/oracle/generated/xmltype.ts create mode 100644 src/types/oracle/index.ts create mode 100644 src/types/oracle/introspect.test.ts create mode 100644 src/types/oracle/introspect.ts create mode 100644 src/types/oracle/overrides/any.ts create mode 100644 src/types/oracle/overrides/binary_double.ts create mode 100644 src/types/oracle/overrides/binary_float.ts create mode 100644 src/types/oracle/overrides/blob.ts create mode 100644 src/types/oracle/overrides/bool.ts create mode 100644 src/types/oracle/overrides/number.ts create mode 100644 src/types/oracle/overrides/raw.ts create mode 100644 src/types/oracle/smoke.test.ts diff --git a/bin/startora b/bin/startora index bc51b2bd..547769b6 100755 --- a/bin/startora +++ b/bin/startora @@ -10,7 +10,9 @@ PORT="${TYPEGRES_ORA_PORT:-1521}" APP_USER="${TYPEGRES_ORA_USER:-typegres}" APP_PASSWORD="${TYPEGRES_ORA_PASSWORD:-typegres}" SYS_PASSWORD="${TYPEGRES_ORA_SYS_PASSWORD:-oracle}" -URL="${ORACLE_URL:-${APP_USER}/${APP_PASSWORD}@localhost:${PORT}/FREEPDB1}" +URL_USER="$(node -e 'process.stdout.write(encodeURIComponent(process.argv[1]))' "$APP_USER")" +URL_PASSWORD="$(node -e 'process.stdout.write(encodeURIComponent(process.argv[1]))' "$APP_PASSWORD")" +URL="${ORACLE_URL:-oracle://${URL_USER}:${URL_PASSWORD}@localhost:${PORT}/FREEPDB1}" if [ -z "${ORACLE_URL:-}" ]; then export ORACLE_URL="$URL" diff --git a/package.json b/package.json index cb3dc9da..44deef6b 100644 --- a/package.json +++ b/package.json @@ -29,6 +29,10 @@ "import": "./dist/types/sqlite/index.mjs", "types": "./dist/types/sqlite/index.d.mts" }, + "./oracle": { + "import": "./dist/types/oracle/index.mjs", + "types": "./dist/types/oracle/index.d.mts" + }, "./exoeval": { "import": "./dist/exoeval/index.mjs", "types": "./dist/exoeval/index.d.mts" @@ -93,6 +97,7 @@ "scripts": { "build": "tsdown", "codegen": "node --experimental-strip-types src/types/postgres/emit.ts && node --experimental-strip-types src/types/sqlite/emit.ts", + "codegen:oracle": "node --experimental-strip-types src/types/oracle/emit.ts", "codegen:check": "tmp=$(mktemp -d) && node --experimental-strip-types src/types/postgres/emit.ts --out-dir \"$tmp/pg\" && { diff -r \"$tmp/pg\" src/types/postgres/generated || { echo 'src/types/postgres/generated is stale - run `npm run codegen` and commit.' >&2; rm -rf \"$tmp\"; exit 1; }; } && node --experimental-strip-types src/types/sqlite/emit.ts --out-dir \"$tmp/sqlite\" && { diff -r \"$tmp/sqlite/generated\" src/types/sqlite/generated || { echo 'src/types/sqlite/generated is stale - run `npm run codegen` and commit.' >&2; rm -rf \"$tmp\"; exit 1; }; } && rm -rf \"$tmp\"", "lint": "eslint src", "typecheck": "tsgo --noEmit", diff --git a/src/drivers/oracle-url.ts b/src/drivers/oracle-url.ts new file mode 100644 index 00000000..ca843ecd --- /dev/null +++ b/src/drivers/oracle-url.ts @@ -0,0 +1,33 @@ +import type oracledb from "oracledb"; + +export const parseOraclePoolAttributes = (value: string): oracledb.PoolAttributes => { + try { + const url = new URL(value); + const user = decodeURIComponent(url.username); + const password = decodeURIComponent(url.password); + const service = decodeURIComponent(url.pathname); + if ( + url.protocol !== "oracle:" || + !user || + !password || + !url.host || + service === "" || + service === "/" + ) { + throw new Error(); + } + return { user, password, connectString: `${url.host}${service}` }; + } catch { + throw new Error( + `ORACLE_URL must be oracle://user:password@host:port/service, got ${JSON.stringify(value)}`, + ); + } +}; + +export const requireOraclePoolAttributes = (): oracledb.PoolAttributes => { + const value = process.env["ORACLE_URL"]; + if (!value) { + throw new Error("ORACLE_URL is not set. Run bin/startora and export its URL before Oracle codegen."); + } + return parseOraclePoolAttributes(value); +}; diff --git a/src/drivers/oracle.test.ts b/src/drivers/oracle.test.ts index 6eb5b406..ecafc6cc 100644 --- a/src/drivers/oracle.test.ts +++ b/src/drivers/oracle.test.ts @@ -7,18 +7,12 @@ // surface, no query builder — those land in later steps. import { describe, test, expect, beforeAll, afterAll } from "vitest"; import { OracleDriver } from "./oracle"; +import { parseOraclePoolAttributes } from "./oracle-url"; import { Database } from "../database"; import { compile, sql } from "../builder/sql"; import type { Connection } from "../database"; const url = process.env["ORACLE_URL"]; -const parseUrl = (s: string) => { - const m = /^([^/]+)\/([^@]+)@(.+)$/.exec(s); - if (!m) { - throw new Error(`ORACLE_URL must be user/password@host:port/service, got ${JSON.stringify(s)}`); - } - return { user: m[1]!, password: m[2]!, connectString: m[3]! }; -}; // Always-on: Connection construction + compile + statement execute, no Oracle process. test("oracle Connection constructs without a live engine", async () => { @@ -47,7 +41,8 @@ describe.skipIf(!url)("oracle driver", () => { let conn: Connection; beforeAll(async () => { - driver = await OracleDriver.create(parseUrl(url!)); + if (!url) { throw new Error("ORACLE_URL is not set"); } + driver = await OracleDriver.create(parseOraclePoolAttributes(url)); db = new Database(); conn = db.connect(driver); }); diff --git a/src/drivers/oracle.ts b/src/drivers/oracle.ts index bab42a9b..752124ab 100644 --- a/src/drivers/oracle.ts +++ b/src/drivers/oracle.ts @@ -8,8 +8,19 @@ import type { Driver, ExecuteFn, QueryResult } from "./types"; // imports `typegres/drivers/oracle`. // // fetchAsString is the full set node-oracledb accepts (NUMBER/DATE/ -// BUFFER/CLOB/NCLOB). VARCHAR2 is already a string. Same contract as -// PgDriver: the driver returns raw text; typed coercion is downstream. +// BUFFER/CLOB/NCLOB). VARCHAR2 is already a string; BLOB is fetched as +// Buffer. Typed coercion remains downstream. + +const oracleBinds = (values: readonly unknown[]): oracledb.BindParameters => + values.map((v) => v instanceof Uint8Array ? Buffer.from(v) : v) as oracledb.BindParameters; + +const normalizeRows = (rows: unknown[] | undefined): QueryResult["rows"] => + (rows ?? []).map((row) => Object.fromEntries( + Object.entries(row as { [key: string]: unknown }).map(([key, value]) => [ + key, + Buffer.isBuffer(value) ? value.toString("hex").toUpperCase() : value, + ]), + )) as QueryResult["rows"]; let fetchConfigured = false; const configureFetch = (): void => { @@ -24,6 +35,7 @@ const configureFetch = (): void => { oracledb.CLOB, oracledb.NCLOB, ]; + oracledb.fetchAsBuffer = [oracledb.BLOB]; fetchConfigured = true; }; @@ -40,11 +52,11 @@ export class OracleDriver implements Driver { async execute({ text, values }: CompiledSql): Promise { const conn = await this.pool.getConnection(); try { - const result = await conn.execute(text, values as oracledb.BindParameters, { + const result = await conn.execute(text, oracleBinds(values), { outFormat: oracledb.OUT_FORMAT_OBJECT, autoCommit: true, }); - return { rows: (result.rows ?? []) as QueryResult["rows"] }; + return { rows: normalizeRows(result.rows) }; } finally { await conn.close(); } @@ -54,11 +66,11 @@ export class OracleDriver implements Driver { const conn = await this.pool.getConnection(); try { return await cb(async ({ text, values }) => { - const result = await conn.execute(text, values as oracledb.BindParameters, { + const result = await conn.execute(text, oracleBinds(values), { outFormat: oracledb.OUT_FORMAT_OBJECT, autoCommit: false, }); - return { rows: (result.rows ?? []) as QueryResult["rows"] }; + return { rows: normalizeRows(result.rows) }; }); } finally { await conn.close(); diff --git a/src/types/emission/emit.ts b/src/types/emission/emit.ts index 93460ea3..5a3cb397 100644 --- a/src/types/emission/emit.ts +++ b/src/types/emission/emit.ts @@ -181,6 +181,7 @@ export const emitMethods = (host: TypeEntry, allFns: EmitFn[], cfg: EmitConfig): ...params .map((a, i) => (included(o.args.indexOf(a)) ? `runtime.NullOf` : null)) .filter((x): x is string => x !== null), + ...(o.variadic && included(o.args.length - 1) ? ["runtime.NullOf"] : []), ]; const nullUnion = nullParts.join(" | "); if (o.nullability === "maybe_null") { @@ -192,7 +193,7 @@ export const emitMethods = (host: TypeEntry, allFns: EmitFn[], cfg: EmitConfig): if (o.nullability === "always" || o.nullability === "on_error") { return formatTypeWithNull(retBase, "0 | 1"); } - if (params.length === 0) { + if (params.length === 0 && !o.variadic) { return formatTypeWithNull(retBase, nullParts[0] ?? "N"); } return formatTypeWithNull(retBase, `runtime.StrictNull<${nullUnion}>`); @@ -303,31 +304,33 @@ export const emitMethods = (host: TypeEntry, allFns: EmitFn[], cfg: EmitConfig): // params remain and the method is rest-only. const fixed = params; if (receiverGeneric(o)) { - // T binds the receiver (the return refers to it), so args don't - // need their own generics — plain unions suffice. + // T binds the receiver (the return refers to it), so fixed args + // don't need their own generics — plain unions suffice. const paramSrc = fixed.map((a, i) => { const resolved = formatTypeWithNull(resolveType(a.type, host, table), "any"); const prim = allowPrimitive ? primitiveUnionFor(a.type) : null; return `arg${i}${a.optional ? "?" : ""}: ${resolved}${prim ? ` | ${prim}` : ""}`; }); + const generics = ["T extends types.Any"]; if (variadic) { const last = o.args[o.args.length - 1]!; const resolved = formatTypeWithNull(resolveType(last.type, host, table), "any"); const prim = primitiveUnionFor(last.type); - paramSrc.push(`...rest: (${resolved}${prim ? ` | ${prim}` : ""})[]`); + generics.push(`R extends (${resolved}${prim ? ` | ${prim}` : ""})[]`); + paramSrc.push("...rest: R"); } - return `${name}>(${["this: T", ...paramSrc].join(", ")})`; + return `${name}<${generics.join(", ")}>(${["this: T", ...paramSrc].join(", ")})`; } - const genericDecl = fixed.length > 0 - ? `<${fixed.map((a, i) => buildArgGeneric(a, i, allowPrimitive)).join(", ")}>` - : ""; + const generics = fixed.map((a, i) => buildArgGeneric(a, i, allowPrimitive)); const paramSrc = fixed.map((a, i) => `arg${i}${a.optional ? "?" : ""}: M${i}`); if (variadic) { const last = o.args[o.args.length - 1]!; const resolved = formatTypeWithNull(resolveType(last.type, host, table), "any"); const prim = primitiveUnionFor(last.type); - paramSrc.push(`...rest: (${resolved}${prim ? ` | ${prim}` : ""})[]`); + generics.push(`R extends (${resolved}${prim ? ` | ${prim}` : ""})[]`); + paramSrc.push("...rest: R"); } + const genericDecl = generics.length > 0 ? `<${generics.join(", ")}>` : ""; return `${name}${genericDecl}(${paramSrc.join(", ")})`; }; diff --git a/src/types/oracle/common.test.ts b/src/types/oracle/common.test.ts new file mode 100644 index 00000000..55bfb2d7 --- /dev/null +++ b/src/types/oracle/common.test.ts @@ -0,0 +1,117 @@ +import { describe, expect, expectTypeOf, test } from "vitest"; +import { compile, sql, type Sql } from "../../builder/sql"; +import { compileOnlyDb } from "../../test-helpers"; +import { Bool, Date as OraDate, Number as OraNumber, Varchar2 } from "./index"; + +const db = compileOnlyDb("oracle"); +const compileOracle = (value: { toSql(): Sql }) => + compile(value.toSql(), { database: db }); + +describe("common Oracle supplement", () => { + test("numeric operators", () => { + expect(compileOracle(OraNumber.from(5).plus(3).times(2).negate())).toEqual({ + text: "(- ((CAST(:1 AS NUMBER) + CAST(:2 AS NUMBER)) * CAST(:3 AS NUMBER)))", + values: [5, 3, 2], + }); + }); + + test("date arithmetic", () => { + expect(compileOracle(OraDate.from(sql`DATE '2025-01-15'`).plus(2))).toEqual({ + text: "(DATE '2025-01-15' + CAST(:1 AS NUMBER))", + values: [2], + }); + expect(compileOracle( + OraDate.from(sql`DATE '2025-01-15'`).minus(OraDate.from(sql`DATE '2025-01-10'`)), + )).toEqual({ + text: "(DATE '2025-01-15' - DATE '2025-01-10')", + values: [], + }); + }); + + test("word operators derive camelCase aliases", () => { + expect(compileOracle(Varchar2.from("hello").like("h%"))).toEqual({ + text: "(CAST(:1 AS VARCHAR2(4000)) LIKE CAST(:2 AS VARCHAR2(4000)))", + values: ["hello", "h%"], + }); + expect(compileOracle(Varchar2.from("hello").notLike("x%"))).toEqual({ + text: "(CAST(:1 AS VARCHAR2(4000)) NOT LIKE CAST(:2 AS VARCHAR2(4000)))", + values: ["hello", "x%"], + }); + }); + + test("NVL2 dispatches its result arguments", () => { + expect(compileOracle(OraNumber.from(1).nvl2("yes", "no"))).toEqual({ + text: '"NVL2"(CAST(:1 AS NUMBER), CAST(:2 AS VARCHAR2(4000)), CAST(:3 AS VARCHAR2(4000)))', + values: [1, "yes", "no"], + }); + }); + + test("common scalar additions", () => { + expect(compileOracle(OraNumber.from(5).widthBucket(0, 10, 5))).toEqual({ + text: '"WIDTH_BUCKET"(CAST(:1 AS NUMBER), CAST(:2 AS NUMBER), CAST(:3 AS NUMBER), CAST(:4 AS NUMBER))', + values: [5, 0, 10, 5], + }); + expect(compileOracle(Bool.from(false).lnnvl())).toEqual({ + text: '"LNNVL"(CAST(:1 AS BOOLEAN))', + values: [false], + }); + }); + + test("GREATEST and LEAST accept variadic values", () => { + expectTypeOf(OraNumber.from(5).greatest(7, 3)).toEqualTypeOf>(); + expectTypeOf(OraNumber.from(5).greatest(OraNumber.from(sql`NULL`))) + .toEqualTypeOf>(); + expect(compileOracle(OraNumber.from(5).greatest(7, 3))).toEqual({ + text: '"GREATEST"(CAST(:1 AS NUMBER), CAST(:2 AS NUMBER), CAST(:3 AS NUMBER))', + values: [5, 7, 3], + }); + expect(compileOracle(Varchar2.from("b").least("a", "c"))).toEqual({ + text: '"LEAST"(CAST(:1 AS VARCHAR2(4000)), CAST(:2 AS VARCHAR2(4000)), CAST(:3 AS VARCHAR2(4000)))', + values: ["b", "a", "c"], + }); + }); + + test("LISTAGG always returns nullable VARCHAR2", () => { + const value = OraNumber.from(5).listagg(","); + expectTypeOf(value).toEqualTypeOf>(); + expect(compileOracle(value)).toEqual({ + text: '"LISTAGG"(CAST(:1 AS NUMBER), CAST(:2 AS VARCHAR2(4000)))', + values: [5, ","], + }); + }); + + test("NULLIF is available on common types and always nullable", () => { + const value = OraNumber.from(5).nullif(5); + expectTypeOf(value).toEqualTypeOf>(); + expect(compileOracle(value)).toEqual({ + text: '"NULLIF"(CAST(:1 AS NUMBER), CAST(:2 AS NUMBER))', + values: [5, 5], + }); + }); + + test("format arguments are optional where Oracle permits omission", () => { + expect(compileOracle(OraNumber.from(5).toChar())).toEqual({ + text: '"TO_CHAR"(CAST(:1 AS NUMBER))', + values: [5], + }); + expect(compileOracle(Varchar2.from("1.5").toBinaryDouble())).toEqual({ + text: '"TO_BINARY_DOUBLE"(CAST(:1 AS VARCHAR2(4000)))', + values: ["1.5"], + }); + }); + + test("numeric statistical aggregates stay on NUMBER", () => { + const value = OraNumber.from(1).corr(2); + expectTypeOf(value).toEqualTypeOf>(); + expect(compileOracle(value)).toEqual({ + text: '"CORR"(CAST(:1 AS NUMBER), CAST(:2 AS NUMBER))', + values: [1, 2], + }); + expectTypeOf<"corr" extends keyof Varchar2<1> ? true : false>().toEqualTypeOf(); + }); + + test("nullable functions and excluded partial forms have honest types", () => { + expectTypeOf(Varchar2.from("abc").regexpSubstr("z")).toEqualTypeOf>(); + expectTypeOf<"decode" extends keyof Varchar2<1> ? true : false>().toEqualTypeOf(); + }); +}); diff --git a/src/types/oracle/config.test.ts b/src/types/oracle/config.test.ts new file mode 100644 index 00000000..b25f3bac --- /dev/null +++ b/src/types/oracle/config.test.ts @@ -0,0 +1,21 @@ +import { describe, expect, test } from "vitest"; +import { parseOraclePoolAttributes } from "../../drivers/oracle-url"; + +describe("Oracle connection configuration", () => { + test("parses standard URLs and percent-encoded credentials", () => { + expect(parseOraclePoolAttributes( + "oracle://type%2Fgres:p%40ss%2Fword@localhost:1521/FREEPDB1", + )).toEqual({ + user: "type/gres", + password: "p@ss/word", + connectString: "localhost:1521/FREEPDB1", + }); + }); + + test("rejects incomplete URLs without connecting", () => { + expect(() => parseOraclePoolAttributes("oracle://user:pass@localhost:1521")) + .toThrow("ORACLE_URL must be"); + expect(() => parseOraclePoolAttributes("typegres/typegres@localhost:1521/FREEPDB1")) + .toThrow("ORACLE_URL must be"); + }); +}); diff --git a/src/types/oracle/emit.ts b/src/types/oracle/emit.ts new file mode 100644 index 00000000..1aa9ac8e --- /dev/null +++ b/src/types/oracle/emit.ts @@ -0,0 +1,264 @@ +// Oracle dialect codegen: SYS.STANDARD typed scalar declarations, +// V$SQLFN_METADATA aggregate/operator inventory, and live engine +// verification feed the shared emitter. Generated files are committed. + +import oracledb from "oracledb"; +import * as path from "node:path"; +import { pathToFileURL } from "node:url"; +import { + writeGeneratedTree, + chromeImportLines, + metaDeclareLines, + typnameStaticLines, + scanOverrideNames, + type ClassChrome, + type EmitConfig, + type TypeEntry, +} from "../emission/emit.ts"; +import type { EmitFn } from "../emission/facts.ts"; +import { requireOraclePoolAttributes } from "../../drivers/oracle-url.ts"; +import { + introspect, + ORACLE_CAST_TARGET, + type OracleTypname, +} from "./introspect.ts"; + +const outDirFlag = process.argv.indexOf("--out-dir"); +const GENERATED_DIR = outDirFlag >= 0 + ? path.resolve(process.argv[outDirFlag + 1]!) + : path.resolve(import.meta.dirname, "generated"); +const OVERRIDES_DIR = path.resolve(import.meta.dirname, "overrides"); +const TYPES_INDEX = path.resolve(import.meta.dirname, "index.ts"); + +const TYPES: (TypeEntry & { typname: OracleTypname })[] = [ + { typname: "any", className: "Any", primitiveTsUnion: "number | string | boolean | Uint8Array" }, + { typname: "number", className: "Number", primitiveTs: "number" }, + { typname: "binary_float", className: "BinaryFloat", primitiveTs: "number" }, + { typname: "binary_double", className: "BinaryDouble", primitiveTs: "number" }, + { typname: "varchar2", className: "Varchar2", primitiveTs: "string" }, + { typname: "nvarchar2", className: "Nvarchar2", primitiveTs: "string" }, + { typname: "char", className: "Char", primitiveTs: "string" }, + { typname: "clob", className: "Clob", primitiveTs: "string" }, + { typname: "nclob", className: "Nclob", primitiveTs: "string" }, + { typname: "date", className: "Date", primitiveTs: "string" }, + { typname: "timestamp", className: "Timestamp", primitiveTs: "string" }, + { typname: "timestamptz", className: "Timestamptz", primitiveTs: "string" }, + { typname: "timestampltz", className: "Timestampltz", primitiveTs: "string" }, + { typname: "time", className: "Time", primitiveTs: "string" }, + { typname: "timetz", className: "Timetz", primitiveTs: "string" }, + { typname: "intervalym", className: "IntervalYm", primitiveTs: "string" }, + { typname: "intervalds", className: "IntervalDs", primitiveTs: "string" }, + { typname: "bool", className: "Bool", primitiveTs: "boolean" }, + { typname: "raw", className: "Raw", primitiveTsUnion: "Uint8Array" }, + { typname: "blob", className: "Blob", primitiveTsUnion: "Uint8Array" }, + { typname: "json", className: "Json", primitiveTs: "string" }, + { typname: "vector", className: "Vector", primitiveTs: "string" }, + { typname: "rowid", className: "Rowid", primitiveTs: "string" }, + { typname: "urowid", className: "Urowid", primitiveTs: "string" }, + { typname: "xmltype", className: "XmlType", primitiveTs: "string" }, +]; + +const CONFIG: EmitConfig = { + typeTable: new Map(TYPES.map((t) => [t.typname, t])), + noMethod: new Set(["coalesce", "in"]), +}; + +// Oracle's catalogs describe ordinary functions well, but expose +// operators as undocumented optimizer names and leave a few ubiquitous +// functions untyped. Keep this deliberately small and SQL-verified. +const ORACLE_REPLACED_FUNCTIONS = new Set([ + "CORR", "COVAR_POP", "COVAR_SAMP", "GREATEST", "LEAST", "LISTAGG", "NULLIF", + "STDDEV_POP", "STDDEV_SAMP", "VAR_POP", "VAR_SAMP", +]); + +const ORACLE_SUPPLEMENT: EmitFn[] = [ + ...["+", "-", "*", "/"].map((sql): EmitFn => ({ + sql, + kind: "binop", + overloads: ["number", "binary_float", "binary_double"].map((type) => ({ + args: [{ type }, { type }], returns: type, nullability: "propagates", + })), + })), + { + sql: "-", kind: "unaryop", + overloads: ["number", "binary_float", "binary_double"].map((type) => ({ + args: [{ type }], returns: type, nullability: "propagates", + })), + }, + { + sql: "+", kind: "binop", + overloads: [ + { args: [{ type: "date" }, { type: "number" }], returns: "date", nullability: "propagates" }, + { args: [{ type: "timestamp" }, { type: "intervalds" }], returns: "timestamp", nullability: "propagates" }, + ], + }, + { + sql: "-", kind: "binop", + overloads: [ + { args: [{ type: "date" }, { type: "number" }], returns: "date", nullability: "propagates" }, + { args: [{ type: "date" }, { type: "date" }], returns: "number", nullability: "propagates" }, + { args: [{ type: "timestamp" }, { type: "timestamp" }], returns: "intervalds", nullability: "propagates" }, + { args: [{ type: "timestamp" }, { type: "intervalds" }], returns: "timestamp", nullability: "propagates" }, + ], + }, + ...["LIKE", "NOT LIKE"].map((sql): EmitFn => ({ + sql, + kind: "binop", + overloads: [{ + args: [{ type: "varchar2" }, { type: "varchar2" }], + returns: "bool", + nullability: "propagates", + }], + })), + { + sql: "LNNVL", kind: "scalar", + overloads: [{ args: [{ type: "bool" }], returns: "bool", nullability: "never" }], + }, + { + sql: "WIDTH_BUCKET", kind: "scalar", + overloads: [{ + args: ["number", "number", "number", "number"].map((type) => ({ type })), + returns: "number", + nullability: "propagates", + }], + }, + { + sql: "NVL2", kind: "scalar", + overloads: ["number", "varchar2", "bool"].map((type) => ({ + args: [{ type: "any" }, { type }, { type }], + returns: type, + nullability: "propagates" as const, + nullPositions: [1, 2], + })), + }, + ...["GREATEST", "LEAST"].map((sql): EmitFn => ({ + sql, + kind: "scalar", + overloads: [ + "number", "binary_float", "binary_double", "varchar2", "date", "timestamp", + "timestamptz", "timestampltz", "intervalym", "intervalds", + ].map((type) => ({ + args: [{ type }], + variadic: true, + returns: type, + nullability: "propagates" as const, + })), + })), + { + sql: "NULLIF", kind: "scalar", + overloads: ["number", "varchar2", "date", "bool"].map((type) => ({ + args: [{ type }, { type }], + returns: type, + nullability: "always" as const, + })), + }, + { + sql: "LISTAGG", kind: "aggregate", + overloads: [{ + args: [{ type: "any" }, { type: "varchar2", optional: true }], + returns: "varchar2", + nullability: "always", + }], + }, + ...["CORR", "COVAR_POP", "COVAR_SAMP"].map((sql): EmitFn => ({ + sql, + kind: "aggregate", + overloads: [{ + args: [{ type: "number" }, { type: "number" }], + returns: "number", + nullability: "always", + }], + })), + ...["STDDEV_POP", "STDDEV_SAMP", "VAR_POP", "VAR_SAMP"].map((sql): EmitFn => ({ + sql, + kind: "aggregate", + overloads: [{ args: [{ type: "number" }], returns: "number", nullability: "always" }], + })), + { + sql: "TO_CHAR", kind: "scalar", + overloads: [ + "number", "binary_float", "binary_double", "date", "timestamp", "timestamptz", + "timestampltz", "time", "timetz", "intervalym", "intervalds", + ].map((type) => ({ args: [{ type }], returns: "varchar2", nullability: "propagates" as const })), + }, + { + sql: "TO_NCHAR", kind: "scalar", + overloads: ["number", "binary_float", "binary_double", "date"].map((type) => ({ + args: [{ type }], returns: "nvarchar2", nullability: "propagates" as const, + })), + }, + ...["TO_BINARY_DOUBLE", "TO_BINARY_FLOAT"].map((sql): EmitFn => ({ + sql, + kind: "scalar", + overloads: [{ + args: [{ type: "varchar2" }], + returns: sql === "TO_BINARY_DOUBLE" ? "binary_double" : "binary_float", + nullability: "propagates", + }], + })), +]; +const OVERRIDE_NAMES = scanOverrideNames(OVERRIDES_DIR); + +const chromeFor = (typname: OracleTypname): ClassChrome => { + const lines = ["// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit."]; + const parentImport = typname === "any" + ? 'import { SqlValue } from "../../sql-value";' + : 'import { Any } from "../overrides/any";'; + lines.push(...chromeImportLines(parentImport)); + const cls = CONFIG.typeTable.get(typname)!.className; + lines.push(`export class ${cls} extends ${typname === "any" ? "SqlValue" : "Any"} {`); + if (typname !== "any") { + lines.push(` declare readonly __view: "${typname}";`); + lines.push(...metaDeclareLines(`types.${cls}`)); + lines.push(...typnameStaticLines(ORACLE_CAST_TARGET[typname], typname, true)); + if (!OVERRIDE_NAMES.has(typname)) { + lines.push(" declare deserialize: (raw: string) => string;"); + } + lines.push(""); + } + return { prologue: lines.join("\n"), epilogue: "}\n" }; +}; + +export const generate = async (): Promise => { + // Catalog NUMBER columns (positions, ids) must stay strings to match + // the introspector row declarations and avoid precision loss. + oracledb.fetchAsString = [oracledb.NUMBER]; + const pool = await oracledb.createPool(requireOraclePoolAttributes()); + try { + const conn = await pool.getConnection(); + try { + const catalogFacts = (await introspect(conn)) + .filter((fact) => !ORACLE_REPLACED_FUNCTIONS.has(fact.sql)) + .map((fact) => fact.sql === "REGEXP_SUBSTR" + ? { + ...fact, + overloads: fact.overloads.map((overload) => ({ + ...overload, + nullability: "always" as const, + })), + } + : fact); + writeGeneratedTree({ + generatedDir: GENERATED_DIR, + barrelPath: TYPES_INDEX, + types: TYPES, + facts: [...catalogFacts, ...ORACLE_SUPPLEMENT], + cfg: CONFIG, + chromeFor: (t) => chromeFor(t.typname as OracleTypname), + overrides: OVERRIDE_NAMES, + }); + console.log(`Generated ${TYPES.length} Oracle types in ${GENERATED_DIR}`); + } finally { + await conn.close(); + } + } finally { + await pool.close(0); + } +}; + +if (process.argv[1] && import.meta.url === pathToFileURL(process.argv[1]).href) { + generate().catch((err) => { + console.error(err); + process.exit(1); + }); +} diff --git a/src/types/oracle/generated/any.ts b/src/types/oracle/generated/any.ts new file mode 100644 index 00000000..358c00ce --- /dev/null +++ b/src/types/oracle/generated/any.ts @@ -0,0 +1,54 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { SqlValue } from "../../sql-value"; +import * as types from "../index"; + +export class Any extends SqlValue { + @expose.unchecked() + anyValue>(this: T): T extends { [meta]: { __nullable: infer U } } ? U : types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], runtime.pgType(this)]]); return runtime.funcCall("ANY_VALUE", [this, ...__rest], __rt) as any; } + @expose.unchecked() + approxCountDistinct(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("APPROX_COUNT_DISTINCT", [this, ...__rest], __rt) as any; } + @expose.unchecked() + count(): types.Number<1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("COUNT", [this, ...__rest], __rt) as any; } + @expose.unchecked() + max>(this: T): T extends { [meta]: { __nullable: infer U } } ? U : types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], runtime.pgType(this)]]); return runtime.funcCall("MAX", [this, ...__rest], __rt) as any; } + @expose.unchecked() + min>(this: T): T extends { [meta]: { __nullable: infer U } } ? U : types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], runtime.pgType(this)]]); return runtime.funcCall("MIN", [this, ...__rest], __rt) as any; } + oraHash | number, M1 extends types.Number | number>(arg0?: M0, arg1?: M1): types.Number | runtime.NullOf>>; + @expose.unchecked() + oraHash(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[], types.Number], [[{ type: types.Number, allowPrimitive: true }], types.Number], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("ORA_HASH", [this, ...__rest], __rt) as any; } + @expose.unchecked() + standardHash | string>(arg0: M0): types.Raw<1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Raw]]); return runtime.funcCall("STANDARD_HASH", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ['!='] | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`!=`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['<'] | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`<`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + lt | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`<`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['<='] | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`<=`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + lte | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`<=`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['='] | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`=`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + eq | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`=`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['>'] | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`>`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + gt | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`>`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['>='] | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`>=`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + gte | number | string | boolean | Uint8Array>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`>=`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + nvl2 | number, M1 extends types.Number | number>(arg0: M0, arg1: M1): types.Number | runtime.NullOf>>; + nvl2 | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + nvl2 | boolean, M1 extends types.Bool | boolean>(arg0: M0, arg1: M1): types.Bool | runtime.NullOf>>; + @expose.unchecked() + nvl2(arg0: unknown, arg1: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Bool, allowPrimitive: true }, { type: types.Bool, allowPrimitive: true }], types.Bool]]); return runtime.funcCall("NVL2", [this, ...__rest], __rt) as any; } + listagg | string>(arg0?: M0): types.Varchar2<0 | 1>; + @expose.unchecked() + listagg(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("LISTAGG", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/binary_double.ts b/src/types/oracle/generated/binary_double.ts new file mode 100644 index 00000000..d5ce4ed7 --- /dev/null +++ b/src/types/oracle/generated/binary_double.ts @@ -0,0 +1,106 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class BinaryDouble extends Any { + declare readonly __view: "binary_double"; + declare [meta]: { + __class: typeof types.BinaryDouble; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.BinaryDouble<0 | 1>; + __nonNullable: types.BinaryDouble<1>; + __aggregate: types.BinaryDouble; + __any: types.BinaryDouble; + }; + static override __typname = runtime.sql`BINARY_DOUBLE`; + static override __typnameText = "binary_double"; + + @expose.unchecked() + abs(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("ABS", [this, ...__rest], __rt) as any; } + @expose.unchecked() + acos(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("ACOS", [this, ...__rest], __rt) as any; } + @expose.unchecked() + asin(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("ASIN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + atan(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("ATAN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + atan2 | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.funcCall("ATAN2", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ceil(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("CEIL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + cos(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("COS", [this, ...__rest], __rt) as any; } + @expose.unchecked() + cosh(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("COSH", [this, ...__rest], __rt) as any; } + @expose.unchecked() + exp(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("EXP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + floor(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("FLOOR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ln(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("LN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + log | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.funcCall("LOG", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nanvl | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.funcCall("NANVL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nvl | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + power | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.funcCall("POWER", [this, ...__rest], __rt) as any; } + @expose.unchecked() + remainder | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.funcCall("REMAINDER", [this, ...__rest], __rt) as any; } + @expose.unchecked() + round(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("ROUND", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sign(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("SIGN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sin(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("SIN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sinh(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("SINH", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sqrt(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("SQRT", [this, ...__rest], __rt) as any; } + @expose.unchecked() + tan(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("TAN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + tanh(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("TANH", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toBinaryDouble(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("TO_BINARY_DOUBLE", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toBoolean(): types.Bool { const [__rt, ...__rest] = runtime.match([], [[[], types.Bool]]); return runtime.funcCall("TO_BOOLEAN", [this, ...__rest], __rt) as any; } + toChar | string>(arg0: M0): types.Varchar2>>; + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + toNchar | string>(arg0: M0): types.Nvarchar2>>; + toNchar | string, M1 extends types.Nvarchar2 | string>(arg0: M0, arg1: M1): types.Nvarchar2 | runtime.NullOf>>; + toNchar(): types.Nvarchar2; + @expose.unchecked() + toNchar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Nvarchar2, allowPrimitive: true }], types.Nvarchar2], [[{ type: types.Nvarchar2, allowPrimitive: true }, { type: types.Nvarchar2, allowPrimitive: true }], types.Nvarchar2], [[], types.Nvarchar2]]); return runtime.funcCall("TO_NCHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + trunc(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.funcCall("TRUNC", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ['+'] | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + plus | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['-'] | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + minus | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['*'] | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.opCall(runtime.sql`*`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + times | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.opCall(runtime.sql`*`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['/'] | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.opCall(runtime.sql`/`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + divide | number>(arg0: M0): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryDouble, allowPrimitive: true }], types.BinaryDouble]]); return runtime.opCall(runtime.sql`/`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + negate(): types.BinaryDouble { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryDouble]]); return runtime.unaryOpCall(runtime.sql`-`, this, __rt) as any; } + @expose.unchecked() + greatest | number)[]>(...rest: R): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.BinaryDouble, allowPrimitive: true, rest: true }], types.BinaryDouble]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | number)[]>(...rest: R): types.BinaryDouble>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.BinaryDouble, allowPrimitive: true, rest: true }], types.BinaryDouble]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/binary_float.ts b/src/types/oracle/generated/binary_float.ts new file mode 100644 index 00000000..29564919 --- /dev/null +++ b/src/types/oracle/generated/binary_float.ts @@ -0,0 +1,78 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class BinaryFloat extends Any { + declare readonly __view: "binary_float"; + declare [meta]: { + __class: typeof types.BinaryFloat; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.BinaryFloat<0 | 1>; + __nonNullable: types.BinaryFloat<1>; + __aggregate: types.BinaryFloat; + __any: types.BinaryFloat; + }; + static override __typname = runtime.sql`BINARY_FLOAT`; + static override __typnameText = "binary_float"; + + @expose.unchecked() + abs(): types.BinaryFloat { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryFloat]]); return runtime.funcCall("ABS", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ceil(): types.BinaryFloat { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryFloat]]); return runtime.funcCall("CEIL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + floor(): types.BinaryFloat { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryFloat]]); return runtime.funcCall("FLOOR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nanvl | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.funcCall("NANVL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nvl | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + remainder | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.funcCall("REMAINDER", [this, ...__rest], __rt) as any; } + @expose.unchecked() + round(): types.BinaryFloat { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryFloat]]); return runtime.funcCall("ROUND", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sign(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("SIGN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sqrt(): types.BinaryFloat { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryFloat]]); return runtime.funcCall("SQRT", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toBinaryFloat(): types.BinaryFloat { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryFloat]]); return runtime.funcCall("TO_BINARY_FLOAT", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toBoolean(): types.Bool { const [__rt, ...__rest] = runtime.match([], [[[], types.Bool]]); return runtime.funcCall("TO_BOOLEAN", [this, ...__rest], __rt) as any; } + toChar | string>(arg0: M0): types.Varchar2>>; + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + toNchar | string>(arg0: M0): types.Nvarchar2>>; + toNchar | string, M1 extends types.Nvarchar2 | string>(arg0: M0, arg1: M1): types.Nvarchar2 | runtime.NullOf>>; + toNchar(): types.Nvarchar2; + @expose.unchecked() + toNchar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Nvarchar2, allowPrimitive: true }], types.Nvarchar2], [[{ type: types.Nvarchar2, allowPrimitive: true }, { type: types.Nvarchar2, allowPrimitive: true }], types.Nvarchar2], [[], types.Nvarchar2]]); return runtime.funcCall("TO_NCHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + trunc(): types.BinaryFloat { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryFloat]]); return runtime.funcCall("TRUNC", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ['+'] | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + plus | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['-'] | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + minus | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['*'] | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.opCall(runtime.sql`*`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + times | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.opCall(runtime.sql`*`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['/'] | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.opCall(runtime.sql`/`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + divide | number>(arg0: M0): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.BinaryFloat, allowPrimitive: true }], types.BinaryFloat]]); return runtime.opCall(runtime.sql`/`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + negate(): types.BinaryFloat { const [__rt, ...__rest] = runtime.match([], [[[], types.BinaryFloat]]); return runtime.unaryOpCall(runtime.sql`-`, this, __rt) as any; } + @expose.unchecked() + greatest | number)[]>(...rest: R): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.BinaryFloat, allowPrimitive: true, rest: true }], types.BinaryFloat]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | number)[]>(...rest: R): types.BinaryFloat>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.BinaryFloat, allowPrimitive: true, rest: true }], types.BinaryFloat]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/blob.ts b/src/types/oracle/generated/blob.ts new file mode 100644 index 00000000..ea8d2987 --- /dev/null +++ b/src/types/oracle/generated/blob.ts @@ -0,0 +1,22 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Blob extends Any { + declare readonly __view: "blob"; + declare [meta]: { + __class: typeof types.Blob; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Blob<0 | 1>; + __nonNullable: types.Blob<1>; + __aggregate: types.Blob; + __any: types.Blob; + }; + static override __typname = runtime.sql`BLOB`; + static override __typnameText = "blob"; + +} diff --git a/src/types/oracle/generated/bool.ts b/src/types/oracle/generated/bool.ts new file mode 100644 index 00000000..d12e9283 --- /dev/null +++ b/src/types/oracle/generated/bool.ts @@ -0,0 +1,30 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Bool extends Any { + declare readonly __view: "bool"; + declare [meta]: { + __class: typeof types.Bool; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Bool<0 | 1>; + __nonNullable: types.Bool<1>; + __aggregate: types.Bool; + __any: types.Bool; + }; + static override __typname = runtime.sql`BOOLEAN`; + static override __typnameText = "bool"; + + @expose.unchecked() + nvl | boolean>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Bool, allowPrimitive: true }], types.Bool]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toBoolean(): types.Bool { const [__rt, ...__rest] = runtime.match([], [[[], types.Bool]]); return runtime.funcCall("TO_BOOLEAN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + lnnvl(): types.Bool<1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Bool]]); return runtime.funcCall("LNNVL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nullif | boolean>(arg0: M0): types.Bool<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Bool, allowPrimitive: true }], types.Bool]]); return runtime.funcCall("NULLIF", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/char.ts b/src/types/oracle/generated/char.ts new file mode 100644 index 00000000..8320f81c --- /dev/null +++ b/src/types/oracle/generated/char.ts @@ -0,0 +1,23 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Char extends Any { + declare readonly __view: "char"; + declare [meta]: { + __class: typeof types.Char; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Char<0 | 1>; + __nonNullable: types.Char<1>; + __aggregate: types.Char; + __any: types.Char; + }; + static override __typname = runtime.sql`CHAR(2000)`; + static override __typnameText = "char"; + declare deserialize: (raw: string) => string; + +} diff --git a/src/types/oracle/generated/clob.ts b/src/types/oracle/generated/clob.ts new file mode 100644 index 00000000..220295ee --- /dev/null +++ b/src/types/oracle/generated/clob.ts @@ -0,0 +1,23 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Clob extends Any { + declare readonly __view: "clob"; + declare [meta]: { + __class: typeof types.Clob; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Clob<0 | 1>; + __nonNullable: types.Clob<1>; + __aggregate: types.Clob; + __any: types.Clob; + }; + static override __typname = runtime.sql`CLOB`; + static override __typnameText = "clob"; + declare deserialize: (raw: string) => string; + +} diff --git a/src/types/oracle/generated/date.ts b/src/types/oracle/generated/date.ts new file mode 100644 index 00000000..451b1a24 --- /dev/null +++ b/src/types/oracle/generated/date.ts @@ -0,0 +1,87 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Date extends Any { + declare readonly __view: "date"; + declare [meta]: { + __class: typeof types.Date; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Date<0 | 1>; + __nonNullable: types.Date<1>; + __aggregate: types.Date; + __any: types.Date; + }; + static override __typname = runtime.sql`DATE`; + static override __typnameText = "date"; + declare deserialize: (raw: string) => string; + + @expose.unchecked() + addMonths | number>(arg0: M0): types.Date>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Date]]); return runtime.funcCall("ADD_MONTHS", [this, ...__rest], __rt) as any; } + ceil | string>(arg0?: M0): types.Date>>; + @expose.unchecked() + ceil(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Date], [[{ type: types.Varchar2, allowPrimitive: true }], types.Date]]); return runtime.funcCall("CEIL", [this, ...__rest], __rt) as any; } + dump | number, M1 extends types.Number | number, M2 extends types.Number | number>(arg0?: M0, arg1?: M1, arg2?: M2): types.Varchar2<1>; + @expose.unchecked() + dump(arg0?: unknown, arg1?: unknown, arg2?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2], [[[], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("DUMP", [this, ...__rest], __rt) as any; } + floor(): types.Date; + floor | string>(arg0: M0): types.Date>>; + @expose.unchecked() + floor(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Date], [[{ type: types.Varchar2, allowPrimitive: true }], types.Date]]); return runtime.funcCall("FLOOR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + lastDay(): types.Date { const [__rt, ...__rest] = runtime.match([], [[[], types.Date]]); return runtime.funcCall("LAST_DAY", [this, ...__rest], __rt) as any; } + @expose.unchecked() + monthsBetween | string>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Date, allowPrimitive: true }], types.Number]]); return runtime.funcCall("MONTHS_BETWEEN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + newTime | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Date | runtime.NullOf>> { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Date]]); return runtime.funcCall("NEW_TIME", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nextDay | string>(arg0: M0): types.Date>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Date]]); return runtime.funcCall("NEXT_DAY", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nvl | string>(arg0: M0): types.Date>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Date, allowPrimitive: true }], types.Date]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + round(): types.Date; + round | string>(arg0: M0): types.Date>>; + @expose.unchecked() + round(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Date], [[{ type: types.Varchar2, allowPrimitive: true }], types.Date]]); return runtime.funcCall("ROUND", [this, ...__rest], __rt) as any; } + toChar | string>(arg0: M0): types.Varchar2>>; + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + toNchar | string>(arg0: M0): types.Nvarchar2>>; + toNchar | string, M1 extends types.Nvarchar2 | string>(arg0: M0, arg1: M1): types.Nvarchar2 | runtime.NullOf>>; + toNchar(): types.Nvarchar2; + @expose.unchecked() + toNchar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Nvarchar2, allowPrimitive: true }], types.Nvarchar2], [[{ type: types.Nvarchar2, allowPrimitive: true }, { type: types.Nvarchar2, allowPrimitive: true }], types.Nvarchar2], [[], types.Nvarchar2]]); return runtime.funcCall("TO_NCHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toTimestamp(): types.Timestamp { const [__rt, ...__rest] = runtime.match([], [[[], types.Timestamp]]); return runtime.funcCall("TO_TIMESTAMP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toTimestampTz(): types.Timestamptz { const [__rt, ...__rest] = runtime.match([], [[[], types.Timestamptz]]); return runtime.funcCall("TO_TIMESTAMP_TZ", [this, ...__rest], __rt) as any; } + trunc(): types.Date; + trunc | string>(arg0: M0): types.Date>>; + @expose.unchecked() + trunc(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Date], [[{ type: types.Varchar2, allowPrimitive: true }], types.Date]]); return runtime.funcCall("TRUNC", [this, ...__rest], __rt) as any; } + @expose.unchecked() + vsize(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("VSIZE", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ['+'] | number>(arg0: M0): types.Date>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Date]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + plus | number>(arg0: M0): types.Date>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Date]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + ['-'] | number>(arg0: M0): types.Date>>; + ['-'] | string>(arg0: M0): types.Number>>; + @expose.unchecked() + ['-'](arg0: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Date], [[{ type: types.Date, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + minus | number>(arg0: M0): types.Date>>; + minus | string>(arg0: M0): types.Number>>; + @expose.unchecked() + minus(arg0: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Date], [[{ type: types.Date, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + greatest | string)[]>(...rest: R): types.Date>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Date, allowPrimitive: true, rest: true }], types.Date]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | string)[]>(...rest: R): types.Date>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Date, allowPrimitive: true, rest: true }], types.Date]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nullif | string>(arg0: M0): types.Date<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Date, allowPrimitive: true }], types.Date]]); return runtime.funcCall("NULLIF", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/intervalds.ts b/src/types/oracle/generated/intervalds.ts new file mode 100644 index 00000000..e197dfaf --- /dev/null +++ b/src/types/oracle/generated/intervalds.ts @@ -0,0 +1,46 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class IntervalDs extends Any { + declare readonly __view: "intervalds"; + declare [meta]: { + __class: typeof types.IntervalDs; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.IntervalDs<0 | 1>; + __nonNullable: types.IntervalDs<1>; + __aggregate: types.IntervalDs; + __any: types.IntervalDs; + }; + static override __typname = runtime.sql`INTERVAL DAY TO SECOND`; + static override __typnameText = "intervalds"; + declare deserialize: (raw: string) => string; + + ceil | string>(arg0?: M0): types.IntervalDs>>; + @expose.unchecked() + ceil(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalDs], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalDs]]); return runtime.funcCall("CEIL", [this, ...__rest], __rt) as any; } + floor | string>(arg0?: M0): types.IntervalDs>>; + @expose.unchecked() + floor(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalDs], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalDs]]); return runtime.funcCall("FLOOR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nvl | string>(arg0: M0): types.IntervalDs>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.IntervalDs, allowPrimitive: true }], types.IntervalDs]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + round | string>(arg0?: M0): types.IntervalDs>>; + @expose.unchecked() + round(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalDs], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalDs]]); return runtime.funcCall("ROUND", [this, ...__rest], __rt) as any; } + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar | string>(arg0: M0): types.Varchar2>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + trunc | string>(arg0?: M0): types.IntervalDs>>; + @expose.unchecked() + trunc(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalDs], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalDs]]); return runtime.funcCall("TRUNC", [this, ...__rest], __rt) as any; } + @expose.unchecked() + greatest | string)[]>(...rest: R): types.IntervalDs>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.IntervalDs, allowPrimitive: true, rest: true }], types.IntervalDs]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | string)[]>(...rest: R): types.IntervalDs>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.IntervalDs, allowPrimitive: true, rest: true }], types.IntervalDs]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/intervalym.ts b/src/types/oracle/generated/intervalym.ts new file mode 100644 index 00000000..4a5f890c --- /dev/null +++ b/src/types/oracle/generated/intervalym.ts @@ -0,0 +1,46 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class IntervalYm extends Any { + declare readonly __view: "intervalym"; + declare [meta]: { + __class: typeof types.IntervalYm; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.IntervalYm<0 | 1>; + __nonNullable: types.IntervalYm<1>; + __aggregate: types.IntervalYm; + __any: types.IntervalYm; + }; + static override __typname = runtime.sql`INTERVAL YEAR TO MONTH`; + static override __typnameText = "intervalym"; + declare deserialize: (raw: string) => string; + + ceil | string>(arg0?: M0): types.IntervalYm>>; + @expose.unchecked() + ceil(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalYm], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalYm]]); return runtime.funcCall("CEIL", [this, ...__rest], __rt) as any; } + floor | string>(arg0?: M0): types.IntervalYm>>; + @expose.unchecked() + floor(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalYm], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalYm]]); return runtime.funcCall("FLOOR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nvl | string>(arg0: M0): types.IntervalYm>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.IntervalYm, allowPrimitive: true }], types.IntervalYm]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + round | string>(arg0?: M0): types.IntervalYm>>; + @expose.unchecked() + round(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalYm], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalYm]]); return runtime.funcCall("ROUND", [this, ...__rest], __rt) as any; } + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar | string>(arg0: M0): types.Varchar2>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + trunc | string>(arg0?: M0): types.IntervalYm>>; + @expose.unchecked() + trunc(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalYm], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalYm]]); return runtime.funcCall("TRUNC", [this, ...__rest], __rt) as any; } + @expose.unchecked() + greatest | string)[]>(...rest: R): types.IntervalYm>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.IntervalYm, allowPrimitive: true, rest: true }], types.IntervalYm]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | string)[]>(...rest: R): types.IntervalYm>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.IntervalYm, allowPrimitive: true, rest: true }], types.IntervalYm]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/json.ts b/src/types/oracle/generated/json.ts new file mode 100644 index 00000000..82de142b --- /dev/null +++ b/src/types/oracle/generated/json.ts @@ -0,0 +1,27 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Json extends Any { + declare readonly __view: "json"; + declare [meta]: { + __class: typeof types.Json; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Json<0 | 1>; + __nonNullable: types.Json<1>; + __aggregate: types.Json; + __any: types.Json; + }; + static override __typname = runtime.sql`JSON`; + static override __typnameText = "json"; + declare deserialize: (raw: string) => string; + + @expose.unchecked() + jsonEqual | string>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Json, allowPrimitive: true }], types.Bool]]); return runtime.funcCall("JSON_EQUAL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + length(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("LENGTH", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/nclob.ts b/src/types/oracle/generated/nclob.ts new file mode 100644 index 00000000..3831a621 --- /dev/null +++ b/src/types/oracle/generated/nclob.ts @@ -0,0 +1,23 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Nclob extends Any { + declare readonly __view: "nclob"; + declare [meta]: { + __class: typeof types.Nclob; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Nclob<0 | 1>; + __nonNullable: types.Nclob<1>; + __aggregate: types.Nclob; + __any: types.Nclob; + }; + static override __typname = runtime.sql`NCLOB`; + static override __typnameText = "nclob"; + declare deserialize: (raw: string) => string; + +} diff --git a/src/types/oracle/generated/number.ts b/src/types/oracle/generated/number.ts new file mode 100644 index 00000000..bf4dc57b --- /dev/null +++ b/src/types/oracle/generated/number.ts @@ -0,0 +1,155 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Number extends Any { + declare readonly __view: "number"; + declare [meta]: { + __class: typeof types.Number; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Number<0 | 1>; + __nonNullable: types.Number<1>; + __aggregate: types.Number; + __any: types.Number; + }; + static override __typname = runtime.sql`NUMBER`; + static override __typnameText = "number"; + + @expose.unchecked() + avg(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("AVG", [this, ...__rest], __rt) as any; } + @expose.unchecked() + median(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("MEDIAN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + mod | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("MOD", [this, ...__rest], __rt) as any; } + @expose.unchecked() + stddev(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("STDDEV", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sum(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("SUM", [this, ...__rest], __rt) as any; } + @expose.unchecked() + variance(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("VARIANCE", [this, ...__rest], __rt) as any; } + @expose.unchecked() + abs(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("ABS", [this, ...__rest], __rt) as any; } + @expose.unchecked() + acos(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("ACOS", [this, ...__rest], __rt) as any; } + @expose.unchecked() + asin(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("ASIN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + atan(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("ATAN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + atan2 | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("ATAN2", [this, ...__rest], __rt) as any; } + @expose.unchecked() + bitand | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("BITAND", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ceil(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("CEIL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + chr(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("CHR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + cos(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("COS", [this, ...__rest], __rt) as any; } + @expose.unchecked() + cosh(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("COSH", [this, ...__rest], __rt) as any; } + dump | number, M1 extends types.Number | number, M2 extends types.Number | number>(arg0?: M0, arg1?: M1, arg2?: M2): types.Varchar2<1>; + @expose.unchecked() + dump(arg0?: unknown, arg1?: unknown, arg2?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2], [[[], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("DUMP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + exp(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("EXP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + floor(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("FLOOR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ln(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("LN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + log | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("LOG", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nanvl | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("NANVL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nchr(): types.Nvarchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Nvarchar2]]); return runtime.funcCall("NCHR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + numtodsinterval | string>(arg0: M0): types.IntervalDs>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalDs]]); return runtime.funcCall("NUMTODSINTERVAL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + numtoyminterval | string>(arg0: M0): types.IntervalYm>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalYm]]); return runtime.funcCall("NUMTOYMINTERVAL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nvl | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + power | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("POWER", [this, ...__rest], __rt) as any; } + @expose.unchecked() + remainder | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("REMAINDER", [this, ...__rest], __rt) as any; } + round | number>(arg0?: M0): types.Number>>; + @expose.unchecked() + round(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Number], [[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("ROUND", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sign(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("SIGN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sin(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("SIN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sinh(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("SINH", [this, ...__rest], __rt) as any; } + @expose.unchecked() + sqrt(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("SQRT", [this, ...__rest], __rt) as any; } + @expose.unchecked() + tan(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("TAN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + tanh(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("TANH", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toBoolean(): types.Bool { const [__rt, ...__rest] = runtime.match([], [[[], types.Bool]]); return runtime.funcCall("TO_BOOLEAN", [this, ...__rest], __rt) as any; } + toChar | string>(arg0: M0): types.Varchar2>>; + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toDate | string>(arg0: M0): types.Date>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Date]]); return runtime.funcCall("TO_DATE", [this, ...__rest], __rt) as any; } + toNchar | string>(arg0: M0): types.Nvarchar2>>; + toNchar | string, M1 extends types.Nvarchar2 | string>(arg0: M0, arg1: M1): types.Nvarchar2 | runtime.NullOf>>; + toNchar(): types.Nvarchar2; + @expose.unchecked() + toNchar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Nvarchar2, allowPrimitive: true }], types.Nvarchar2], [[{ type: types.Nvarchar2, allowPrimitive: true }, { type: types.Nvarchar2, allowPrimitive: true }], types.Nvarchar2], [[], types.Nvarchar2]]); return runtime.funcCall("TO_NCHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toNumber(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("TO_NUMBER", [this, ...__rest], __rt) as any; } + trunc | number>(arg0?: M0): types.Number>>; + @expose.unchecked() + trunc(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Number], [[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("TRUNC", [this, ...__rest], __rt) as any; } + @expose.unchecked() + vsize(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("VSIZE", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ['+'] | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + plus | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['-'] | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + minus | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['*'] | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`*`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + times | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`*`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['/'] | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`/`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + divide | number>(arg0: M0): types.Number>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.opCall(runtime.sql`/`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + negate(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.unaryOpCall(runtime.sql`-`, this, __rt) as any; } + @expose.unchecked() + widthBucket | number, M1 extends types.Number | number, M2 extends types.Number | number>(arg0: M0, arg1: M1, arg2: M2): types.Number | runtime.NullOf | runtime.NullOf>> { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2], [[[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("WIDTH_BUCKET", [this, ...__rest], __rt) as any; } + @expose.unchecked() + greatest | number)[]>(...rest: R): types.Number>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Number, allowPrimitive: true, rest: true }], types.Number]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | number)[]>(...rest: R): types.Number>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Number, allowPrimitive: true, rest: true }], types.Number]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nullif | number>(arg0: M0): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("NULLIF", [this, ...__rest], __rt) as any; } + @expose.unchecked() + corr | number>(arg0: M0): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("CORR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + covarPop | number>(arg0: M0): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("COVAR_POP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + covarSamp | number>(arg0: M0): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("COVAR_SAMP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + stddevPop(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("STDDEV_POP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + stddevSamp(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("STDDEV_SAMP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + varPop(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("VAR_POP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + varSamp(): types.Number<0 | 1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("VAR_SAMP", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/nvarchar2.ts b/src/types/oracle/generated/nvarchar2.ts new file mode 100644 index 00000000..27d970c1 --- /dev/null +++ b/src/types/oracle/generated/nvarchar2.ts @@ -0,0 +1,25 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Nvarchar2 extends Any { + declare readonly __view: "nvarchar2"; + declare [meta]: { + __class: typeof types.Nvarchar2; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Nvarchar2<0 | 1>; + __nonNullable: types.Nvarchar2<1>; + __aggregate: types.Nvarchar2; + __any: types.Nvarchar2; + }; + static override __typname = runtime.sql`NVARCHAR2(2000)`; + static override __typnameText = "nvarchar2"; + declare deserialize: (raw: string) => string; + + @expose.unchecked() + toNchar(): types.Nvarchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Nvarchar2]]); return runtime.funcCall("TO_NCHAR", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/raw.ts b/src/types/oracle/generated/raw.ts new file mode 100644 index 00000000..8ce5faa0 --- /dev/null +++ b/src/types/oracle/generated/raw.ts @@ -0,0 +1,26 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Raw extends Any { + declare readonly __view: "raw"; + declare [meta]: { + __class: typeof types.Raw; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Raw<0 | 1>; + __nonNullable: types.Raw<1>; + __aggregate: types.Raw; + __any: types.Raw; + }; + static override __typname = runtime.sql`RAW(2000)`; + static override __typnameText = "raw"; + + @expose.unchecked() + rawtohex(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("RAWTOHEX", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toBlob(): types.Blob { const [__rt, ...__rest] = runtime.match([], [[[], types.Blob]]); return runtime.funcCall("TO_BLOB", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/rowid.ts b/src/types/oracle/generated/rowid.ts new file mode 100644 index 00000000..d5d4f9c2 --- /dev/null +++ b/src/types/oracle/generated/rowid.ts @@ -0,0 +1,23 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Rowid extends Any { + declare readonly __view: "rowid"; + declare [meta]: { + __class: typeof types.Rowid; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Rowid<0 | 1>; + __nonNullable: types.Rowid<1>; + __aggregate: types.Rowid; + __any: types.Rowid; + }; + static override __typname = runtime.sql`ROWID`; + static override __typnameText = "rowid"; + declare deserialize: (raw: string) => string; + +} diff --git a/src/types/oracle/generated/time.ts b/src/types/oracle/generated/time.ts new file mode 100644 index 00000000..0094c7d0 --- /dev/null +++ b/src/types/oracle/generated/time.ts @@ -0,0 +1,28 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Time extends Any { + declare readonly __view: "time"; + declare [meta]: { + __class: typeof types.Time; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Time<0 | 1>; + __nonNullable: types.Time<1>; + __aggregate: types.Time; + __any: types.Time; + }; + static override __typname = runtime.sql`TIME`; + static override __typnameText = "time"; + declare deserialize: (raw: string) => string; + + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar | string>(arg0: M0): types.Varchar2>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/timestamp.ts b/src/types/oracle/generated/timestamp.ts new file mode 100644 index 00000000..f0469204 --- /dev/null +++ b/src/types/oracle/generated/timestamp.ts @@ -0,0 +1,50 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Timestamp extends Any { + declare readonly __view: "timestamp"; + declare [meta]: { + __class: typeof types.Timestamp; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Timestamp<0 | 1>; + __nonNullable: types.Timestamp<1>; + __aggregate: types.Timestamp; + __any: types.Timestamp; + }; + static override __typname = runtime.sql`TIMESTAMP`; + static override __typnameText = "timestamp"; + declare deserialize: (raw: string) => string; + + @expose.unchecked() + fromTz | string>(arg0: M0): types.Timestamptz>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Timestamptz]]); return runtime.funcCall("FROM_TZ", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nvl | string>(arg0: M0): types.Timestamp>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Timestamp, allowPrimitive: true }], types.Timestamp]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar | string>(arg0: M0): types.Varchar2>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toTimestampTz(): types.Timestamptz { const [__rt, ...__rest] = runtime.match([], [[[], types.Timestamptz]]); return runtime.funcCall("TO_TIMESTAMP_TZ", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ['+'] | string>(arg0: M0): types.Timestamp>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.IntervalDs, allowPrimitive: true }], types.Timestamp]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + plus | string>(arg0: M0): types.Timestamp>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.IntervalDs, allowPrimitive: true }], types.Timestamp]]); return runtime.opCall(runtime.sql`+`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + ['-'] | string>(arg0: M0): types.IntervalDs>>; + ['-']>(arg0: M0): types.Timestamp>>; + @expose.unchecked() + ['-'](arg0: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Timestamp, allowPrimitive: true }], types.IntervalDs], [[{ type: types.IntervalDs }], types.Timestamp]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + minus | string>(arg0: M0): types.IntervalDs>>; + minus>(arg0: M0): types.Timestamp>>; + @expose.unchecked() + minus(arg0: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Timestamp, allowPrimitive: true }], types.IntervalDs], [[{ type: types.IntervalDs }], types.Timestamp]]); return runtime.opCall(runtime.sql`-`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + greatest | string)[]>(...rest: R): types.Timestamp>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Timestamp, allowPrimitive: true, rest: true }], types.Timestamp]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | string)[]>(...rest: R): types.Timestamp>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Timestamp, allowPrimitive: true, rest: true }], types.Timestamp]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/timestampltz.ts b/src/types/oracle/generated/timestampltz.ts new file mode 100644 index 00000000..91d31b3e --- /dev/null +++ b/src/types/oracle/generated/timestampltz.ts @@ -0,0 +1,38 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Timestampltz extends Any { + declare readonly __view: "timestampltz"; + declare [meta]: { + __class: typeof types.Timestampltz; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Timestampltz<0 | 1>; + __nonNullable: types.Timestampltz<1>; + __aggregate: types.Timestampltz; + __any: types.Timestampltz; + }; + static override __typname = runtime.sql`TIMESTAMP WITH LOCAL TIME ZONE`; + static override __typnameText = "timestampltz"; + declare deserialize: (raw: string) => string; + + @expose.unchecked() + nvl | string>(arg0: M0): types.Timestampltz>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Timestampltz, allowPrimitive: true }], types.Timestampltz]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar | string>(arg0: M0): types.Varchar2>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toTimestamp(): types.Timestamp { const [__rt, ...__rest] = runtime.match([], [[[], types.Timestamp]]); return runtime.funcCall("TO_TIMESTAMP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toTimestampTz(): types.Timestamptz { const [__rt, ...__rest] = runtime.match([], [[[], types.Timestamptz]]); return runtime.funcCall("TO_TIMESTAMP_TZ", [this, ...__rest], __rt) as any; } + @expose.unchecked() + greatest | string)[]>(...rest: R): types.Timestampltz>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Timestampltz, allowPrimitive: true, rest: true }], types.Timestampltz]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | string)[]>(...rest: R): types.Timestampltz>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Timestampltz, allowPrimitive: true, rest: true }], types.Timestampltz]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/timestamptz.ts b/src/types/oracle/generated/timestamptz.ts new file mode 100644 index 00000000..b747514b --- /dev/null +++ b/src/types/oracle/generated/timestamptz.ts @@ -0,0 +1,36 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Timestamptz extends Any { + declare readonly __view: "timestamptz"; + declare [meta]: { + __class: typeof types.Timestamptz; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Timestamptz<0 | 1>; + __nonNullable: types.Timestamptz<1>; + __aggregate: types.Timestamptz; + __any: types.Timestamptz; + }; + static override __typname = runtime.sql`TIMESTAMP WITH TIME ZONE`; + static override __typnameText = "timestamptz"; + declare deserialize: (raw: string) => string; + + @expose.unchecked() + nvl | string>(arg0: M0): types.Timestamptz>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Timestamptz, allowPrimitive: true }], types.Timestamptz]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar | string>(arg0: M0): types.Varchar2>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toTimestamp(): types.Timestamp { const [__rt, ...__rest] = runtime.match([], [[[], types.Timestamp]]); return runtime.funcCall("TO_TIMESTAMP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + greatest | string)[]>(...rest: R): types.Timestamptz>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Timestamptz, allowPrimitive: true, rest: true }], types.Timestamptz]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | string)[]>(...rest: R): types.Timestamptz>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Timestamptz, allowPrimitive: true, rest: true }], types.Timestamptz]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/timetz.ts b/src/types/oracle/generated/timetz.ts new file mode 100644 index 00000000..43bab03e --- /dev/null +++ b/src/types/oracle/generated/timetz.ts @@ -0,0 +1,28 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Timetz extends Any { + declare readonly __view: "timetz"; + declare [meta]: { + __class: typeof types.Timetz; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Timetz<0 | 1>; + __nonNullable: types.Timetz<1>; + __aggregate: types.Timetz; + __any: types.Timetz; + }; + static override __typname = runtime.sql`TIME WITH TIME ZONE`; + static override __typnameText = "timetz"; + declare deserialize: (raw: string) => string; + + toChar | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + toChar | string>(arg0: M0): types.Varchar2>>; + toChar(): types.Varchar2; + @expose.unchecked() + toChar(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/urowid.ts b/src/types/oracle/generated/urowid.ts new file mode 100644 index 00000000..d4884ef3 --- /dev/null +++ b/src/types/oracle/generated/urowid.ts @@ -0,0 +1,23 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Urowid extends Any { + declare readonly __view: "urowid"; + declare [meta]: { + __class: typeof types.Urowid; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Urowid<0 | 1>; + __nonNullable: types.Urowid<1>; + __aggregate: types.Urowid; + __any: types.Urowid; + }; + static override __typname = runtime.sql`UROWID`; + static override __typnameText = "urowid"; + declare deserialize: (raw: string) => string; + +} diff --git a/src/types/oracle/generated/varchar2.ts b/src/types/oracle/generated/varchar2.ts new file mode 100644 index 00000000..de4d1b06 --- /dev/null +++ b/src/types/oracle/generated/varchar2.ts @@ -0,0 +1,164 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Varchar2 extends Any { + declare readonly __view: "varchar2"; + declare [meta]: { + __class: typeof types.Varchar2; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Varchar2<0 | 1>; + __nonNullable: types.Varchar2<1>; + __aggregate: types.Varchar2; + __any: types.Varchar2; + }; + static override __typname = runtime.sql`VARCHAR2(4000)`; + static override __typnameText = "varchar2"; + declare deserialize: (raw: string) => string; + + @expose.unchecked() + ascii(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("ASCII", [this, ...__rest], __rt) as any; } + @expose.unchecked() + concat | string>(arg0: M0): types.Varchar2>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("CONCAT", [this, ...__rest], __rt) as any; } + convert | string>(arg0: M0): types.Varchar2>>; + convert | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + @expose.unchecked() + convert(arg0: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("CONVERT", [this, ...__rest], __rt) as any; } + dump | number, M1 extends types.Number | number, M2 extends types.Number | number>(arg0?: M0, arg1?: M1, arg2?: M2): types.Varchar2<1>; + @expose.unchecked() + dump(arg0?: unknown, arg1?: unknown, arg2?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2], [[[], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("DUMP", [this, ...__rest], __rt) as any; } + @expose.unchecked() + hextoraw(): types.Raw { const [__rt, ...__rest] = runtime.match([], [[[], types.Raw]]); return runtime.funcCall("HEXTORAW", [this, ...__rest], __rt) as any; } + @expose.unchecked() + initcap(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("INITCAP", [this, ...__rest], __rt) as any; } + instr | string, M1 extends types.Number | number, M2 extends types.Number | number>(arg0: M0, arg1?: M1, arg2?: M2): types.Number | runtime.NullOf | runtime.NullOf>>; + @expose.unchecked() + instr(arg0: unknown, arg1?: unknown, arg2?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("INSTR", [this, ...__rest], __rt) as any; } + instrb | string, M1 extends types.Number | number, M2 extends types.Number | number>(arg0: M0, arg1?: M1, arg2?: M2): types.Number | runtime.NullOf | runtime.NullOf>>; + @expose.unchecked() + instrb(arg0: unknown, arg1?: unknown, arg2?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("INSTRB", [this, ...__rest], __rt) as any; } + @expose.unchecked() + length(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("LENGTH", [this, ...__rest], __rt) as any; } + @expose.unchecked() + lengthb(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("LENGTHB", [this, ...__rest], __rt) as any; } + @expose.unchecked() + lower(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("LOWER", [this, ...__rest], __rt) as any; } + lpad | number, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + lpad | number>(arg0: M0): types.Varchar2>>; + @expose.unchecked() + lpad(arg0: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Number, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("LPAD", [this, ...__rest], __rt) as any; } + ltrim | string>(arg0: M0): types.Varchar2>>; + ltrim(): types.Varchar2; + @expose.unchecked() + ltrim(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("LTRIM", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nvl | string>(arg0: M0): types.Varchar2>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("NVL", [this, ...__rest], __rt) as any; } + regexpCount | string, M1 extends types.Number | number, M2 extends types.Varchar2 | string>(arg0: M0, arg1?: M1, arg2?: M2): types.Number | runtime.NullOf | runtime.NullOf>>; + @expose.unchecked() + regexpCount(arg0: unknown, arg1?: unknown, arg2?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Number]]); return runtime.funcCall("REGEXP_COUNT", [this, ...__rest], __rt) as any; } + regexpInstr | string, M1 extends types.Number | number, M2 extends types.Number | number, M3 extends types.Number | number, M4 extends types.Varchar2 | string, M5 extends types.Number | number>(arg0: M0, arg1?: M1, arg2?: M2, arg3?: M3, arg4?: M4, arg5?: M5): types.Number | runtime.NullOf | runtime.NullOf | runtime.NullOf | runtime.NullOf | runtime.NullOf>>; + @expose.unchecked() + regexpInstr(arg0: unknown, arg1?: unknown, arg2?: unknown, arg3?: unknown, arg4?: unknown, arg5?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2, arg3, arg4, arg5], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Number]]); return runtime.funcCall("REGEXP_INSTR", [this, ...__rest], __rt) as any; } + regexpLike | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1?: M1): types.Bool | runtime.NullOf>>; + @expose.unchecked() + regexpLike(arg0: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Bool], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Bool]]); return runtime.funcCall("REGEXP_LIKE", [this, ...__rest], __rt) as any; } + regexpReplace | string, M1 extends types.Varchar2 | string, M2 extends types.Number | number, M3 extends types.Number | number, M4 extends types.Varchar2 | string>(arg0: M0, arg1?: M1, arg2?: M2, arg3?: M3, arg4?: M4): types.Varchar2 | runtime.NullOf | runtime.NullOf | runtime.NullOf | runtime.NullOf>>; + @expose.unchecked() + regexpReplace(arg0: unknown, arg1?: unknown, arg2?: unknown, arg3?: unknown, arg4?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2, arg3, arg4], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("REGEXP_REPLACE", [this, ...__rest], __rt) as any; } + regexpSubstr | string, M1 extends types.Number | number, M2 extends types.Number | number, M3 extends types.Varchar2 | string, M4 extends types.Number | number>(arg0: M0, arg1?: M1, arg2?: M2, arg3?: M3, arg4?: M4): types.Varchar2<0 | 1>; + @expose.unchecked() + regexpSubstr(arg0: unknown, arg1?: unknown, arg2?: unknown, arg3?: unknown, arg4?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1, arg2, arg3, arg4], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("REGEXP_SUBSTR", [this, ...__rest], __rt) as any; } + replace | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1?: M1): types.Varchar2 | runtime.NullOf>>; + @expose.unchecked() + replace(arg0: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("REPLACE", [this, ...__rest], __rt) as any; } + rpad | number, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>>; + rpad | number>(arg0: M0): types.Varchar2>>; + @expose.unchecked() + rpad(arg0: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Number, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("RPAD", [this, ...__rest], __rt) as any; } + rtrim | string>(arg0: M0): types.Varchar2>>; + rtrim(): types.Varchar2; + @expose.unchecked() + rtrim(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2], [[], types.Varchar2]]); return runtime.funcCall("RTRIM", [this, ...__rest], __rt) as any; } + @expose.unchecked() + soundex(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("SOUNDEX", [this, ...__rest], __rt) as any; } + substr | number, M1 extends types.Number | number>(arg0: M0, arg1?: M1): types.Varchar2 | runtime.NullOf>>; + @expose.unchecked() + substr(arg0: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("SUBSTR", [this, ...__rest], __rt) as any; } + substrb | number, M1 extends types.Number | number>(arg0: M0, arg1?: M1): types.Varchar2 | runtime.NullOf>>; + @expose.unchecked() + substrb(arg0: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Number, allowPrimitive: true }], types.Varchar2], [[{ type: types.Number, allowPrimitive: true }, { type: types.Number, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("SUBSTRB", [this, ...__rest], __rt) as any; } + toBinaryDouble | string>(arg0: M0): types.BinaryDouble>>; + toBinaryDouble | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.BinaryDouble | runtime.NullOf>>; + toBinaryDouble(): types.BinaryDouble; + @expose.unchecked() + toBinaryDouble(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.BinaryDouble], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.BinaryDouble], [[], types.BinaryDouble]]); return runtime.funcCall("TO_BINARY_DOUBLE", [this, ...__rest], __rt) as any; } + toBinaryFloat | string>(arg0: M0): types.BinaryFloat>>; + toBinaryFloat | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.BinaryFloat | runtime.NullOf>>; + toBinaryFloat(): types.BinaryFloat; + @expose.unchecked() + toBinaryFloat(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }], types.BinaryFloat], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.BinaryFloat], [[], types.BinaryFloat]]); return runtime.funcCall("TO_BINARY_FLOAT", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toBoolean(): types.Bool { const [__rt, ...__rest] = runtime.match([], [[[], types.Bool]]); return runtime.funcCall("TO_BOOLEAN", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toChar(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("TO_CHAR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toClob(): types.Clob { const [__rt, ...__rest] = runtime.match([], [[[], types.Clob]]); return runtime.funcCall("TO_CLOB", [this, ...__rest], __rt) as any; } + toDate(): types.Date; + toDate | string>(arg0: M0): types.Date>>; + toDate | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Date | runtime.NullOf>>; + @expose.unchecked() + toDate(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[], types.Date], [[{ type: types.Varchar2, allowPrimitive: true }], types.Date], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Date]]); return runtime.funcCall("TO_DATE", [this, ...__rest], __rt) as any; } + toDsinterval(): types.IntervalDs; + toDsinterval | string>(arg0: M0): types.IntervalDs>>; + @expose.unchecked() + toDsinterval(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.IntervalDs], [[{ type: types.Varchar2, allowPrimitive: true }], types.IntervalDs]]); return runtime.funcCall("TO_DSINTERVAL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toNclob(): types.Nclob { const [__rt, ...__rest] = runtime.match([], [[[], types.Nclob]]); return runtime.funcCall("TO_NCLOB", [this, ...__rest], __rt) as any; } + toNumber(): types.Number; + toNumber | string>(arg0: M0): types.Number>>; + toNumber | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Number | runtime.NullOf>>; + @expose.unchecked() + toNumber(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }], types.Number], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Number]]); return runtime.funcCall("TO_NUMBER", [this, ...__rest], __rt) as any; } + toTimestamp(): types.Timestamp; + toTimestamp | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Timestamp | runtime.NullOf>>; + toTimestamp | string>(arg0: M0): types.Timestamp>>; + @expose.unchecked() + toTimestamp(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[], types.Timestamp], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Timestamp], [[{ type: types.Varchar2, allowPrimitive: true }], types.Timestamp]]); return runtime.funcCall("TO_TIMESTAMP", [this, ...__rest], __rt) as any; } + toTimestampTz(): types.Timestamptz; + toTimestampTz | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Timestamptz | runtime.NullOf>>; + toTimestampTz | string>(arg0: M0): types.Timestamptz>>; + @expose.unchecked() + toTimestampTz(arg0?: unknown, arg1?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[], types.Timestamptz], [[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Timestamptz], [[{ type: types.Varchar2, allowPrimitive: true }], types.Timestamptz]]); return runtime.funcCall("TO_TIMESTAMP_TZ", [this, ...__rest], __rt) as any; } + @expose.unchecked() + toYminterval(): types.IntervalYm { const [__rt, ...__rest] = runtime.match([], [[[], types.IntervalYm]]); return runtime.funcCall("TO_YMINTERVAL", [this, ...__rest], __rt) as any; } + @expose.unchecked() + translate | string, M1 extends types.Varchar2 | string>(arg0: M0, arg1: M1): types.Varchar2 | runtime.NullOf>> { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Varchar2, allowPrimitive: true }, { type: types.Varchar2, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("TRANSLATE", [this, ...__rest], __rt) as any; } + @expose.unchecked() + trim(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("TRIM", [this, ...__rest], __rt) as any; } + @expose.unchecked() + tzOffset(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("TZ_OFFSET", [this, ...__rest], __rt) as any; } + @expose.unchecked() + unistr(): types.Nvarchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Nvarchar2]]); return runtime.funcCall("UNISTR", [this, ...__rest], __rt) as any; } + @expose.unchecked() + upper(): types.Varchar2 { const [__rt, ...__rest] = runtime.match([], [[[], types.Varchar2]]); return runtime.funcCall("UPPER", [this, ...__rest], __rt) as any; } + @expose.unchecked() + vsize(): types.Number { const [__rt, ...__rest] = runtime.match([], [[[], types.Number]]); return runtime.funcCall("VSIZE", [this, ...__rest], __rt) as any; } + @expose.unchecked() + ['LIKE'] | string>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`LIKE`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + like | string>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`LIKE`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + ['NOT LIKE'] | string>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`NOT LIKE`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + notLike | string>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Bool]]); return runtime.opCall(runtime.sql`NOT LIKE`, [this, ...__rest] as [unknown, unknown], __rt) as any; } + @expose.unchecked() + greatest | string)[]>(...rest: R): types.Varchar2>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Varchar2, allowPrimitive: true, rest: true }], types.Varchar2]]); return runtime.funcCall("GREATEST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + least | string)[]>(...rest: R): types.Varchar2>> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Varchar2, allowPrimitive: true, rest: true }], types.Varchar2]]); return runtime.funcCall("LEAST", [this, ...__rest], __rt) as any; } + @expose.unchecked() + nullif | string>(arg0: M0): types.Varchar2<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Varchar2, allowPrimitive: true }], types.Varchar2]]); return runtime.funcCall("NULLIF", [this, ...__rest], __rt) as any; } +} diff --git a/src/types/oracle/generated/vector.ts b/src/types/oracle/generated/vector.ts new file mode 100644 index 00000000..5af32a8a --- /dev/null +++ b/src/types/oracle/generated/vector.ts @@ -0,0 +1,23 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class Vector extends Any { + declare readonly __view: "vector"; + declare [meta]: { + __class: typeof types.Vector; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.Vector<0 | 1>; + __nonNullable: types.Vector<1>; + __aggregate: types.Vector; + __any: types.Vector; + }; + static override __typname = runtime.sql`VECTOR`; + static override __typnameText = "vector"; + declare deserialize: (raw: string) => string; + +} diff --git a/src/types/oracle/generated/xmltype.ts b/src/types/oracle/generated/xmltype.ts new file mode 100644 index 00000000..70597aff --- /dev/null +++ b/src/types/oracle/generated/xmltype.ts @@ -0,0 +1,23 @@ +// Auto-generated by src/types/oracle/emit.ts from Oracle catalogs — do not edit. +import * as runtime from "../../runtime"; +import { meta } from "../../sql-value"; +import { expose } from "../../../exoeval/tool"; +import { Any } from "../overrides/any"; +import * as types from "../index"; + +export class XmlType extends Any { + declare readonly __view: "xmltype"; + declare [meta]: { + __class: typeof types.XmlType; + __raw: runtime.Sql; + __nullability: N; + __nullable: types.XmlType<0 | 1>; + __nonNullable: types.XmlType<1>; + __aggregate: types.XmlType; + __any: types.XmlType; + }; + static override __typname = runtime.sql`XMLTYPE`; + static override __typnameText = "xmltype"; + declare deserialize: (raw: string) => string; + +} diff --git a/src/types/oracle/index.ts b/src/types/oracle/index.ts new file mode 100644 index 00000000..e8733396 --- /dev/null +++ b/src/types/oracle/index.ts @@ -0,0 +1,28 @@ +// Oracle dialect barrel. Codegen populates the marker block. +// [generated-start] +export { Any } from "./overrides/any"; +export { BinaryDouble } from "./overrides/binary_double"; +export { BinaryFloat } from "./overrides/binary_float"; +export { Blob } from "./overrides/blob"; +export { Bool } from "./overrides/bool"; +export { Char } from "./generated/char"; +export { Clob } from "./generated/clob"; +export { Date } from "./generated/date"; +export { IntervalDs } from "./generated/intervalds"; +export { IntervalYm } from "./generated/intervalym"; +export { Json } from "./generated/json"; +export { Nclob } from "./generated/nclob"; +export { Number } from "./overrides/number"; +export { Nvarchar2 } from "./generated/nvarchar2"; +export { Raw } from "./overrides/raw"; +export { Rowid } from "./generated/rowid"; +export { Time } from "./generated/time"; +export { Timestamp } from "./generated/timestamp"; +export { Timestampltz } from "./generated/timestampltz"; +export { Timestamptz } from "./generated/timestamptz"; +export { Timetz } from "./generated/timetz"; +export { Urowid } from "./generated/urowid"; +export { Varchar2 } from "./generated/varchar2"; +export { Vector } from "./generated/vector"; +export { XmlType } from "./generated/xmltype"; +// [generated-end] diff --git a/src/types/oracle/introspect.test.ts b/src/types/oracle/introspect.test.ts new file mode 100644 index 00000000..11b3c01b --- /dev/null +++ b/src/types/oracle/introspect.test.ts @@ -0,0 +1,67 @@ +import { describe, test, expect, beforeAll, afterAll } from "vitest"; +import oracledb from "oracledb"; +import { requireOraclePoolAttributes } from "../../drivers/oracle-url"; +import { introspect } from "./introspect"; +import type { EmitFn } from "../emission/facts"; + +const enabled = process.env["ORACLE_URL"] !== undefined; + +describe.skipIf(!enabled)("oracle catalog introspection", () => { + let pool: oracledb.Pool; + let conn: oracledb.Connection; + let facts: EmitFn[]; + + beforeAll(async () => { + oracledb.fetchAsString = [oracledb.NUMBER]; + pool = await oracledb.createPool(requireOraclePoolAttributes()); + conn = await pool.getConnection(); + facts = await introspect(conn); + }, 60_000); + + afterAll(async () => { + await conn.close(); + await pool.close(0); + }); + + test("typed STANDARD scalar overloads are emitted", () => { + const abs = facts.find((f) => f.sql === "ABS"); + expect(abs).toMatchObject({ + kind: "scalar", + overloads: expect.arrayContaining([ + { args: [{ type: "number" }], returns: "number", nullability: "propagates" }, + ]), + }); + }); + + test("engine verification removes PL/SQL-only overloads", () => { + const addMonths = facts.find((f) => f.sql === "ADD_MONTHS")!; + expect(addMonths.overloads).toContainEqual({ + args: [{ type: "date" }, { type: "number" }], + returns: "date", + nullability: "propagates", + }); + expect(addMonths.overloads).not.toContainEqual(expect.objectContaining({ + args: [{ type: "number" }, { type: "date" }], + })); + }); + + test("V$SQLFN supplies aggregates and relational operators", () => { + expect(facts.find((f) => f.sql === "AVG")).toMatchObject({ + kind: "aggregate", + overloads: [{ args: [{ type: "number" }], returns: "number", nullability: "always" }], + }); + expect(facts.find((f) => f.sql === "=")).toMatchObject({ + kind: "binop", + overloads: [{ args: [{ type: "any" }, { type: "any" }], returns: "bool" }], + }); + }); + + test("only reviewed catalog functions cross the trust boundary", () => { + const names = new Set(facts.map((f) => f.sql)); + expect(names).toContain("ABS"); + expect(names).not.toContain("SYS_CONTEXT"); + expect(names).not.toContain("SYS_PLSQL_CPU"); + expect(names).not.toContain("CALENDAR_ADD_DAYS"); + expect(names).not.toContain("STATS_T_TEST_INDEP"); + }); +}); diff --git a/src/types/oracle/introspect.ts b/src/types/oracle/introspect.ts new file mode 100644 index 00000000..a9d00a64 --- /dev/null +++ b/src/types/oracle/introspect.ts @@ -0,0 +1,412 @@ +import oracledb from "oracledb"; +import type { EmitFn, Nullability } from "../emission/facts.ts"; + +export type OracleTypname = + | "any" + | "number" + | "binary_float" + | "binary_double" + | "varchar2" + | "nvarchar2" + | "char" + | "clob" + | "nclob" + | "date" + | "timestamp" + | "timestamptz" + | "timestampltz" + | "time" + | "timetz" + | "intervalym" + | "intervalds" + | "bool" + | "raw" + | "blob" + | "json" + | "vector" + | "rowid" + | "urowid" + | "xmltype"; + +// SYS.STANDARD exposes PL/SQL declarations. Collapse PL/SQL-only +// BINARY_INTEGER into SQL NUMBER; keep SQL types distinct. Types not +// modeled by typegres (OBJECT, REF CURSOR, TABLE, MLSLABEL, …) return +// undefined and their whole overload is omitted. +export const oracleTypeName = (dataType: string): OracleTypname | undefined => { + switch (dataType) { + case "NUMBER": + case "BINARY_INTEGER": return "number"; + case "BINARY_FLOAT": return "binary_float"; + case "BINARY_DOUBLE": return "binary_double"; + case "VARCHAR2": return "varchar2"; + case "NVARCHAR2": return "nvarchar2"; + case "CHAR": return "char"; + case "CLOB": return "clob"; + case "NCLOB": return "nclob"; + case "DATE": return "date"; + case "TIMESTAMP": return "timestamp"; + case "TIMESTAMP WITH TIME ZONE": return "timestamptz"; + case "TIMESTAMP WITH LOCAL TIME ZONE": return "timestampltz"; + case "TIME": return "time"; + case "TIME WITH TIME ZONE": return "timetz"; + case "INTERVAL YEAR TO MONTH": return "intervalym"; + case "INTERVAL DAY TO SECOND": return "intervalds"; + case "BOOLEAN": return "bool"; + case "RAW": return "raw"; + case "BLOB": return "blob"; + case "JSON": return "json"; + case "VECTOR": return "vector"; + case "ROWID": return "rowid"; + case "UROWID": return "urowid"; + case "OPAQUE/XMLTYPE": return "xmltype"; + default: return undefined; + } +}; + +// SQL spelling for CAST(NULL AS …) during catalog verification and +// for generated classes' __typname. This deliberately follows the +// collapsed typegres type, not the PL/SQL declaration's spelling. +export const ORACLE_CAST_TARGET: { [K in OracleTypname]: string } = { + any: "VARCHAR2(4000)", + number: "NUMBER", + binary_float: "BINARY_FLOAT", + binary_double: "BINARY_DOUBLE", + varchar2: "VARCHAR2(4000)", + nvarchar2: "NVARCHAR2(2000)", + char: "CHAR(2000)", + clob: "CLOB", + nclob: "NCLOB", + date: "DATE", + timestamp: "TIMESTAMP", + timestamptz: "TIMESTAMP WITH TIME ZONE", + timestampltz: "TIMESTAMP WITH LOCAL TIME ZONE", + time: "TIME", + timetz: "TIME WITH TIME ZONE", + intervalym: "INTERVAL YEAR TO MONTH", + intervalds: "INTERVAL DAY TO SECOND", + bool: "BOOLEAN", + raw: "RAW(2000)", + blob: "BLOB", + json: "JSON", + vector: "VECTOR", + rowid: "ROWID", + urowid: "UROWID", + xmltype: "XMLTYPE", +}; + +type StandardArgRow = { + OBJECT_NAME: string; + OVERLOAD: string | null; + POSITION: string; + DATA_TYPE: string; + DEFAULTED: "Y" | "N"; + IN_OUT: string; +}; + +type SqlFnRow = { + FUNC_ID: string; + NAME: string; + MINARGS: string; + MAXARGS: string; + DATATYPE: string; + AGGREGATE: "YES" | "NO"; + DISP_TYPE: string; +}; + +type SqlFnArgRow = { + FUNC_ID: string; + ARGNUM: string; + DATATYPE: string; +}; + +// The catalog supplies signatures, not trust. Only reviewed, commonly +// useful pure functions belong in the generated API; unknown names are +// excluded even when Oracle marks them DETERMINISTIC. +const CATALOG_FUNCTION_ALLOWLIST = new Set([ + // Numeric. + "ABS", "ACOS", "ASIN", "ATAN", "ATAN2", "BITAND", "CEIL", "COS", "COSH", + "EXP", "FLOOR", "LN", "LOG", "MOD", "NANVL", "POWER", "REMAINDER", "ROUND", + "SIGN", "SIN", "SINH", "SQRT", "TAN", "TANH", "TRUNC", + + // Character, binary, and hashing. + "ASCII", "CHR", "CONCAT", "CONVERT", "DUMP", "HEXTORAW", "INITCAP", "INSTR", + "INSTRB", "LENGTH", "LENGTHB", "LOWER", "LPAD", "LTRIM", "NCHR", "ORA_HASH", + "RAWTOHEX", "REGEXP_COUNT", "REGEXP_INSTR", "REGEXP_LIKE", "REGEXP_REPLACE", + "REGEXP_SUBSTR", "REPLACE", "RPAD", "RTRIM", "SOUNDEX", "STANDARD_HASH", + "SUBSTR", "SUBSTRB", "TRANSLATE", "TRIM", "UNISTR", "UPPER", "VSIZE", + + // Null selection, conversion, date/time, intervals, and JSON comparison. + "ADD_MONTHS", "COALESCE", "FROM_TZ", "GREATEST", "JSON_EQUAL", + "LAST_DAY", "LEAST", "MONTHS_BETWEEN", "NEW_TIME", "NEXT_DAY", "NULLIF", + "NUMTODSINTERVAL", "NUMTOYMINTERVAL", "NVL", "TO_BINARY_DOUBLE", + "TO_BINARY_FLOAT", "TO_BLOB", "TO_BOOLEAN", "TO_CHAR", "TO_CLOB", "TO_DATE", + "TO_DSINTERVAL", "TO_NCHAR", "TO_NCLOB", "TO_NUMBER", "TO_TIMESTAMP", + "TO_TIMESTAMP_TZ", "TO_YMINTERVAL", "TZ_OFFSET", + + // Common aggregates. + "ANY_VALUE", "APPROX_COUNT_DISTINCT", "AVG", "CORR", "COUNT", "COVAR_POP", + "COVAR_SAMP", "LISTAGG", "MAX", "MEDIAN", "MIN", "STDDEV", "STDDEV_POP", + "STDDEV_SAMP", "SUM", "VARIANCE", "VAR_POP", "VAR_SAMP", +]); + +const rowsOf = async ( + conn: oracledb.Connection, + sql: string, + binds: oracledb.BindParameters = [], +): Promise => { + const result = await conn.execute(sql, binds, { outFormat: oracledb.OUT_FORMAT_OBJECT }); + return (result.rows ?? []) as T[]; +}; + +const safeSqlName = (name: string): boolean => /^[A-Z][A-Z0-9_$#]*$/.test(name); + +const verifyCall = async ( + conn: oracledb.Connection, + name: string, + args: OracleTypname[], + aggregate = false, +): Promise<{ valid: boolean; nullability: Nullability }> => { + if (!safeSqlName(name)) { return { valid: false, nullability: "propagates" }; } + const callArgs = args.map((t) => `CAST(NULL AS ${ORACLE_CAST_TARGET[t]})`).join(", "); + const sql = `SELECT ${name}(${callArgs}) AS "V" FROM DUAL`; + try { + // Parse first: this rejects PL/SQL-only overloads whose types look + // SQL-valid (STANDARD's ADD_MONTHS(NUMBER, DATE), for example) + // without conflating syntax/type errors with value-domain errors. + await conn.getStatementInfo(sql); + } catch { + return { valid: false, nullability: "propagates" }; + } + if (aggregate) { + return { valid: true, nullability: name === "COUNT" ? "never" : "always" }; + } + try { + const rows = await rowsOf<{ V: unknown }>(conn, sql); + const value = rows[0]?.V; + return { + valid: true, + nullability: value === null || value === undefined ? "propagates" : "never", + }; + } catch { + // Signature parsed but NULL is outside its runtime domain. Keep the + // catalog fact; exact error/null semantics can be refined later. + return { valid: true, nullability: "propagates" }; + } +}; + +const scalarFacts = async ( + conn: oracledb.Connection, + sqlFnNames: Set, +): Promise => { + const rows = await rowsOf(conn, ` + SELECT a.object_name, a.overload, a.position, a.data_type, + a.defaulted, a.in_out + FROM all_arguments a + WHERE a.owner = 'SYS' + AND a.package_name = 'STANDARD' + AND a.object_name IS NOT NULL + ORDER BY a.object_name, NVL(TO_NUMBER(a.overload), 0), a.position + `); + + const groups = new Map(); + for (const row of rows) { + if (!sqlFnNames.has(row.OBJECT_NAME)) { continue; } + const key = `${row.OBJECT_NAME}\0${row.OVERLOAD ?? "0"}`; + const group = groups.get(key) ?? []; + group.push(row); + groups.set(key, group); + } + + const byName = new Map(); + for (const group of groups.values()) { + const ret = group.find((r) => Number(r.POSITION) === 0 && r.IN_OUT.includes("OUT")); + const args = group.filter((r) => Number(r.POSITION) > 0 && r.IN_OUT.includes("IN")); + if (!ret || args.length === 0) { continue; } + const returnType = oracleTypeName(ret.DATA_TYPE); + const argTypes = args.map((a) => oracleTypeName(a.DATA_TYPE)); + if (!returnType || argTypes.some((t) => t === undefined)) { continue; } + + const name = group[0]!.OBJECT_NAME; + const verified = await verifyCall(conn, name, argTypes as OracleTypname[]); + if (!verified.valid) { continue; } + const overload = { + args: args.map((arg, i) => ({ + type: argTypes[i]!, + ...(arg.DEFAULTED === "Y" ? { optional: true as const } : {}), + })), + returns: returnType, + nullability: verified.nullability, + }; + const list = byName.get(name) ?? []; + // Type collapsing (BINARY_INTEGER → number) can make catalog + // overloads identical. Keep one emitted signature. + const key = JSON.stringify(overload); + if (!list.some((o) => JSON.stringify(o) === key)) { list.push(overload); } + byName.set(name, list); + } + + return [...byName].map(([sql, overloads]) => ({ + sql, + kind: "scalar" as const, + overloads, + })); +}; + +const sqlFnType = (dataType: string): OracleTypname | undefined => { + switch (dataType) { + case "NUMERIC": return "number"; + case "STRING": return "varchar2"; + case "DATETYPE": return "date"; + case "BINARY": return "raw"; + case "BOOLEAN": return "bool"; + case "EXPR": return "any"; + default: return undefined; + } +}; + +// V$SQLFN_ARG_METADATA is the broad SQL catalog: 529 function IDs +// carry per-position coarse domains (NUMERIC/STRING/DATETYPE/BINARY/ +// BOOLEAN/EXPR). This pass covers scalars and aggregates that aren't +// declared in STANDARD. STANDARD's exact SQL types are layered on next. +const sqlFnFacts = async ( + conn: oracledb.Connection, + metadata: SqlFnRow[], + argRows: SqlFnArgRow[], +): Promise => { + const argsById = new Map(); + for (const row of argRows) { + const list = argsById.get(row.FUNC_ID) ?? []; + list.push(row); + argsById.set(row.FUNC_ID, list); + } + + const byFact = new Map(); + const aggregateNames = new Set( + metadata.filter((row) => row.AGGREGATE === "YES").map((row) => row.NAME), + ); + for (const row of metadata) { + if (row.DISP_TYPE !== "NORMAL" || !safeSqlName(row.NAME)) { continue; } + // The view repeats aggregate names with AGGREGATE=NO for internal + // evaluation forms. AVG(NULL) still parses as an aggregate, so + // call verification alone can't distinguish those duplicate rows. + if (row.AGGREGATE === "NO" && aggregateNames.has(row.NAME)) { continue; } + const catalogArgs = argsById.get(row.FUNC_ID); + if (!catalogArgs?.length) { continue; } + const minArgs = Number(row.MINARGS); + const maxArgs = Number(row.MAXARGS); + if (minArgs < 1) { continue; } + + const argTypes = catalogArgs + .sort((a, b) => Number(a.ARGNUM) - Number(b.ARGNUM)) + .map((a) => sqlFnType(a.DATATYPE)); + if (argTypes.some((t) => t === undefined)) { continue; } + // A variadic catalog entry can list only the repeated domain even + // when MINARGS > 1 (COALESCE: one EXPR row, minargs=2). Repeat the + // final domain until the minimum callable shape is represented. + while (argTypes.length < minArgs) { argTypes.push(argTypes.at(-1)); } + + const returnType = row.DATATYPE === "ARG 1" ? "arg0" : sqlFnType(row.DATATYPE); + if (!returnType) { continue; } + const typedArgs = argTypes as OracleTypname[]; + const aggregate = row.AGGREGATE === "YES"; + const verified = await verifyCall(conn, row.NAME, typedArgs, aggregate); + if (!verified.valid) { continue; } + + const overload = { + args: typedArgs.map((type, i) => ({ + type, + ...(maxArgs !== 0 && i >= minArgs ? { optional: true as const } : {}), + })), + ...(maxArgs === 0 ? { variadic: true as const } : {}), + returns: returnType, + nullability: verified.nullability, + }; + const kind = aggregate ? "aggregate" as const : "scalar" as const; + const key = `${kind}\0${row.NAME}`; + const fact = byFact.get(key) ?? { sql: row.NAME, kind, overloads: [] }; + const callShape = JSON.stringify({ args: overload.args, variadic: overload.variadic }); + const existingIndex = fact.overloads.findIndex((o) => + JSON.stringify({ args: o.args, variadic: o.variadic }) === callShape, + ); + if (existingIndex < 0) { + fact.overloads.push(overload); + } else { + const existing = fact.overloads[existingIndex]!; + // Duplicate metadata may claim both ARG 1 and a concrete return + // for the same call (AVG(NUMERIC)). Concrete is the narrower fact. + if (existing.returns === "arg0" && overload.returns !== "arg0") { + fact.overloads.splice(existingIndex, 1, overload); + } + } + byFact.set(key, fact); + } + return [...byFact.values()].map((fact) => { + if (fact.kind !== "scalar") { return fact; } + const hasConcreteHost = fact.overloads.some((o) => o.args[0]?.type !== "any"); + return hasConcreteHost + ? { ...fact, overloads: fact.overloads.filter((o) => o.args[0]?.type !== "any") } + : fact; + }); +}; + +const operatorFacts = (metadata: SqlFnRow[]): EmitFn[] => { + const seen = new Set(); + const out: EmitFn[] = []; + for (const row of metadata) { + if (row.DISP_TYPE !== "REL-OP" || Number(row.MINARGS) !== 2) { continue; } + if (!/^(?:=|!=|<|<=|>|>=)$/.test(row.NAME) || seen.has(row.NAME)) { continue; } + seen.add(row.NAME); + out.push({ + sql: row.NAME, + kind: "binop", + overloads: [{ + args: [{ type: "any" }, { type: "any" }], + returns: "bool", + nullability: "propagates", + }], + }); + } + return out; +}; + +const mergeFacts = (facts: EmitFn[]): EmitFn[] => { + const merged = new Map(); + for (const fact of facts) { + const key = `${fact.kind}\0${fact.sql}`; + const existing = merged.get(key) ?? { ...fact, overloads: [] }; + for (const overload of fact.overloads) { + const overloadKey = JSON.stringify(overload); + if (!existing.overloads.some((o) => JSON.stringify(o) === overloadKey)) { + existing.overloads.push(overload); + } + } + merged.set(key, existing); + } + return [...merged.values()]; +}; + +export const introspect = async (conn: oracledb.Connection): Promise => { + const metadata = await rowsOf(conn, ` + SELECT func_id, name, minargs, maxargs, datatype, aggregate, disp_type + FROM v$sqlfn_metadata + ORDER BY name, func_id, minargs, maxargs, datatype, aggregate, disp_type + `); + const argRows = await rowsOf(conn, ` + SELECT func_id, argnum, datatype + FROM v$sqlfn_arg_metadata + ORDER BY func_id, argnum + `); + const trustedMetadata = metadata.filter((row) => CATALOG_FUNCTION_ALLOWLIST.has(row.NAME)); + const names = new Set(trustedMetadata.map((r) => r.NAME.toUpperCase())); + const exactScalars = await scalarFacts(conn, names); + const exactNames = new Set(exactScalars.map((f) => f.sql)); + const coarseFacts = (await sqlFnFacts(conn, trustedMetadata, argRows)).filter((f) => + f.kind === "aggregate" || !exactNames.has(f.sql)); + return mergeFacts([ + ...coarseFacts, + ...exactScalars, + // Operator symbols carry no executable function body and are + // independently constrained to the six reviewed relational forms. + ...operatorFacts(metadata), + ]); +}; diff --git a/src/types/oracle/overrides/any.ts b/src/types/oracle/overrides/any.ts new file mode 100644 index 00000000..f2b5b60a --- /dev/null +++ b/src/types/oracle/overrides/any.ts @@ -0,0 +1,41 @@ +import { Any as Generated } from "../generated/any"; +import { type Dialect, inListSql, meta } from "../../sql-value"; +import * as types from "../index"; +import { sql, type Sql } from "../../../builder/sql"; +import { expose } from "../../../exoeval/tool"; + +export class Any extends Generated { + declare [meta]: { + __class: typeof Any; + __raw: Sql; + __nullability: N; + __nullable: Any<0 | 1>; + __nonNullable: Any<1>; + __aggregate: Any; + }; + static override dialect: Dialect = { + name: "oracle", + get root() { return types.Any; }, + get bool() { return types.Bool; }, + }; + static override __typname = sql`any`; + static override __typnameText = "any"; + static override acceptsPrimitive(v: unknown): boolean { + if (this !== Any) { return typeof v === this.primitiveTs; } + return ["number", "string", "boolean"].includes(typeof v) || v instanceof Uint8Array; + } + + isNull(): types.Bool<1> { + return types.Bool.from(sql`(${this.toSql()} IS NULL)`) as types.Bool<1>; + } + + isNotNull(): types.Bool<1> { + return types.Bool.from(sql`(${this.toSql()} IS NOT NULL)`) as types.Bool<1>; + } + + // eslint-disable-next-line no-restricted-syntax -- generic vararg signature inexpressible in zod + @expose.unchecked() + in(...vals: [Any | boolean | number | string | Uint8Array, ...(Any | boolean | number | string | Uint8Array)[]]): types.Bool { + return types.Bool.from(inListSql(this, vals)) as types.Bool; + } +} diff --git a/src/types/oracle/overrides/binary_double.ts b/src/types/oracle/overrides/binary_double.ts new file mode 100644 index 00000000..c8a94b1c --- /dev/null +++ b/src/types/oracle/overrides/binary_double.ts @@ -0,0 +1,6 @@ +import { BinaryDouble as Generated } from "../generated/binary_double"; + +export class BinaryDouble extends Generated { + static override primitiveTs = "number"; + override deserialize(raw: string): number { return parseFloat(raw); } +} diff --git a/src/types/oracle/overrides/binary_float.ts b/src/types/oracle/overrides/binary_float.ts new file mode 100644 index 00000000..8dfabf86 --- /dev/null +++ b/src/types/oracle/overrides/binary_float.ts @@ -0,0 +1,6 @@ +import { BinaryFloat as Generated } from "../generated/binary_float"; + +export class BinaryFloat extends Generated { + static override primitiveTs = "number"; + override deserialize(raw: string): number { return parseFloat(raw); } +} diff --git a/src/types/oracle/overrides/blob.ts b/src/types/oracle/overrides/blob.ts new file mode 100644 index 00000000..14556d83 --- /dev/null +++ b/src/types/oracle/overrides/blob.ts @@ -0,0 +1,7 @@ +import { hexToBytes } from "../../../util"; +import { Blob as Generated } from "../generated/blob"; + +export class Blob extends Generated { + static override acceptsPrimitive(v: unknown): boolean { return v instanceof Uint8Array; } + override deserialize(raw: string): Uint8Array { return hexToBytes(raw); } +} diff --git a/src/types/oracle/overrides/bool.ts b/src/types/oracle/overrides/bool.ts new file mode 100644 index 00000000..13ae7d8e --- /dev/null +++ b/src/types/oracle/overrides/bool.ts @@ -0,0 +1,21 @@ +import { Bool as Generated } from "../generated/bool"; +import { boolAnd, boolNot, boolOr } from "../../bool"; +import type { NullOf, StrictNull } from "../../runtime"; + +export class Bool extends Generated { + static override primitiveTs = "boolean"; + static override acceptsPrimitive(v: unknown): boolean { return typeof v === "boolean"; } + override deserialize(raw: string): boolean { return raw.toUpperCase() === "TRUE"; } + + and>(other: M): Bool>> { + return Bool.from(boolAnd(this.toSql(), other, Bool.dialect.name)) as any; + } + + or>(other: M): Bool>> { + return Bool.from(boolOr(this.toSql(), other, Bool.dialect.name)) as any; + } + + not(): Bool { + return Bool.from(boolNot(this.toSql(), Bool.dialect.name)) as any; + } +} diff --git a/src/types/oracle/overrides/number.ts b/src/types/oracle/overrides/number.ts new file mode 100644 index 00000000..aaa73eef --- /dev/null +++ b/src/types/oracle/overrides/number.ts @@ -0,0 +1,8 @@ +import { Number as Generated } from "../generated/number"; + +// Oracle NUMBER has up to 38 decimal digits. Accept JS numbers for +// parameters, but hydrate as string so large/decimal values stay exact. +export class Number extends Generated { + static override primitiveTs = "number"; + declare deserialize: (raw: string) => string; +} diff --git a/src/types/oracle/overrides/raw.ts b/src/types/oracle/overrides/raw.ts new file mode 100644 index 00000000..36863bea --- /dev/null +++ b/src/types/oracle/overrides/raw.ts @@ -0,0 +1,7 @@ +import { hexToBytes } from "../../../util"; +import { Raw as Generated } from "../generated/raw"; + +export class Raw extends Generated { + static override acceptsPrimitive(v: unknown): boolean { return v instanceof Uint8Array; } + override deserialize(raw: string): Uint8Array { return hexToBytes(raw); } +} diff --git a/src/types/oracle/smoke.test.ts b/src/types/oracle/smoke.test.ts new file mode 100644 index 00000000..9fdcb6ee --- /dev/null +++ b/src/types/oracle/smoke.test.ts @@ -0,0 +1,112 @@ +import { describe, test, expect, beforeAll, afterAll } from "vitest"; +import { OracleDriver } from "../../drivers/oracle"; +import { requireOraclePoolAttributes } from "../../drivers/oracle-url"; +import { Database } from "../../database"; +import { sql } from "../../builder/sql"; +import type { Connection } from "../../database"; +import { Number as OraNumber, Varchar2, Date as OraDate, Raw } from "./index"; + +const enabled = process.env["ORACLE_URL"] !== undefined; + +describe.skipIf(!enabled)("oracle generated types", () => { + let db: Database; + let conn: Connection; + + beforeAll(async () => { + db = new Database(); + conn = db.connect(await OracleDriver.create(requireOraclePoolAttributes())); + }); + + afterAll(async () => { + await conn.close(); + }); + + test("catalog scalar methods compose and execute", async () => { + const n = OraNumber.from(-5).abs(); + const s = Varchar2.from("hello").upper(); + const result = await conn.execute(sql` + SELECT ${n.toSql()} AS ${db.scopedIdent("n")}, + ${s.toSql()} AS ${db.scopedIdent("s")} + FROM DUAL + `); + expect(result.rows).toEqual([{ n: "5", s: "HELLO" }]); + }); + + test("date methods use the catalog argument order", async () => { + const d = OraDate.from(sql`DATE '2025-01-15'`).addMonths(1); + const result = await conn.execute(sql` + SELECT TO_CHAR(${d.toSql()}, 'YYYY-MM-DD') AS ${db.scopedIdent("d")} FROM DUAL + `); + expect(result.rows).toEqual([{ d: "2025-02-15" }]); + }); + + test("catalog relational operators produce Oracle predicates", async () => { + const predicate = OraNumber.from(3).eq(3); + const result = await conn.execute(sql` + SELECT CASE WHEN ${predicate.toSql()} THEN 'yes' ELSE 'no' END AS ${db.scopedIdent("v")} + FROM DUAL + `); + expect(result.rows).toEqual([{ v: "yes" }]); + }); + + test("common supplemented operators and functions execute", async () => { + const arithmetic = OraNumber.from(5).plus(3).times(2).negate(); + const date = OraDate.from(sql`DATE '2025-01-15'`).plus(2); + const like = Varchar2.from("hello").like("h%"); + const fallback = OraNumber.from(1).nvl2("yes", "no"); + const bucket = OraNumber.from(5).widthBucket(0, 10, 5); + const query = sql` + SELECT ${arithmetic.toSql()} AS ${db.scopedIdent("arithmetic")}, + TO_CHAR(${date.toSql()}, 'YYYY-MM-DD') AS ${db.scopedIdent("date")}, + CASE WHEN ${like.toSql()} THEN 'yes' ELSE 'no' END AS ${db.scopedIdent("like")}, + ${fallback.toSql()} AS ${db.scopedIdent("fallback")}, + ${bucket.toSql()} AS ${db.scopedIdent("bucket")} + FROM DUAL + `; + const result = await conn.execute(query); + expect(result.rows).toEqual([{ + arithmetic: "-16", date: "2025-01-17", like: "yes", fallback: "yes", bucket: "3", + }]); + }); + + test("reviewed catalog corrections execute", async () => { + const greatest = OraNumber.from(5).greatest(7, 3); + const nullif = OraNumber.from(5).nullif(5); + const formatted = OraNumber.from(5).toChar(); + const missingMatch = Varchar2.from("abc").regexpSubstr("z"); + const result = await conn.execute(sql` + SELECT ${greatest.toSql()} AS ${db.scopedIdent("greatest")}, + ${nullif.toSql()} AS ${db.scopedIdent("nullif")}, + ${formatted.toSql()} AS ${db.scopedIdent("formatted")}, + ${missingMatch.toSql()} AS ${db.scopedIdent("missingMatch")} + FROM DUAL + `); + expect(result.rows).toEqual([{ + greatest: "7", nullif: null, formatted: "5", missingMatch: null, + }]); + }); + + test("RAW and BLOB use their driver-defined binary formats", async () => { + const raw = Raw.from(new Uint8Array([0xde, 0xad])); + const blob = raw.toBlob(); + const result = await conn.execute(sql` + SELECT ${raw.toSql()} AS ${db.scopedIdent("raw")}, + ${blob.toSql()} AS ${db.scopedIdent("blob")} + FROM DUAL + `); + expect(result.rows).toEqual([{ raw: "DEAD", blob: "DEAD" }]); + expect(raw.deserialize(result.rows[0]!["raw"]!)).toEqual(new Uint8Array([0xde, 0xad])); + expect(blob.deserialize(result.rows[0]!["blob"]!)).toEqual(new Uint8Array([0xde, 0xad])); + }); + + test("catalog aggregate metadata emits aggregate methods", async () => { + const avg = OraNumber.from(5).avg(); + const list = OraNumber.from(5).listagg(","); + const result = await conn.execute(sql` + SELECT ${avg.toSql()} AS ${db.scopedIdent("avg")}, + ${list.toSql()} AS ${db.scopedIdent("list")} + FROM DUAL + `); + expect(result.rows).toEqual([{ avg: "5", list: "5" }]); + }); +}); diff --git a/src/types/postgres/overrides/any.ts b/src/types/postgres/overrides/any.ts index caef5ace..61a70c44 100644 --- a/src/types/postgres/overrides/any.ts +++ b/src/types/postgres/overrides/any.ts @@ -12,12 +12,11 @@ // finished loading. import { Any as Generated } from "../generated/any"; import type { Dialect } from "../../sql-value"; -import { meta } from "../../sql-value"; +import { inListSql, meta } from "../../sql-value"; import type { NullOf, StrictNull, TsTypeOf } from "../../runtime"; import * as types from "../index"; import { sql, type Sql } from "../../../builder/sql"; import { expose } from "../../../exoeval/tool"; -import { isPlainData } from "../../../util"; export class Any extends Generated { // Narrow SqlValue's `[meta].__aggregate: SqlValue` to @@ -70,18 +69,6 @@ export class Any extends Generated { this: T, ...vals: Vs ): types.Bool | NullOf>> { - const wrapped = vals.map((v) => { - if (v instanceof Any) {return v;} - if (!isPlainData(v)) { - const name = (Object.getPrototypeOf(v) as { constructor?: { name?: string } } | null)?.constructor?.name ?? "anonymous"; - throw new TypeError( - `Any.in: cannot accept ${name} instance as a list value. ` + - `Pass a typegres expression or a primitive matching ${(this[meta].__class as typeof Any).__typnameText}.`, - ); - } - return this[meta].__class.serialize(v); - }); - const list = sql.join(wrapped.map((v) => v.toSql())); - return types.Bool.from(sql`(${this.toSql()} IN (${list}))`) as unknown as types.Bool | NullOf>>; + return types.Bool.from(inListSql(this, vals)) as unknown as types.Bool | NullOf>>; } } diff --git a/src/types/sql-value.ts b/src/types/sql-value.ts index 30d75774..b14a69e5 100644 --- a/src/types/sql-value.ts +++ b/src/types/sql-value.ts @@ -211,6 +211,27 @@ export class SqlValue { export const isColumn = (v: unknown): v is SqlValue => v instanceof SqlValue && v[meta].__raw instanceof Unbound; +// Shared runtime for dialect roots' differently-typed `.in()` methods. +// The public signatures stay on each root because their class hierarchies +// require different amounts of type-level recursion. +export const inListSql = (receiver: SqlValue, vals: unknown[]): Sql => { + const cls = receiver[meta].__class; + const root = cls.dialect.root; + const wrapped = vals.map((v) => { + if (v instanceof root) { return v; } + // Uint8Array is the one bindable primitive that is a class instance. + if (!(v instanceof Uint8Array) && !isPlainData(v)) { + const name = (Object.getPrototypeOf(v) as { constructor?: { name?: string } } | null)?.constructor?.name ?? "anonymous"; + throw new TypeError( + `Any.in: cannot accept ${name} instance as a list value. ` + + `Pass a typegres expression or a primitive matching ${cls.__typnameText}.`, + ); + } + return cls.serialize(v); + }); + return sql`(${receiver.toSql()} IN (${sql.join(wrapped.map((v) => v.toSql()))}))`; +}; + // Look up a column by name on a Table instance. Throws with a specific // message when the field is missing or is an expression rather than a // column declaration. Used by mutation builders and live wrappers. diff --git a/src/types/sqlite/generated/any.ts b/src/types/sqlite/generated/any.ts index 67684b4e..78cda2d6 100644 --- a/src/types/sqlite/generated/any.ts +++ b/src/types/sqlite/generated/any.ts @@ -19,18 +19,18 @@ import * as types from "../index"; export class Any extends SqlValue { /** `concat` — Concatenation of all non-NULL args (3.44+). */ @expose.unchecked() - concat(...rest: (types.Any | number | string | boolean | Uint8Array)[]): types.Text<1> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("concat", [this, ...__rest], __rt) as any; } + concat | number | string | boolean | Uint8Array)[]>(...rest: R): types.Text<1> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("concat", [this, ...__rest], __rt) as any; } /** `hex` — Uppercase hex rendering of the blob-coerced value; hex(NULL) = ''. */ @expose.unchecked() hex(): types.Text<1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Text]]); return runtime.funcCall("hex", [this, ...__rest], __rt) as any; } /** `max` — Scalar max of 2+ values (SQLite cross-type ordering). */ - max | number | string | boolean | Uint8Array>(arg0: M0, ...rest: (types.Any | number | string | boolean | Uint8Array)[]): types.Any>>; + max | number | string | boolean | Uint8Array, R extends (types.Any | number | string | boolean | Uint8Array)[]>(arg0: M0, ...rest: R): types.Any | runtime.NullOf>>; /** `max` — Maximum value; NULL over the empty set. */ max>(this: T): T extends { [meta]: { __nullable: infer U } } ? U : types.Any<0 | 1>; @expose.unchecked() max(this: any, ...args: unknown[]): any { const [__rt, ...__rest] = runtime.match(args, [[[{ type: types.Any, allowPrimitive: true }, { type: types.Any, allowPrimitive: true, rest: true }], types.Any], [[], runtime.pgType(this)]]); return runtime.funcCall("max", [this, ...__rest], __rt) as any; } /** `min` — Scalar min of 2+ values (SQLite cross-type ordering). */ - min | number | string | boolean | Uint8Array>(arg0: M0, ...rest: (types.Any | number | string | boolean | Uint8Array)[]): types.Any>>; + min | number | string | boolean | Uint8Array, R extends (types.Any | number | string | boolean | Uint8Array)[]>(arg0: M0, ...rest: R): types.Any | runtime.NullOf>>; /** `min` — Minimum value; NULL over the empty set. */ min>(this: T): T extends { [meta]: { __nullable: infer U } } ? U : types.Any<0 | 1>; @expose.unchecked() @@ -51,23 +51,23 @@ export class Any extends SqlValue { @expose.unchecked() nullif>(this: T, arg0: types.Any | number | string | boolean | Uint8Array): T extends { [meta]: { __nullable: infer U } } ? U : types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Any, allowPrimitive: true }], runtime.pgType(this)]]); return runtime.funcCall("nullif", [this, ...__rest], __rt) as any; } /** `date` — YYYY-MM-DD for the given time value + modifiers. */ - date | string>(arg0?: M0, ...rest: (types.Text | string)[]): types.Text<0 | 1>; + date | string, R extends (types.Text | string)[]>(arg0?: M0, ...rest: R): types.Text<0 | 1>; @expose.unchecked() date(...args: unknown[]): any { const [__rt, ...__rest] = runtime.match(args, [[[], types.Text], [[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("date", [this, ...__rest], __rt) as any; } /** `time` — HH:MM:SS for the given time value + modifiers. */ - time | string>(arg0?: M0, ...rest: (types.Text | string)[]): types.Text<0 | 1>; + time | string, R extends (types.Text | string)[]>(arg0?: M0, ...rest: R): types.Text<0 | 1>; @expose.unchecked() time(...args: unknown[]): any { const [__rt, ...__rest] = runtime.match(args, [[[], types.Text], [[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("time", [this, ...__rest], __rt) as any; } /** `datetime` — YYYY-MM-DD HH:MM:SS for the given time value + modifiers. */ - datetime | string>(arg0?: M0, ...rest: (types.Text | string)[]): types.Text<0 | 1>; + datetime | string, R extends (types.Text | string)[]>(arg0?: M0, ...rest: R): types.Text<0 | 1>; @expose.unchecked() datetime(...args: unknown[]): any { const [__rt, ...__rest] = runtime.match(args, [[[], types.Text], [[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("datetime", [this, ...__rest], __rt) as any; } /** `julianday` — Julian day number (REAL). */ - julianday | string>(arg0?: M0, ...rest: (types.Text | string)[]): types.Real<0 | 1>; + julianday | string, R extends (types.Text | string)[]>(arg0?: M0, ...rest: R): types.Real<0 | 1>; @expose.unchecked() julianday(...args: unknown[]): any { const [__rt, ...__rest] = runtime.match(args, [[[], types.Real], [[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Real]]); return runtime.funcCall("julianday", [this, ...__rest], __rt) as any; } /** `unixepoch` — Unix timestamp (INTEGER; add 'subsec' for REAL). */ - unixepoch | string>(arg0?: M0, ...rest: (types.Text | string)[]): types.Integer<0 | 1>; + unixepoch | string, R extends (types.Text | string)[]>(arg0?: M0, ...rest: R): types.Integer<0 | 1>; @expose.unchecked() unixepoch(...args: unknown[]): any { const [__rt, ...__rest] = runtime.match(args, [[[], types.Integer], [[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Integer]]); return runtime.funcCall("unixepoch", [this, ...__rest], __rt) as any; } /** `timediff` — Human-readable A − B duration (3.43+). */ @@ -91,10 +91,10 @@ export class Any extends SqlValue { total(): types.Real<1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Real]]); return runtime.funcCall("total", [this, ...__rest], __rt) as any; } /** `json_array` — JSON array from the arguments. */ @expose.unchecked() - jsonArray(...rest: (types.Any | number | string | boolean | Uint8Array)[]): types.Text<1> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("json_array", [this, ...__rest], __rt) as any; } + jsonArray | number | string | boolean | Uint8Array)[]>(...rest: R): types.Text<1> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("json_array", [this, ...__rest], __rt) as any; } /** `jsonb_array` — JSON array from the arguments. */ @expose.unchecked() - jsonbArray(...rest: (types.Any | number | string | boolean | Uint8Array)[]): types.Blob<1> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Any, allowPrimitive: true, rest: true }], types.Blob]]); return runtime.funcCall("jsonb_array", [this, ...__rest], __rt) as any; } + jsonbArray | number | string | boolean | Uint8Array)[]>(...rest: R): types.Blob<1> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Any, allowPrimitive: true, rest: true }], types.Blob]]); return runtime.funcCall("jsonb_array", [this, ...__rest], __rt) as any; } /** `json_quote` — SQL value → JSON representation. */ @expose.unchecked() jsonQuote(): types.Text<1> { const [__rt, ...__rest] = runtime.match([], [[[], types.Text]]); return runtime.funcCall("json_quote", [this, ...__rest], __rt) as any; } diff --git a/src/types/sqlite/generated/blob.ts b/src/types/sqlite/generated/blob.ts index 67c1f8da..9300e585 100644 --- a/src/types/sqlite/generated/blob.ts +++ b/src/types/sqlite/generated/blob.ts @@ -64,10 +64,10 @@ export class Blob extends Any { jsonErrorPosition(): types.Integer { const [__rt, ...__rest] = runtime.match([], [[[], types.Integer]]); return runtime.funcCall("json_error_position", [this, ...__rest], __rt) as any; } /** `json_extract` — Extract value(s) at path(s) — SQL value for scalars, JSON text otherwise. */ @expose.unchecked() - jsonExtract | string>(arg0: M0, ...rest: (types.Text | string)[]): types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Any]]); return runtime.funcCall("json_extract", [this, ...__rest], __rt) as any; } + jsonExtract | string, R extends (types.Text | string)[]>(arg0: M0, ...rest: R): types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Any]]); return runtime.funcCall("json_extract", [this, ...__rest], __rt) as any; } /** `jsonb_extract` — Extract at path(s) — JSONB for objects/arrays, SQL value for scalars. */ @expose.unchecked() - jsonbExtract | string>(arg0: M0, ...rest: (types.Text | string)[]): types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Any]]); return runtime.funcCall("jsonb_extract", [this, ...__rest], __rt) as any; } + jsonbExtract | string, R extends (types.Text | string)[]>(arg0: M0, ...rest: R): types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Any]]); return runtime.funcCall("jsonb_extract", [this, ...__rest], __rt) as any; } /** `json_insert` — Insert value at path if absent (more path/value pairs may follow). */ @expose.unchecked() jsonInsert | string, M1 extends types.Any | number | string | boolean | Uint8Array>(arg0: M0, arg1: M1): types.Text<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Any, allowPrimitive: true }], types.Text]]); return runtime.funcCall("json_insert", [this, ...__rest], __rt) as any; } @@ -92,10 +92,10 @@ export class Blob extends Any { jsonPretty(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Text], [[{ type: types.Text, allowPrimitive: true }], types.Text]]); return runtime.funcCall("json_pretty", [this, ...__rest], __rt) as any; } /** `json_remove` — Remove the value(s) at path(s). */ @expose.unchecked() - jsonRemove | string>(arg0: M0, ...rest: (types.Text | string)[]): types.Text<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("json_remove", [this, ...__rest], __rt) as any; } + jsonRemove | string, R extends (types.Text | string)[]>(arg0: M0, ...rest: R): types.Text<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("json_remove", [this, ...__rest], __rt) as any; } /** `jsonb_remove` — Remove the value(s) at path(s). */ @expose.unchecked() - jsonbRemove | string>(arg0: M0, ...rest: (types.Text | string)[]): types.Blob<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Blob]]); return runtime.funcCall("jsonb_remove", [this, ...__rest], __rt) as any; } + jsonbRemove | string, R extends (types.Text | string)[]>(arg0: M0, ...rest: R): types.Blob<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Blob]]); return runtime.funcCall("jsonb_remove", [this, ...__rest], __rt) as any; } /** `json_replace` — Replace value at path if present (more path/value pairs may follow). */ @expose.unchecked() jsonReplace | string, M1 extends types.Any | number | string | boolean | Uint8Array>(arg0: M0, arg1: M1): types.Text<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Any, allowPrimitive: true }], types.Text]]); return runtime.funcCall("json_replace", [this, ...__rest], __rt) as any; } diff --git a/src/types/sqlite/generated/integer.ts b/src/types/sqlite/generated/integer.ts index e0e807cb..decd2d7d 100644 --- a/src/types/sqlite/generated/integer.ts +++ b/src/types/sqlite/generated/integer.ts @@ -37,7 +37,7 @@ export class Integer extends Any { abs(): types.Integer { const [__rt, ...__rest] = runtime.match([], [[[], types.Integer]]); return runtime.funcCall("abs", [this, ...__rest], __rt) as any; } /** `char` — String from unicode code points. */ @expose.unchecked() - char(...rest: (types.Integer | number)[]): types.Text<1> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Integer, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("char", [this, ...__rest], __rt) as any; } + char | number)[]>(...rest: R): types.Text<1> { const [__rt, ...__rest] = runtime.match([...rest], [[[{ type: types.Integer, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("char", [this, ...__rest], __rt) as any; } /** `round` — Round to Y digits (default 0). Result is REAL. */ round | number>(arg0?: M0): types.Real>>; @expose.unchecked() diff --git a/src/types/sqlite/generated/text.ts b/src/types/sqlite/generated/text.ts index 96c6d128..c9bb7bca 100644 --- a/src/types/sqlite/generated/text.ts +++ b/src/types/sqlite/generated/text.ts @@ -34,13 +34,13 @@ export class Text extends Any { /** `concat_ws` — Concatenation with separator, skipping NULLs (3.44+). */ @expose.unchecked() - concatWs | number | string | boolean | Uint8Array>(arg0: M0, ...rest: (types.Any | number | string | boolean | Uint8Array)[]): types.Text> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Any, allowPrimitive: true }, { type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("concat_ws", [this, ...__rest], __rt) as any; } + concatWs | number | string | boolean | Uint8Array, R extends (types.Any | number | string | boolean | Uint8Array)[]>(arg0: M0, ...rest: R): types.Text> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Any, allowPrimitive: true }, { type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("concat_ws", [this, ...__rest], __rt) as any; } /** `format` — printf-style formatting (see printf.html). */ @expose.unchecked() - format | number | string | boolean | Uint8Array>(arg0: M0, ...rest: (types.Any | number | string | boolean | Uint8Array)[]): types.Text> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Any, allowPrimitive: true }, { type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("format", [this, ...__rest], __rt) as any; } + format | number | string | boolean | Uint8Array, R extends (types.Any | number | string | boolean | Uint8Array)[]>(arg0: M0, ...rest: R): types.Text> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Any, allowPrimitive: true }, { type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("format", [this, ...__rest], __rt) as any; } /** `printf` — Alias of format(). */ @expose.unchecked() - printf | number | string | boolean | Uint8Array>(arg0: M0, ...rest: (types.Any | number | string | boolean | Uint8Array)[]): types.Text> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Any, allowPrimitive: true }, { type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("printf", [this, ...__rest], __rt) as any; } + printf | number | string | boolean | Uint8Array, R extends (types.Any | number | string | boolean | Uint8Array)[]>(arg0: M0, ...rest: R): types.Text> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Any, allowPrimitive: true }, { type: types.Any, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("printf", [this, ...__rest], __rt) as any; } /** `glob` — X GLOB pattern — case-sensitive glob match (glob(P, X) function form). */ @expose.unchecked() glob | string>(arg0: M0): types.Bool>> { const [__rt, ...__rest] = runtime.match([arg0], [[[{ type: types.Text, allowPrimitive: true }], types.Bool]]); return runtime.funcCall("glob", [this, ...__rest], __rt) as any; } @@ -102,7 +102,7 @@ export class Text extends Any { @expose.unchecked() upper(): types.Text { const [__rt, ...__rest] = runtime.match([], [[[], types.Text]]); return runtime.funcCall("upper", [this, ...__rest], __rt) as any; } /** `strftime` — Format a time value per the %-substitution string. */ - strftime | number | string | boolean | Uint8Array, M1 extends types.Text | string>(arg0: M0, arg1?: M1, ...rest: (types.Text | string)[]): types.Text<0 | 1>; + strftime | number | string | boolean | Uint8Array, M1 extends types.Text | string, R extends (types.Text | string)[]>(arg0: M0, arg1?: M1, ...rest: R): types.Text<0 | 1>; @expose.unchecked() strftime(...args: unknown[]): any { const [__rt, ...__rest] = runtime.match(args, [[[{ type: types.Any, allowPrimitive: true }], types.Text], [[{ type: types.Any, allowPrimitive: true }, { type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("strftime", [this, ...__rest], __rt) as any; } /** `json` — Validate + minify JSON (jsonb → binary). */ @@ -120,10 +120,10 @@ export class Text extends Any { jsonErrorPosition(): types.Integer { const [__rt, ...__rest] = runtime.match([], [[[], types.Integer]]); return runtime.funcCall("json_error_position", [this, ...__rest], __rt) as any; } /** `json_extract` — Extract value(s) at path(s) — SQL value for scalars, JSON text otherwise. */ @expose.unchecked() - jsonExtract | string>(arg0: M0, ...rest: (types.Text | string)[]): types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Any]]); return runtime.funcCall("json_extract", [this, ...__rest], __rt) as any; } + jsonExtract | string, R extends (types.Text | string)[]>(arg0: M0, ...rest: R): types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Any]]); return runtime.funcCall("json_extract", [this, ...__rest], __rt) as any; } /** `jsonb_extract` — Extract at path(s) — JSONB for objects/arrays, SQL value for scalars. */ @expose.unchecked() - jsonbExtract | string>(arg0: M0, ...rest: (types.Text | string)[]): types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Any]]); return runtime.funcCall("jsonb_extract", [this, ...__rest], __rt) as any; } + jsonbExtract | string, R extends (types.Text | string)[]>(arg0: M0, ...rest: R): types.Any<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Any]]); return runtime.funcCall("jsonb_extract", [this, ...__rest], __rt) as any; } /** `json_insert` — Insert value at path if absent (more path/value pairs may follow). */ @expose.unchecked() jsonInsert | string, M1 extends types.Any | number | string | boolean | Uint8Array>(arg0: M0, arg1: M1): types.Text<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Any, allowPrimitive: true }], types.Text]]); return runtime.funcCall("json_insert", [this, ...__rest], __rt) as any; } @@ -154,10 +154,10 @@ export class Text extends Any { jsonPretty(arg0?: unknown): any { const [__rt, ...__rest] = runtime.match([arg0], [[[], types.Text], [[{ type: types.Text, allowPrimitive: true }], types.Text]]); return runtime.funcCall("json_pretty", [this, ...__rest], __rt) as any; } /** `json_remove` — Remove the value(s) at path(s). */ @expose.unchecked() - jsonRemove | string>(arg0: M0, ...rest: (types.Text | string)[]): types.Text<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("json_remove", [this, ...__rest], __rt) as any; } + jsonRemove | string, R extends (types.Text | string)[]>(arg0: M0, ...rest: R): types.Text<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Text]]); return runtime.funcCall("json_remove", [this, ...__rest], __rt) as any; } /** `jsonb_remove` — Remove the value(s) at path(s). */ @expose.unchecked() - jsonbRemove | string>(arg0: M0, ...rest: (types.Text | string)[]): types.Blob<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Blob]]); return runtime.funcCall("jsonb_remove", [this, ...__rest], __rt) as any; } + jsonbRemove | string, R extends (types.Text | string)[]>(arg0: M0, ...rest: R): types.Blob<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, ...rest], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Text, allowPrimitive: true, rest: true }], types.Blob]]); return runtime.funcCall("jsonb_remove", [this, ...__rest], __rt) as any; } /** `json_replace` — Replace value at path if present (more path/value pairs may follow). */ @expose.unchecked() jsonReplace | string, M1 extends types.Any | number | string | boolean | Uint8Array>(arg0: M0, arg1: M1): types.Text<0 | 1> { const [__rt, ...__rest] = runtime.match([arg0, arg1], [[[{ type: types.Text, allowPrimitive: true }, { type: types.Any, allowPrimitive: true }], types.Text]]); return runtime.funcCall("json_replace", [this, ...__rest], __rt) as any; } diff --git a/src/types/sqlite/overrides/any.ts b/src/types/sqlite/overrides/any.ts index 8194e9c4..1a77350c 100644 --- a/src/types/sqlite/overrides/any.ts +++ b/src/types/sqlite/overrides/any.ts @@ -8,11 +8,10 @@ // access happens at method-call time. import { Any as Generated } from "../generated/any"; import { type Dialect } from "../../sql-value"; -import { meta } from "../../sql-value"; +import { inListSql, meta } from "../../sql-value"; import * as types from "../index"; import { sql, type Sql } from "../../../builder/sql"; import { expose } from "../../../exoeval/tool"; -import { isPlainData } from "../../../util"; export class Any extends Generated { declare [meta]: { @@ -57,21 +56,6 @@ export class Any extends Generated { // eslint-disable-next-line no-restricted-syntax -- generic vararg signature inexpressible in zod @expose.unchecked() in(...vals: [Any | boolean | number | string | Uint8Array, ...(Any | boolean | number | string | Uint8Array)[]]): types.Bool { - const wrapped = vals.map((v) => { - if (v instanceof Any) {return v;} - // Uint8Array is the blob primitive — a class instance, so it - // fails isPlainData but is accepted the same way the generated - // methods accept it (serialize() still enforces per-receiver). - if (!(v instanceof Uint8Array) && !isPlainData(v)) { - const name = (Object.getPrototypeOf(v) as { constructor?: { name?: string } } | null)?.constructor?.name ?? "anonymous"; - throw new TypeError( - `Any.in: cannot accept ${name} instance as a list value. ` + - `Pass a typegres expression or a primitive matching ${(this[meta].__class as typeof Any).__typnameText}.`, - ); - } - return this[meta].__class.serialize(v); - }); - const list = sql.join(wrapped.map((v) => v.toSql())); - return types.Bool.from(sql`(${this.toSql()} IN (${list}))`) as types.Bool; + return types.Bool.from(inListSql(this, vals)) as types.Bool; } } diff --git a/src/types/sqlite/overrides/blob.ts b/src/types/sqlite/overrides/blob.ts index b90d89c7..ecae0963 100644 --- a/src/types/sqlite/overrides/blob.ts +++ b/src/types/sqlite/overrides/blob.ts @@ -4,11 +4,13 @@ // Uint8Array too: the driver normalizes result blobs to \x-prefixed // hex (PG bytea repr — see driver.ts normalizeValue), which // deserialize() parses back to bytes. +import { hexToBytes } from "../../../util"; import { Blob as Generated } from "../generated/blob"; export class Blob extends Generated { static override acceptsPrimitive(v: unknown): boolean { return v instanceof Uint8Array; } override deserialize(raw: string): Uint8Array { - return Uint8Array.from(Buffer.from(raw.startsWith("\\x") ? raw.slice(2) : raw, "hex")); + if (!raw.startsWith("\\x")) { throw new TypeError("SQLite BLOB must use \\x-prefixed hex"); } + return hexToBytes(raw.slice(2)); } } diff --git a/src/util.ts b/src/util.ts index f33e71b3..17dfe034 100644 --- a/src/util.ts +++ b/src/util.ts @@ -44,6 +44,16 @@ export const isThenable = (v: unknown): v is PromiseLike => { ); }; +export const hexToBytes = (hex: string): Uint8Array => { + if (hex.length % 2 !== 0 || !/^[0-9a-f]*$/i.test(hex)) { + throw new TypeError("Expected an even-length hexadecimal string"); + } + return Uint8Array.from( + { length: hex.length / 2 }, + (_, i) => parseInt(hex.slice(i * 2, i * 2 + 2), 16), + ); +}; + // --- @expose-aware row deserialization --- // // Final-presentation gate for the @expose contract. If `output` is a diff --git a/tsconfig.json b/tsconfig.json index 5034aa5b..44c0ff8f 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -21,6 +21,7 @@ "typegres": ["./src/index.ts"], "typegres/postgres": ["./src/types/postgres/index.ts"], "typegres/sqlite": ["./src/types/sqlite/index.ts"], + "typegres/oracle": ["./src/types/oracle/index.ts"], "typegres/drivers/pg": ["./src/drivers/pg.ts"], "typegres/drivers/pglite": ["./src/drivers/pglite.ts"], "typegres/drivers/sqlite": ["./src/drivers/sqlite.ts"], diff --git a/tsdown.config.ts b/tsdown.config.ts index 5f645854..755e9434 100644 --- a/tsdown.config.ts +++ b/tsdown.config.ts @@ -20,7 +20,7 @@ export default defineConfig([ // loaders — those use `require` / `__filename` and would trip Node's // CJS/ESM mixed-mode check when a consumer runs the CLI. { - entry: ["src/index.ts", "src/config.ts", "src/builder/sql.ts", "src/types/postgres/index.ts", "src/types/sqlite/index.ts", "src/cli.ts", "src/exoeval/index.ts", "src/capnweb/shim.ts", "src/drivers/do.ts", "src/drivers/pg.ts", "src/drivers/pglite.ts", "src/drivers/sqlite.ts", "src/drivers/oracle.ts"], + entry: ["src/index.ts", "src/config.ts", "src/builder/sql.ts", "src/types/postgres/index.ts", "src/types/sqlite/index.ts", "src/types/oracle/index.ts", "src/cli.ts", "src/exoeval/index.ts", "src/capnweb/shim.ts", "src/drivers/do.ts", "src/drivers/pg.ts", "src/drivers/pglite.ts", "src/drivers/sqlite.ts", "src/drivers/oracle.ts"], format: ["esm"], clean: true, // capnweb is force-bundled: typegres needs a fork that isn't on npm, so it diff --git a/vitest.config.ts b/vitest.config.ts index a8a7436e..c9449c3d 100644 --- a/vitest.config.ts +++ b/vitest.config.ts @@ -22,6 +22,7 @@ const shared = { "typegres/drivers/do": `${src}/drivers/do.ts`, "typegres/postgres": `${src}/types/postgres/index.ts`, "typegres/sqlite": `${src}/types/sqlite/index.ts`, + "typegres/oracle": `${src}/types/oracle/index.ts`, typegres: `${src}/index.ts`, }, },