bun-query-builder 0.2.4 → 0.2.6
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 +54 -4
- package/dist/config.d.ts +7 -6
- package/dist/drivers/index-name.d.ts +27 -0
- package/dist/drivers/index.d.ts +2 -0
- package/dist/drivers/vitess.d.ts +38 -0
- package/dist/src/index.js +54 -3
- package/dist/types.d.ts +5 -1
- package/package.json +1 -1
package/dist/bin/cli.js
CHANGED
|
@@ -11643,7 +11643,7 @@ var init_dist = __esm(() => {
|
|
|
11643
11643
|
// src/config.ts
|
|
11644
11644
|
import process19 from "process";
|
|
11645
11645
|
function isMysqlLike(dialect = config5.dialect) {
|
|
11646
|
-
return dialect === "mysql" || dialect === "singlestore";
|
|
11646
|
+
return dialect === "mysql" || dialect === "singlestore" || dialect === "vitess";
|
|
11647
11647
|
}
|
|
11648
11648
|
function resolveDialect(explicit) {
|
|
11649
11649
|
if (explicit)
|
|
@@ -12094,7 +12094,7 @@ function resolveDatabaseName(dbConfig = config5.database) {
|
|
|
12094
12094
|
return String(raw).replace(/^['"]|['"]$/g, "");
|
|
12095
12095
|
}
|
|
12096
12096
|
function createConnectionString(dialect, dbConfig) {
|
|
12097
|
-
if ((dialect === "postgres" || dialect === "mysql" || dialect === "singlestore") && process21.env.DB_CONNECTION === dialect) {
|
|
12097
|
+
if ((dialect === "postgres" || dialect === "mysql" || dialect === "singlestore" || dialect === "vitess") && process21.env.DB_CONNECTION === dialect) {
|
|
12098
12098
|
const e = process21.env;
|
|
12099
12099
|
const envDb = (e.DB_DATABASE || dbConfig.database || "").replace(/^['"]|['"]$/g, "");
|
|
12100
12100
|
const envUser = e.DB_USERNAME || dbConfig.username;
|
|
@@ -12115,6 +12115,7 @@ function createConnectionString(dialect, dbConfig) {
|
|
|
12115
12115
|
return `postgres://${username}:${password}@${host}${port ? `:${port}` : ""}/${database}${sslQ}`;
|
|
12116
12116
|
case "mysql":
|
|
12117
12117
|
case "singlestore":
|
|
12118
|
+
case "vitess":
|
|
12118
12119
|
return `mysql://${username}:${password}@${host}${port ? `:${port}` : ""}/${database}${sslQ}`;
|
|
12119
12120
|
case "sqlite":
|
|
12120
12121
|
if (database === ":memory:") {
|
|
@@ -18078,10 +18079,26 @@ export default model
|
|
|
18078
18079
|
var init_make_model = () => {};
|
|
18079
18080
|
|
|
18080
18081
|
// src/drivers/index-name.ts
|
|
18082
|
+
function fingerprint(value) {
|
|
18083
|
+
let hash = 2166136261;
|
|
18084
|
+
for (let i = 0;i < value.length; i++) {
|
|
18085
|
+
hash ^= value.charCodeAt(i);
|
|
18086
|
+
hash = Math.imul(hash, 16777619) >>> 0;
|
|
18087
|
+
}
|
|
18088
|
+
return hash.toString(36).padStart(7, "0").slice(-7);
|
|
18089
|
+
}
|
|
18090
|
+
function boundIdentifier(name, limit = MAX_IDENTIFIER_LENGTH) {
|
|
18091
|
+
if (name.length <= limit)
|
|
18092
|
+
return name;
|
|
18093
|
+
const suffix = `_${fingerprint(name)}`;
|
|
18094
|
+
return name.slice(0, limit - suffix.length) + suffix;
|
|
18095
|
+
}
|
|
18081
18096
|
function qualifiedIndexName(tableName, indexName) {
|
|
18082
18097
|
const prefix = `${tableName}_`;
|
|
18083
|
-
|
|
18098
|
+
const qualified = indexName.startsWith(prefix) ? indexName : `${prefix}${indexName}`;
|
|
18099
|
+
return boundIdentifier(qualified);
|
|
18084
18100
|
}
|
|
18101
|
+
var MAX_IDENTIFIER_LENGTH = 63;
|
|
18085
18102
|
|
|
18086
18103
|
// src/drivers/mysql.ts
|
|
18087
18104
|
class MySQLDriver {
|
|
@@ -18509,6 +18526,35 @@ var init_singlestore = __esm(() => {
|
|
|
18509
18526
|
};
|
|
18510
18527
|
});
|
|
18511
18528
|
|
|
18529
|
+
// src/drivers/vitess.ts
|
|
18530
|
+
var VitessDriver;
|
|
18531
|
+
var init_vitess = __esm(() => {
|
|
18532
|
+
init_mysql();
|
|
18533
|
+
VitessDriver = class VitessDriver extends MySQLDriver {
|
|
18534
|
+
getAutoIncrementClause(_column) {
|
|
18535
|
+
return "";
|
|
18536
|
+
}
|
|
18537
|
+
renderColumn(column) {
|
|
18538
|
+
if (!column.references)
|
|
18539
|
+
return super.renderColumn(column);
|
|
18540
|
+
const { references: _references, ...withoutReference } = column;
|
|
18541
|
+
return super.renderColumn(withoutReference);
|
|
18542
|
+
}
|
|
18543
|
+
createTable(table) {
|
|
18544
|
+
return super.createTable(table);
|
|
18545
|
+
}
|
|
18546
|
+
addForeignKey() {
|
|
18547
|
+
return "";
|
|
18548
|
+
}
|
|
18549
|
+
createMigrationsTable() {
|
|
18550
|
+
return `CREATE TABLE IF NOT EXISTS migrations (
|
|
18551
|
+
migration VARCHAR(255) NOT NULL PRIMARY KEY,
|
|
18552
|
+
executed_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
|
|
18553
|
+
)`;
|
|
18554
|
+
}
|
|
18555
|
+
};
|
|
18556
|
+
});
|
|
18557
|
+
|
|
18512
18558
|
// src/drivers/sqlite.ts
|
|
18513
18559
|
function isNumericPlanType(type) {
|
|
18514
18560
|
return type === "integer" || type === "bigint" || type === "float" || type === "double" || type === "decimal";
|
|
@@ -18720,6 +18766,8 @@ function getDialectDriver(dialect) {
|
|
|
18720
18766
|
return new MySQLDriver;
|
|
18721
18767
|
case "singlestore":
|
|
18722
18768
|
return new SingleStoreDriver;
|
|
18769
|
+
case "vitess":
|
|
18770
|
+
return new VitessDriver;
|
|
18723
18771
|
case "sqlite":
|
|
18724
18772
|
return new SQLiteDriver;
|
|
18725
18773
|
default:
|
|
@@ -18730,11 +18778,13 @@ var init_drivers = __esm(() => {
|
|
|
18730
18778
|
init_mysql();
|
|
18731
18779
|
init_postgres();
|
|
18732
18780
|
init_singlestore();
|
|
18781
|
+
init_vitess();
|
|
18733
18782
|
init_sqlite();
|
|
18734
18783
|
init_mysql();
|
|
18735
18784
|
init_postgres();
|
|
18736
18785
|
init_singlestore();
|
|
18737
18786
|
init_sqlite();
|
|
18787
|
+
init_vitess();
|
|
18738
18788
|
});
|
|
18739
18789
|
|
|
18740
18790
|
// src/workspace.ts
|
|
@@ -31464,7 +31514,7 @@ function getPrefix() {
|
|
|
31464
31514
|
}
|
|
31465
31515
|
var prefix = getPrefix();
|
|
31466
31516
|
// package.json
|
|
31467
|
-
var version2 = "0.2.
|
|
31517
|
+
var version2 = "0.2.6";
|
|
31468
31518
|
|
|
31469
31519
|
// bin/cli.ts
|
|
31470
31520
|
init_actions();
|
package/dist/config.d.ts
CHANGED
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
import type { QueryBuilderConfig, SupportedDialect } from './types';
|
|
2
2
|
/**
|
|
3
|
-
* Whether a dialect belongs to the MySQL wire-protocol family (MySQL itself
|
|
4
|
-
* SingleStore). These share `?` placeholders, backtick identifier
|
|
5
|
-
* `ON DUPLICATE KEY UPDATE` upserts, `LAST_INSERT_ID()` id recovery,
|
|
6
|
-
* `YYYY-MM-DD HH:MM:SS` datetime literal shape. Runtime DML branches
|
|
7
|
-
* off this helper rather than `dialect === 'mysql'` so
|
|
8
|
-
* same behavior; only DDL (see
|
|
3
|
+
* Whether a dialect belongs to the MySQL wire-protocol family (MySQL itself,
|
|
4
|
+
* SingleStore, or Vitess). These share `?` placeholders, backtick identifier
|
|
5
|
+
* quoting, `ON DUPLICATE KEY UPDATE` upserts, `LAST_INSERT_ID()` id recovery,
|
|
6
|
+
* and the `YYYY-MM-DD HH:MM:SS` datetime literal shape. Runtime DML branches
|
|
7
|
+
* should key off this helper rather than `dialect === 'mysql'` so the
|
|
8
|
+
* distributed dialects inherit the same behavior; only DDL (see
|
|
9
|
+
* `SingleStoreDriver` / `VitessDriver`) diverges.
|
|
9
10
|
*/
|
|
10
11
|
export declare function isMysqlLike(dialect?: SupportedDialect): boolean;
|
|
11
12
|
/**
|
|
@@ -1 +1,28 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shorten a name to what the database will actually store.
|
|
3
|
+
*
|
|
4
|
+
* Truncating and appending the fingerprint of the full name keeps the result
|
|
5
|
+
* readable at the front - where the table and column names are - and unique at
|
|
6
|
+
* the back.
|
|
7
|
+
*/
|
|
8
|
+
export declare function boundIdentifier(name: string, limit?: unknown): string;
|
|
9
|
+
/**
|
|
10
|
+
* The name an index has in the database.
|
|
11
|
+
*
|
|
12
|
+
* Qualified with its table when it is not already, then bounded. Both halves
|
|
13
|
+
* have to happen here rather than at the call sites, because the diff compares
|
|
14
|
+
* what the model declares against what the database reports, and those only
|
|
15
|
+
* agree if the same function produced both.
|
|
16
|
+
*/
|
|
1
17
|
export declare function qualifiedIndexName(tableName: string, indexName: string): string;
|
|
18
|
+
/**
|
|
19
|
+
* Postgres truncates any identifier over 63 bytes, silently, with a notice
|
|
20
|
+
* nobody reads. MySQL refuses one over 64 outright.
|
|
21
|
+
*
|
|
22
|
+
* A truncated index name is worse than a rejected one. The database ends up
|
|
23
|
+
* holding a name the model never declared, so the next diff looks for the
|
|
24
|
+
* declared name, does not find it, and proposes creating it - forever. That is
|
|
25
|
+
* exactly what "drop and recreate this index, unchanged, on every single run"
|
|
26
|
+
* looks like from the outside.
|
|
27
|
+
*/
|
|
28
|
+
export declare const MAX_IDENTIFIER_LENGTH: 63;
|
package/dist/drivers/index.d.ts
CHANGED
|
@@ -2,6 +2,7 @@ import { MySQLDriver } from './mysql';
|
|
|
2
2
|
import { PostgresDriver } from './postgres';
|
|
3
3
|
import { SingleStoreDriver } from './singlestore';
|
|
4
4
|
import { SQLiteDriver } from './sqlite';
|
|
5
|
+
import { VitessDriver } from './vitess';
|
|
5
6
|
import type { DialectDriver } from './postgres';
|
|
6
7
|
import type { SupportedDialect } from '../types';
|
|
7
8
|
export type { DialectDriver } from './postgres';
|
|
@@ -32,6 +33,7 @@ export { MySQLDriver } from './mysql';
|
|
|
32
33
|
export { PostgresDriver } from './postgres';
|
|
33
34
|
export { SingleStoreDriver } from './singlestore';
|
|
34
35
|
export { SQLiteDriver } from './sqlite';
|
|
36
|
+
export { VitessDriver } from './vitess';
|
|
35
37
|
// DynamoDB driver (NoSQL)
|
|
36
38
|
export {
|
|
37
39
|
createDynamoDBDriver,
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { MySQLDriver } from './mysql';
|
|
2
|
+
import type { ColumnPlan, TablePlan } from '../migrations';
|
|
3
|
+
/**
|
|
4
|
+
* Vitess DDL driver.
|
|
5
|
+
*
|
|
6
|
+
* Vitess shards MySQL behind vtgate, which speaks the MySQL wire protocol, so
|
|
7
|
+
* runtime DML (placeholders, backtick quoting, `ON DUPLICATE KEY UPDATE`,
|
|
8
|
+
* `LAST_INSERT_ID`) is identical — see `isMysqlLike` in `config.ts`. Only DDL
|
|
9
|
+
* diverges, and every divergence below follows from one fact: a keyspace is
|
|
10
|
+
* split across shards that share nothing.
|
|
11
|
+
*
|
|
12
|
+
* - **No foreign keys.** Enforcing one would need a cross-shard read on every
|
|
13
|
+
* write, so vtgate rejects them in a sharded keyspace. Both forms are
|
|
14
|
+
* suppressed: the `ALTER TABLE … ADD CONSTRAINT` statement (`addForeignKey`)
|
|
15
|
+
* and the inline `REFERENCES` clause the MySQL driver emits inside a column
|
|
16
|
+
* definition. Missing the inline form would be the subtler bug — the table
|
|
17
|
+
* plan carries the reference on the column, so a `CREATE TABLE` would fail
|
|
18
|
+
* on its own without any FK statement being generated.
|
|
19
|
+
* - **No AUTO_INCREMENT.** Each shard would independently hand out the same
|
|
20
|
+
* values and collide. This is not a parse error, which makes it worse than
|
|
21
|
+
* one: the DDL succeeds and the collisions appear later, under load, as
|
|
22
|
+
* duplicate-key failures on inserts that were previously fine. Primary keys
|
|
23
|
+
* must come from the application or from a sequence table in an unsharded
|
|
24
|
+
* keyspace, declared in the VSchema.
|
|
25
|
+
*
|
|
26
|
+
* **Sharding is not expressed in DDL.** Unlike SingleStore, where the shard key
|
|
27
|
+
* is a `CREATE TABLE` clause, Vitess keeps the topology in a separate VSchema
|
|
28
|
+
* document that maps each table's sharding column to a vindex. So `createTable`
|
|
29
|
+
* here is plain MySQL minus the two constructs above, and nothing in this
|
|
30
|
+
* driver needs to know how a table is sharded.
|
|
31
|
+
*/
|
|
32
|
+
export declare class VitessDriver extends MySQLDriver {
|
|
33
|
+
protected getAutoIncrementClause(_column: ColumnPlan): string;
|
|
34
|
+
protected renderColumn(column: ColumnPlan): string;
|
|
35
|
+
createTable(table: TablePlan): string;
|
|
36
|
+
addForeignKey(): string;
|
|
37
|
+
createMigrationsTable(): string;
|
|
38
|
+
}
|
package/dist/src/index.js
CHANGED
|
@@ -11642,7 +11642,7 @@ var init_dist = __esm(() => {
|
|
|
11642
11642
|
// src/config.ts
|
|
11643
11643
|
import process19 from "process";
|
|
11644
11644
|
function isMysqlLike(dialect = config5.dialect) {
|
|
11645
|
-
return dialect === "mysql" || dialect === "singlestore";
|
|
11645
|
+
return dialect === "mysql" || dialect === "singlestore" || dialect === "vitess";
|
|
11646
11646
|
}
|
|
11647
11647
|
function resolveDialect(explicit) {
|
|
11648
11648
|
if (explicit)
|
|
@@ -12093,7 +12093,7 @@ function resolveDatabaseName(dbConfig = config5.database) {
|
|
|
12093
12093
|
return String(raw).replace(/^['"]|['"]$/g, "");
|
|
12094
12094
|
}
|
|
12095
12095
|
function createConnectionString(dialect, dbConfig) {
|
|
12096
|
-
if ((dialect === "postgres" || dialect === "mysql" || dialect === "singlestore") && process21.env.DB_CONNECTION === dialect) {
|
|
12096
|
+
if ((dialect === "postgres" || dialect === "mysql" || dialect === "singlestore" || dialect === "vitess") && process21.env.DB_CONNECTION === dialect) {
|
|
12097
12097
|
const e = process21.env;
|
|
12098
12098
|
const envDb = (e.DB_DATABASE || dbConfig.database || "").replace(/^['"]|['"]$/g, "");
|
|
12099
12099
|
const envUser = e.DB_USERNAME || dbConfig.username;
|
|
@@ -12114,6 +12114,7 @@ function createConnectionString(dialect, dbConfig) {
|
|
|
12114
12114
|
return `postgres://${username}:${password}@${host}${port ? `:${port}` : ""}/${database}${sslQ}`;
|
|
12115
12115
|
case "mysql":
|
|
12116
12116
|
case "singlestore":
|
|
12117
|
+
case "vitess":
|
|
12117
12118
|
return `mysql://${username}:${password}@${host}${port ? `:${port}` : ""}/${database}${sslQ}`;
|
|
12118
12119
|
case "sqlite":
|
|
12119
12120
|
if (database === ":memory:") {
|
|
@@ -18077,10 +18078,26 @@ export default model
|
|
|
18077
18078
|
var init_make_model = () => {};
|
|
18078
18079
|
|
|
18079
18080
|
// src/drivers/index-name.ts
|
|
18081
|
+
function fingerprint(value) {
|
|
18082
|
+
let hash = 2166136261;
|
|
18083
|
+
for (let i = 0;i < value.length; i++) {
|
|
18084
|
+
hash ^= value.charCodeAt(i);
|
|
18085
|
+
hash = Math.imul(hash, 16777619) >>> 0;
|
|
18086
|
+
}
|
|
18087
|
+
return hash.toString(36).padStart(7, "0").slice(-7);
|
|
18088
|
+
}
|
|
18089
|
+
function boundIdentifier(name, limit = MAX_IDENTIFIER_LENGTH) {
|
|
18090
|
+
if (name.length <= limit)
|
|
18091
|
+
return name;
|
|
18092
|
+
const suffix = `_${fingerprint(name)}`;
|
|
18093
|
+
return name.slice(0, limit - suffix.length) + suffix;
|
|
18094
|
+
}
|
|
18080
18095
|
function qualifiedIndexName(tableName, indexName) {
|
|
18081
18096
|
const prefix = `${tableName}_`;
|
|
18082
|
-
|
|
18097
|
+
const qualified = indexName.startsWith(prefix) ? indexName : `${prefix}${indexName}`;
|
|
18098
|
+
return boundIdentifier(qualified);
|
|
18083
18099
|
}
|
|
18100
|
+
var MAX_IDENTIFIER_LENGTH = 63;
|
|
18084
18101
|
|
|
18085
18102
|
// src/drivers/mysql.ts
|
|
18086
18103
|
class MySQLDriver {
|
|
@@ -18508,6 +18525,35 @@ var init_singlestore = __esm(() => {
|
|
|
18508
18525
|
};
|
|
18509
18526
|
});
|
|
18510
18527
|
|
|
18528
|
+
// src/drivers/vitess.ts
|
|
18529
|
+
var VitessDriver;
|
|
18530
|
+
var init_vitess = __esm(() => {
|
|
18531
|
+
init_mysql();
|
|
18532
|
+
VitessDriver = class VitessDriver extends MySQLDriver {
|
|
18533
|
+
getAutoIncrementClause(_column) {
|
|
18534
|
+
return "";
|
|
18535
|
+
}
|
|
18536
|
+
renderColumn(column) {
|
|
18537
|
+
if (!column.references)
|
|
18538
|
+
return super.renderColumn(column);
|
|
18539
|
+
const { references: _references, ...withoutReference } = column;
|
|
18540
|
+
return super.renderColumn(withoutReference);
|
|
18541
|
+
}
|
|
18542
|
+
createTable(table) {
|
|
18543
|
+
return super.createTable(table);
|
|
18544
|
+
}
|
|
18545
|
+
addForeignKey() {
|
|
18546
|
+
return "";
|
|
18547
|
+
}
|
|
18548
|
+
createMigrationsTable() {
|
|
18549
|
+
return `CREATE TABLE IF NOT EXISTS migrations (
|
|
18550
|
+
migration VARCHAR(255) NOT NULL PRIMARY KEY,
|
|
18551
|
+
executed_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
|
|
18552
|
+
)`;
|
|
18553
|
+
}
|
|
18554
|
+
};
|
|
18555
|
+
});
|
|
18556
|
+
|
|
18511
18557
|
// src/drivers/sqlite.ts
|
|
18512
18558
|
function isNumericPlanType(type) {
|
|
18513
18559
|
return type === "integer" || type === "bigint" || type === "float" || type === "double" || type === "decimal";
|
|
@@ -18719,6 +18765,8 @@ function getDialectDriver(dialect) {
|
|
|
18719
18765
|
return new MySQLDriver;
|
|
18720
18766
|
case "singlestore":
|
|
18721
18767
|
return new SingleStoreDriver;
|
|
18768
|
+
case "vitess":
|
|
18769
|
+
return new VitessDriver;
|
|
18722
18770
|
case "sqlite":
|
|
18723
18771
|
return new SQLiteDriver;
|
|
18724
18772
|
default:
|
|
@@ -18729,11 +18777,13 @@ var init_drivers = __esm(() => {
|
|
|
18729
18777
|
init_mysql();
|
|
18730
18778
|
init_postgres();
|
|
18731
18779
|
init_singlestore();
|
|
18780
|
+
init_vitess();
|
|
18732
18781
|
init_sqlite();
|
|
18733
18782
|
init_mysql();
|
|
18734
18783
|
init_postgres();
|
|
18735
18784
|
init_singlestore();
|
|
18736
18785
|
init_sqlite();
|
|
18786
|
+
init_vitess();
|
|
18737
18787
|
});
|
|
18738
18788
|
|
|
18739
18789
|
// src/workspace.ts
|
|
@@ -29564,6 +29614,7 @@ export {
|
|
|
29564
29614
|
browserQuery,
|
|
29565
29615
|
browserAuth,
|
|
29566
29616
|
applySqliteBootstrapPragmas,
|
|
29617
|
+
VitessDriver,
|
|
29567
29618
|
SingleTableRepository,
|
|
29568
29619
|
SingleTableQueryBuilder,
|
|
29569
29620
|
SingleTablePatterns,
|
package/dist/types.d.ts
CHANGED
|
@@ -293,7 +293,11 @@ export declare interface UnsafeOptions {
|
|
|
293
293
|
* but its DDL adds distributed-table concepts (`SHARD KEY`, `SORT KEY`,
|
|
294
294
|
* `ROWSTORE`/columnstore) and drops foreign keys — handled by the dedicated
|
|
295
295
|
* `SingleStoreDriver`.
|
|
296
|
+
* - 'vitess': Sharded MySQL behind vtgate. Shares MySQL's wire protocol and
|
|
297
|
+
* DML (see `isMysqlLike`), but a sharded keyspace rejects foreign keys and
|
|
298
|
+
* AUTO_INCREMENT, and its sharding topology lives in a separate VSchema
|
|
299
|
+
* document rather than in DDL — handled by the dedicated `VitessDriver`.
|
|
296
300
|
* - 'sqlite': Lightweight engine; some features are limited or emulated
|
|
297
301
|
* - 'browser': Browser-compatible mode that uses fetch() API calls instead of direct database connections
|
|
298
302
|
*/
|
|
299
|
-
export type SupportedDialect = 'postgres' | 'mysql' | 'singlestore' | 'sqlite' | 'browser';
|
|
303
|
+
export type SupportedDialect = 'postgres' | 'mysql' | 'singlestore' | 'vitess' | 'sqlite' | 'browser';
|
package/package.json
CHANGED