bun-query-builder 0.1.23 → 0.1.25
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/bin/cli.js +3512 -4266
- package/dist/browser.d.ts +1 -1
- package/dist/client.d.ts +27 -5
- package/dist/config.d.ts +0 -5
- package/dist/drivers/sqlite.d.ts +1 -1
- package/dist/orm.d.ts +85 -36
- package/dist/schema.d.ts +1 -1
- package/dist/src/index.js +3497 -4252
- package/dist/type-inference.d.ts +1 -1
- package/package.json +3 -3
package/dist/browser.d.ts
CHANGED
package/dist/client.d.ts
CHANGED
|
@@ -32,9 +32,9 @@ export declare interface WhereRaw {
|
|
|
32
32
|
export declare interface BaseSelectQueryBuilder<DB extends DatabaseSchema<any>, TTable extends keyof DB & string, TSelected, TJoined extends string = TTable,> {
|
|
33
33
|
distinct: () => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
34
34
|
distinctOn: (...columns: (keyof DB[TTable]['columns'] & string | string)[]) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
35
|
-
selectRaw: (fragment:
|
|
35
|
+
selectRaw: (fragment: SqlFragment) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
36
36
|
where: (expr: WhereExpression<DB[TTable]['columns']> | string, op?: WhereOperator, value?: any) => SelectQueryBuilder<DB, TTable, TSelected>
|
|
37
|
-
whereRaw: (fragment:
|
|
37
|
+
whereRaw: (fragment: SqlFragment) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
38
38
|
whereColumn: (left: string, op: WhereOperator, right: string) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
39
39
|
orWhereColumn: (left: string, op: WhereOperator, right: string) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
40
40
|
whereIn: (column: keyof DB[TTable]['columns'] & string, values: any[] | { toSQL: () => any }) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
@@ -100,13 +100,13 @@ export declare interface BaseSelectQueryBuilder<DB extends DatabaseSchema<any>,
|
|
|
100
100
|
crossJoin: <T2 extends keyof DB & string>(table: T2) => SelectQueryBuilder<DB, TTable, TSelected, TJoined | T2>
|
|
101
101
|
crossJoinSub: (sub: { toSQL: () => any }, alias: string) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
102
102
|
groupBy: (...columns: (keyof DB[TTable]['columns'] & string | string)[]) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
103
|
-
groupByRaw: (fragment:
|
|
103
|
+
groupByRaw: (fragment: SqlFragment) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
104
104
|
having: (expr: WhereExpression<any>) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
105
|
-
havingRaw: (fragment:
|
|
105
|
+
havingRaw: (fragment: SqlFragment) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
106
106
|
addSelect: (...columns: (keyof DB[TTable]['columns'] & string | string)[]) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
107
107
|
select?: (columns: (keyof DB[TTable]['columns'] & string | string)[]) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
108
108
|
selectAll?: () => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
109
|
-
orderByRaw: (fragment:
|
|
109
|
+
orderByRaw: (fragment: SqlFragment) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
110
110
|
union: (other: { toSQL: () => any }) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
111
111
|
unionAll: (other: { toSQL: () => any }) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
112
112
|
forPage: (page: number, perPage: number) => SelectQueryBuilder<DB, TTable, TSelected, TJoined>
|
|
@@ -356,6 +356,28 @@ export declare interface TransactionOptions {
|
|
|
356
356
|
declare type Primitive = string | number | boolean | bigint | Date | null | undefined;
|
|
357
357
|
declare type ValueOrRef = Primitive;
|
|
358
358
|
export type WhereOperator = '=' | '!=' | '<' | '>' | '<=' | '>=' | 'like' | 'in' | 'not in' | 'is' | 'is not';
|
|
359
|
+
/**
|
|
360
|
+
* Brand for SQL fragments produced by Bun's `sql\`...\`` tagged-template
|
|
361
|
+
* (or any equivalent helper). Typed as `object` so the *Raw methods
|
|
362
|
+
* (`whereRaw`, `selectRaw`, `groupByRaw`, `havingRaw`, `orderByRaw`)
|
|
363
|
+
* refuse to compile when passed a bare string — concatenated user
|
|
364
|
+
* input (`whereRaw(\`status = '${req.body.s}'\`)`) was the canonical
|
|
365
|
+
* SQL-injection vector flagged by the audit as Q-3.
|
|
366
|
+
*
|
|
367
|
+
* Callers who legitimately need raw SQL use `sql\`...\`` which
|
|
368
|
+
* separates the SQL fragment from parameter values:
|
|
369
|
+
*
|
|
370
|
+
* ```ts
|
|
371
|
+
* import { sql } from 'bun'
|
|
372
|
+
* db.selectFrom('users').whereRaw(sql\`lower(name) = lower(${input})\`)
|
|
373
|
+
* ```
|
|
374
|
+
*
|
|
375
|
+
* The runtime guard in each *Raw method also rejects bare strings as
|
|
376
|
+
* a defense-in-depth backstop for `as any` casts.
|
|
377
|
+
*
|
|
378
|
+
* See stacksjs/stacks#1858 Q-3.
|
|
379
|
+
*/
|
|
380
|
+
export type SqlFragment = object;
|
|
359
381
|
export type WhereExpression<TableColumns> = | Partial<{ [K in keyof TableColumns & string]: ValueOrRef | ValueOrRef[] }>
|
|
360
382
|
| [key: keyof TableColumns & string, op: WhereOperator, value: ValueOrRef | ValueOrRef[]]
|
|
361
383
|
| WhereRaw;
|
package/dist/config.d.ts
CHANGED
|
@@ -11,11 +11,6 @@ export declare function getPlaceholder(index: number): string;
|
|
|
11
11
|
*/
|
|
12
12
|
export declare function getPlaceholders(count: number, startIndex?: number): string;
|
|
13
13
|
export declare function getConfig(): Promise<QueryBuilderConfig>;
|
|
14
|
-
/**
|
|
15
|
-
* Programmatically set/override the query builder configuration.
|
|
16
|
-
* This is useful when you want to configure bun-query-builder from
|
|
17
|
-
* your application code rather than using a config file.
|
|
18
|
-
*/
|
|
19
14
|
export declare function setConfig(userConfig: Partial<QueryBuilderConfig>): void;
|
|
20
15
|
export declare const defaultConfig: QueryBuilderConfig;
|
|
21
16
|
// For backwards compatibility — synchronous access with default fallback.
|
package/dist/drivers/sqlite.d.ts
CHANGED
|
@@ -18,7 +18,7 @@ export declare class SQLiteDriver implements DialectDriver {
|
|
|
18
18
|
createEnumType(_enumTypeName: string, _values: string[]): string;
|
|
19
19
|
createTable(table: TablePlan): string;
|
|
20
20
|
createIndex(tableName: string, index: IndexPlan): string;
|
|
21
|
-
addForeignKey(
|
|
21
|
+
addForeignKey(_tableName: string, _columnName: string, _refTable: string, _refColumn: string, _onDelete?: string, _onUpdate?: string): string;
|
|
22
22
|
addColumn(tableName: string, column: ColumnPlan): string;
|
|
23
23
|
modifyColumn(tableName: string, column: ColumnPlan): string;
|
|
24
24
|
dropTable(tableName: string): string;
|
package/dist/orm.d.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { Database, type SQLQueryBindings } from 'bun:sqlite';
|
|
2
|
-
import type { Faker } from 'ts-
|
|
2
|
+
import type { Faker } from '@stacksjs/ts-faker';
|
|
3
|
+
import type { SupportedDialect } from './types';
|
|
3
4
|
export type {
|
|
4
5
|
ModelInstance,
|
|
5
6
|
ModelQueryBuilder,
|
|
@@ -13,12 +14,21 @@ export type {
|
|
|
13
14
|
HiddenKeys,
|
|
14
15
|
};
|
|
15
16
|
export declare function configureOrm(options: { database?: string | Database; verbose?: boolean }): void;
|
|
17
|
+
/**
|
|
18
|
+
* Return the underlying `bun:sqlite` Database backing the model layer.
|
|
19
|
+
*
|
|
20
|
+
* Only meaningful when the active dialect is sqlite (or a sqlite Database was
|
|
21
|
+
* supplied via `configureOrm`). For mysql/postgres there is no `Database`
|
|
22
|
+
* object — use the async model API instead. Retained for backwards
|
|
23
|
+
* compatibility with callers that reach for the raw sqlite handle (tests,
|
|
24
|
+
* low-level table setup).
|
|
25
|
+
*/
|
|
16
26
|
export declare function getDatabase(): Database;
|
|
17
27
|
/**
|
|
18
28
|
* Create a model class from a definition with full type inference
|
|
19
29
|
*/
|
|
20
30
|
export declare function createModel<const TDef extends ModelDefinition>(definition: TDef): void;
|
|
21
|
-
export declare function createTableFromModel(definition: ModelDefinition): void
|
|
31
|
+
export declare function createTableFromModel(definition: ModelDefinition): Promise<void>;
|
|
22
32
|
export declare function seedModel(definition: ModelDefinition, count?: number, faker?: Record<string, unknown>): Promise<void>;
|
|
23
33
|
// Attribute definition with explicit type
|
|
24
34
|
export declare interface TypedAttribute<T = unknown> {
|
|
@@ -119,6 +129,14 @@ export declare interface ModelDefinition {
|
|
|
119
129
|
readonly afterDelete?: (model: ModelHookInstance) => void | Promise<void>
|
|
120
130
|
}
|
|
121
131
|
}
|
|
132
|
+
declare interface OrmExecutor {
|
|
133
|
+
readonly dialect: SupportedDialect
|
|
134
|
+
all: (sql: string, params: unknown[]) => Promise<Record<string, unknown>[]>
|
|
135
|
+
get: (sql: string, params: unknown[]) => Promise<Record<string, unknown> | undefined>
|
|
136
|
+
run: (sql: string, params: unknown[]) => Promise<RunResult>
|
|
137
|
+
insert: (sql: string, params: unknown[], primaryKey: string) => Promise<RunResult>
|
|
138
|
+
readonly sqliteDb?: Database
|
|
139
|
+
}
|
|
122
140
|
/**
|
|
123
141
|
* Resolve a relation from its name and the parent model's definition.
|
|
124
142
|
* Uses the model registry to find the related model's definition.
|
|
@@ -234,6 +252,37 @@ export type InferRelationNames<TDef> = | InferBelongsToNames<TDef>
|
|
|
234
252
|
| InferHasOneThroughNames<TDef>
|
|
235
253
|
| InferHasManyThroughNames<TDef>;
|
|
236
254
|
declare type WhereOperator = '=' | '!=' | '<' | '>' | '<=' | '>=' | 'like' | 'not like' | 'in' | 'not in';
|
|
255
|
+
// --- Dialect-aware execution layer -------------------------------------------
|
|
256
|
+
//
|
|
257
|
+
// The model API historically ran every query through a hardcoded in-memory
|
|
258
|
+
// `bun:sqlite` Database, so projects configured for MySQL/Postgres had their
|
|
259
|
+
// model calls silently routed to a fresh, empty SQLite database — every query
|
|
260
|
+
// returned "no such table" (stacksjs/bun-query-builder#1021).
|
|
261
|
+
//
|
|
262
|
+
// All model queries now go through an `OrmExecutor` chosen from the configured
|
|
263
|
+
// dialect. SQLite keeps its synchronous `bun:sqlite` engine (wrapped in
|
|
264
|
+
// resolved Promises); MySQL/Postgres route through Bun's async `SQL` driver via
|
|
265
|
+
// the shared `getOrCreateBunSql()` connection — the same path the direct
|
|
266
|
+
// `selectFrom(...)` builder already uses. Because the network drivers are
|
|
267
|
+
// async-only, every model read/write method now returns a Promise.
|
|
268
|
+
declare type RunResult = { changes: number, lastInsertId: number | bigint | null }
|
|
269
|
+
declare class SqliteExecutor implements OrmExecutor {
|
|
270
|
+
readonly dialect: unknown;
|
|
271
|
+
public readonly sqliteDb: Database;
|
|
272
|
+
constructor(sqliteDb: Database);
|
|
273
|
+
all(sql: string, params: unknown[]): Promise<Record<string, unknown>[]>;
|
|
274
|
+
get(sql: string, params: unknown[]): Promise<Record<string, unknown> | undefined>;
|
|
275
|
+
run(sql: string, params: unknown[]): Promise<RunResult>;
|
|
276
|
+
insert(sql: string, params: unknown[]): Promise<RunResult>;
|
|
277
|
+
}
|
|
278
|
+
declare class DriverExecutor implements OrmExecutor {
|
|
279
|
+
public readonly dialect: SupportedDialect;
|
|
280
|
+
constructor(dialect: SupportedDialect);
|
|
281
|
+
all(sql: string, params: unknown[]): Promise<Record<string, unknown>[]>;
|
|
282
|
+
get(sql: string, params: unknown[]): Promise<Record<string, unknown> | undefined>;
|
|
283
|
+
run(sql: string, params: unknown[]): Promise<RunResult>;
|
|
284
|
+
insert(sql: string, params: unknown[], primaryKey: string): Promise<RunResult>;
|
|
285
|
+
}
|
|
237
286
|
/**
|
|
238
287
|
* Model instance - represents a single database record
|
|
239
288
|
*/
|
|
@@ -256,11 +305,11 @@ declare class ModelInstance<TDef extends ModelDefinition, TSelected extends Colu
|
|
|
256
305
|
getChanges(): Partial<InferModelAttributes<TDef>>;
|
|
257
306
|
fill(data: Partial<Pick<InferModelAttributes<TDef>, FillableKeys<TDef>>>): this;
|
|
258
307
|
forceFill(data: Partial<InferModelAttributes<TDef>>): this;
|
|
259
|
-
save(): this
|
|
260
|
-
update(data: Partial<Pick<InferModelAttributes<TDef>, FillableKeys<TDef>>>): this
|
|
261
|
-
fresh(): ModelInstance<TDef, TSelected> | null
|
|
262
|
-
delete(): boolean
|
|
263
|
-
refresh(): this | null
|
|
308
|
+
save(): Promise<this>;
|
|
309
|
+
update(data: Partial<Pick<InferModelAttributes<TDef>, FillableKeys<TDef>>>): Promise<this>;
|
|
310
|
+
fresh(): Promise<ModelInstance<TDef, TSelected> | null>;
|
|
311
|
+
delete(): Promise<boolean>;
|
|
312
|
+
refresh(): Promise<this | null>;
|
|
264
313
|
replicate(): ModelInstance<TDef, TSelected>;
|
|
265
314
|
toArray(): Record<string, unknown>;
|
|
266
315
|
toJSON(): Omit<Pick<ModelAttributes<TDef>, TSelected & keyof ModelAttributes<TDef>>, HiddenKeys<TDef>>;
|
|
@@ -288,15 +337,15 @@ export declare class BelongsToManyRelationBuilder<TRel extends ModelDefinition>
|
|
|
288
337
|
orderBy(column: string, direction?: 'asc' | 'desc'): this;
|
|
289
338
|
limit(n: number): this;
|
|
290
339
|
offset(n: number): this;
|
|
291
|
-
get(): ModelInstance<TRel, any>[]
|
|
292
|
-
first(): ModelInstance<TRel, any> | undefined
|
|
293
|
-
count(): number
|
|
294
|
-
exists(): boolean
|
|
295
|
-
attach(idOrIds: unknown | unknown[], extras?: Record<string, unknown>): number
|
|
296
|
-
detach(idOrIds?: unknown | unknown[]): number
|
|
297
|
-
updateExistingPivot(relatedId: unknown, extras: Record<string, unknown>): number
|
|
298
|
-
sync(items: Array<unknown | { id: unknown, [key: string]: unknown }>): { attached: unknown[], detached: unknown[], updated: unknown[] }
|
|
299
|
-
toggle(idOrIds: unknown | unknown[]): { attached: unknown[], detached: unknown[] }
|
|
340
|
+
get(): Promise<ModelInstance<TRel, any>[]>;
|
|
341
|
+
first(): Promise<ModelInstance<TRel, any> | undefined>;
|
|
342
|
+
count(): Promise<number>;
|
|
343
|
+
exists(): Promise<boolean>;
|
|
344
|
+
attach(idOrIds: unknown | unknown[], extras?: Record<string, unknown>): Promise<number>;
|
|
345
|
+
detach(idOrIds?: unknown | unknown[]): Promise<number>;
|
|
346
|
+
updateExistingPivot(relatedId: unknown, extras: Record<string, unknown>): Promise<number>;
|
|
347
|
+
sync(items: Array<unknown | { id: unknown, [key: string]: unknown }>): Promise<{ attached: unknown[], detached: unknown[], updated: unknown[] }>;
|
|
348
|
+
toggle(idOrIds: unknown | unknown[]): Promise<{ attached: unknown[], detached: unknown[] }>;
|
|
300
349
|
}
|
|
301
350
|
/**
|
|
302
351
|
* Query builder with precise type narrowing
|
|
@@ -339,18 +388,18 @@ declare class ModelQueryBuilder<TDef extends ModelDefinition, TSelected extends
|
|
|
339
388
|
with<R extends InferRelationNames<TDef>>(...relations: R[]): ModelQueryBuilder<TDef, TSelected>;
|
|
340
389
|
getWithRelations(): string[];
|
|
341
390
|
toSql(): { sql: string; params: unknown[] };
|
|
342
|
-
get(): ModelInstance<TDef, TSelected>[]
|
|
343
|
-
first(): ModelInstance<TDef, TSelected> | undefined
|
|
344
|
-
firstOrFail(): ModelInstance<TDef, TSelected
|
|
345
|
-
last(): ModelInstance<TDef, TSelected> | undefined
|
|
346
|
-
count(): number
|
|
347
|
-
exists(): boolean
|
|
348
|
-
doesntExist(): boolean
|
|
349
|
-
sole(): ModelInstance<TDef, TSelected
|
|
350
|
-
increment<K extends NumericColumns<TDef>>(column: K, amount?: number): number
|
|
351
|
-
decrement<K extends NumericColumns<TDef>>(column: K, amount?: number): number
|
|
352
|
-
chunk(size: number, callback: (items: ModelInstance<TDef, TSelected>[]) => void | false): void
|
|
353
|
-
paginate(page?: number, perPage?: number): {
|
|
391
|
+
get(): Promise<ModelInstance<TDef, TSelected>[]>;
|
|
392
|
+
first(): Promise<ModelInstance<TDef, TSelected> | undefined>;
|
|
393
|
+
firstOrFail(): Promise<ModelInstance<TDef, TSelected>>;
|
|
394
|
+
last(): Promise<ModelInstance<TDef, TSelected> | undefined>;
|
|
395
|
+
count(): Promise<number>;
|
|
396
|
+
exists(): Promise<boolean>;
|
|
397
|
+
doesntExist(): Promise<boolean>;
|
|
398
|
+
sole(): Promise<ModelInstance<TDef, TSelected>>;
|
|
399
|
+
increment<K extends NumericColumns<TDef>>(column: K, amount?: number): Promise<number>;
|
|
400
|
+
decrement<K extends NumericColumns<TDef>>(column: K, amount?: number): Promise<number>;
|
|
401
|
+
chunk(size: number, callback: (items: ModelInstance<TDef, TSelected>[]) => void | false | Promise<void | false>): Promise<void>;
|
|
402
|
+
paginate(page?: number, perPage?: number): Promise<{
|
|
354
403
|
data: ModelInstance<TDef, TSelected>[]
|
|
355
404
|
total: number
|
|
356
405
|
page: number
|
|
@@ -360,12 +409,12 @@ declare class ModelQueryBuilder<TDef extends ModelDefinition, TSelected extends
|
|
|
360
409
|
isEmpty: boolean
|
|
361
410
|
from: number | null
|
|
362
411
|
to: number | null
|
|
363
|
-
}
|
|
364
|
-
pluck<K extends ColumnName<TDef>>(column: K): (K extends keyof ModelAttributes<TDef> ? ModelAttributes<TDef>[K] : unknown)[]
|
|
365
|
-
max<K extends ColumnName<TDef>>(column: K): number | null
|
|
366
|
-
min<K extends ColumnName<TDef>>(column: K): number | null
|
|
367
|
-
avg<K extends NumericColumns<TDef>>(column: K): number
|
|
368
|
-
sum<K extends NumericColumns<TDef>>(column: K): number
|
|
369
|
-
delete(): number
|
|
370
|
-
update(data: Partial<Pick<InferModelAttributes<TDef>, FillableKeys<TDef>>>): number
|
|
412
|
+
}>;
|
|
413
|
+
pluck<K extends ColumnName<TDef>>(column: K): Promise<(K extends keyof ModelAttributes<TDef> ? ModelAttributes<TDef>[K] : unknown)[]>;
|
|
414
|
+
max<K extends ColumnName<TDef>>(column: K): Promise<number | null>;
|
|
415
|
+
min<K extends ColumnName<TDef>>(column: K): Promise<number | null>;
|
|
416
|
+
avg<K extends NumericColumns<TDef>>(column: K): Promise<number>;
|
|
417
|
+
sum<K extends NumericColumns<TDef>>(column: K): Promise<number>;
|
|
418
|
+
delete(): Promise<number>;
|
|
419
|
+
update(data: Partial<Pick<InferModelAttributes<TDef>, FillableKeys<TDef>>>): Promise<number>;
|
|
371
420
|
}
|
package/dist/schema.d.ts
CHANGED