@uql/core 3.5.2 → 3.6.1
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/CHANGELOG.md +13 -3
- package/README.md +197 -202
- package/dist/d1/d1Querier.d.ts.map +1 -1
- package/dist/d1/d1Querier.js +1 -3
- package/dist/d1/d1Querier.js.map +1 -1
- package/dist/libsql/libsqlQuerier.d.ts.map +1 -1
- package/dist/libsql/libsqlQuerier.js +1 -3
- package/dist/libsql/libsqlQuerier.js.map +1 -1
- package/dist/maria/mariadbQuerier.d.ts.map +1 -1
- package/dist/maria/mariadbQuerier.js +0 -2
- package/dist/maria/mariadbQuerier.js.map +1 -1
- package/dist/migrate/cli-config.d.ts +2 -10
- package/dist/migrate/cli-config.d.ts.map +1 -1
- package/dist/migrate/cli-config.js +26 -5
- package/dist/migrate/cli-config.js.map +1 -1
- package/dist/migrate/cli.d.ts.map +1 -1
- package/dist/migrate/cli.js +19 -8
- package/dist/migrate/cli.js.map +1 -1
- package/dist/migrate/index.d.ts +2 -1
- package/dist/migrate/index.d.ts.map +1 -1
- package/dist/migrate/index.js +1 -0
- package/dist/migrate/index.js.map +1 -1
- package/dist/migrate/migrator.d.ts +6 -5
- package/dist/migrate/migrator.d.ts.map +1 -1
- package/dist/migrate/migrator.js +18 -17
- package/dist/migrate/migrator.js.map +1 -1
- package/dist/migrate/storage/databaseStorage.js +10 -10
- package/dist/migrate/storage/databaseStorage.js.map +1 -1
- package/dist/mongo/mongodbQuerier.d.ts.map +1 -1
- package/dist/mongo/mongodbQuerier.js +42 -12
- package/dist/mongo/mongodbQuerier.js.map +1 -1
- package/dist/mysql/mysql2Querier.d.ts.map +1 -1
- package/dist/mysql/mysql2Querier.js +0 -2
- package/dist/mysql/mysql2Querier.js.map +1 -1
- package/dist/neon/neonQuerier.d.ts.map +1 -1
- package/dist/neon/neonQuerier.js +0 -2
- package/dist/neon/neonQuerier.js.map +1 -1
- package/dist/postgres/pgQuerier.d.ts.map +1 -1
- package/dist/postgres/pgQuerier.js +0 -2
- package/dist/postgres/pgQuerier.js.map +1 -1
- package/dist/querier/abstractPoolQuerier.d.ts +1 -1
- package/dist/querier/abstractPoolQuerier.d.ts.map +1 -1
- package/dist/querier/abstractPoolQuerier.js +1 -1
- package/dist/querier/abstractPoolQuerier.js.map +1 -1
- package/dist/querier/abstractQuerier.d.ts +5 -1
- package/dist/querier/abstractQuerier.d.ts.map +1 -1
- package/dist/querier/abstractQuerier.js +7 -1
- package/dist/querier/abstractQuerier.js.map +1 -1
- package/dist/querier/abstractQuerierPool.d.ts +4 -0
- package/dist/querier/abstractQuerierPool.d.ts.map +1 -1
- package/dist/querier/abstractQuerierPool.js +7 -0
- package/dist/querier/abstractQuerierPool.js.map +1 -1
- package/dist/querier/abstractSqlQuerier.d.ts +3 -2
- package/dist/querier/abstractSqlQuerier.d.ts.map +1 -1
- package/dist/querier/abstractSqlQuerier.js +7 -3
- package/dist/querier/abstractSqlQuerier.js.map +1 -1
- package/dist/querier/decorator/index.d.ts +1 -0
- package/dist/querier/decorator/index.d.ts.map +1 -1
- package/dist/querier/decorator/index.js +1 -0
- package/dist/querier/decorator/index.js.map +1 -1
- package/dist/querier/decorator/log.d.ts +7 -0
- package/dist/querier/decorator/log.d.ts.map +1 -0
- package/dist/querier/decorator/log.js +27 -0
- package/dist/querier/decorator/log.js.map +1 -0
- package/dist/sqlite/sqliteQuerier.d.ts.map +1 -1
- package/dist/sqlite/sqliteQuerier.js +1 -3
- package/dist/sqlite/sqliteQuerier.js.map +1 -1
- package/dist/type/config.d.ts +13 -0
- package/dist/type/config.d.ts.map +1 -0
- package/dist/type/config.js +2 -0
- package/dist/type/config.js.map +1 -0
- package/dist/type/index.d.ts +2 -0
- package/dist/type/index.d.ts.map +1 -1
- package/dist/type/index.js +2 -0
- package/dist/type/index.js.map +1 -1
- package/dist/type/logger.d.ts +56 -0
- package/dist/type/logger.d.ts.map +1 -0
- package/dist/type/logger.js +2 -0
- package/dist/type/logger.js.map +1 -0
- package/dist/type/migration.d.ts +7 -3
- package/dist/type/migration.d.ts.map +1 -1
- package/dist/type/querier.d.ts +3 -5
- package/dist/type/querier.d.ts.map +1 -1
- package/dist/type/querier.js.map +1 -1
- package/dist/type/querierPool.d.ts +4 -0
- package/dist/type/querierPool.d.ts.map +1 -1
- package/dist/util/index.d.ts +1 -0
- package/dist/util/index.d.ts.map +1 -1
- package/dist/util/index.js +1 -0
- package/dist/util/index.js.map +1 -1
- package/dist/util/logger.d.ts +31 -0
- package/dist/util/logger.d.ts.map +1 -0
- package/dist/util/logger.js +112 -0
- package/dist/util/logger.js.map +1 -0
- package/package.json +2 -2
package/CHANGELOG.md
CHANGED
|
@@ -3,17 +3,18 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
-
## [3.
|
|
6
|
+
## [3.6.1](https://github.com/rogerpadilla/uql/compare/@uql/core@3.6.0...@uql/core@3.6.1) (2026-01-04)
|
|
7
7
|
|
|
8
8
|
|
|
9
9
|
### Bug Fixes
|
|
10
10
|
|
|
11
|
-
*
|
|
11
|
+
* Correct README formatting and enhance user registration logic in UserService ([161fd73](https://github.com/rogerpadilla/uql/commit/161fd73ab11162c6534d51ed5b1b8fd7ca23f539))
|
|
12
12
|
|
|
13
13
|
|
|
14
14
|
### Features
|
|
15
15
|
|
|
16
|
-
*
|
|
16
|
+
* add CLI config flag, improve error handling, and introduce logging features; adjust README wording ([be50f29](https://github.com/rogerpadilla/uql/commit/be50f2951c26feb2c54c60b02b1733b3a5ca67a4))
|
|
17
|
+
* Enhance migration CLI with new config and shared querier pool, and add transaction support to querier pools. ([c5b4ab4](https://github.com/rogerpadilla/uql/commit/c5b4ab466277b43a52219bd3f1ab8d073d23a6c1))
|
|
17
18
|
|
|
18
19
|
|
|
19
20
|
|
|
@@ -25,6 +26,15 @@ All notable changes to this project will be documented in this file. Please add
|
|
|
25
26
|
|
|
26
27
|
date format is [yyyy-mm-dd]
|
|
27
28
|
|
|
29
|
+
## [3.6.1] - 2026-01-04
|
|
30
|
+
### New Features
|
|
31
|
+
- **CLI**: Added `--config` / `-c` flag to `uql-migrate` to load a custom configuration file.
|
|
32
|
+
- **CLI**: Improved error handling when loading configuration files (syntax errors are no longer swallowed).
|
|
33
|
+
|
|
34
|
+
## [3.6.0] - 2026-01-04
|
|
35
|
+
### New Features
|
|
36
|
+
- **CLI**: Added default logger, support to log slow-queries in a parameterized way, and ability to define custom loggers.
|
|
37
|
+
|
|
28
38
|
## [3.5.0] - 2026-01-03
|
|
29
39
|
### Refactor
|
|
30
40
|
- **Dialect-Aware String Defaults**: Optimized default column types for TypeScript `string` fields across all supported databases.
|
package/README.md
CHANGED
|
@@ -6,8 +6,8 @@
|
|
|
6
6
|
|
|
7
7
|
**[UQL](https://uql.app)** is the [smartest ORM](https://medium.com/@rogerpadillac/in-search-of-the-perfect-orm-e01fcc9bce3d) for TypeScript. It is engineered to be **fast**, **safe**, and **universally compatible**.
|
|
8
8
|
|
|
9
|
-
- **Runs Everywhere**: Node.js, Bun, Deno, Cloudflare Workers, Electron, React Native, and
|
|
10
|
-
- **Unified API**: A consistent
|
|
9
|
+
- **Runs Everywhere**: Node.js, Bun, Deno, Cloudflare Workers, Electron, React Native, and the Browser.
|
|
10
|
+
- **Unified API**: A consistent query interface for PostgreSQL (incl. CockroachDB, YugabyteDB), MySQL (incl. TiDB, Aurora), MariaDB, SQLite, LibSQL, Neon, Cloudflare D1, and MongoDB.
|
|
11
11
|
|
|
12
12
|
|
|
13
13
|
|
|
@@ -24,73 +24,78 @@ const users = await querier.findMany(User, {
|
|
|
24
24
|
|
|
25
25
|
## Why UQL?
|
|
26
26
|
|
|
27
|
-
|
|
27
|
+
| Feature | **UQL** | Traditional ORMs |
|
|
28
|
+
| :--- | :--- | :--- |
|
|
29
|
+
| **API** | **Unified & Intuitive**: Same syntax for SQL & NoSQL. | Fragmented: SQL and Mongo feel like different worlds. |
|
|
30
|
+
| **Safety** | **Deep Type-Safety**: Validates relations & operators at any depth. | Surface-level: Often loses types in complex joins. |
|
|
31
|
+
| **Syntax** | **Serializable JSON**: Pure data, perfect for APIs/Websockets. | Method-Chaining: Hard to transport over the wire. |
|
|
32
|
+
| **Efficiency** | **Sticky Connections**: Minimal overhead, human-readable SQL. | Heavy: Often generates "SQL Soup" that's hard to debug. |
|
|
28
33
|
|
|
29
34
|
|
|
30
35
|
|
|
31
36
|
## Features
|
|
32
37
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
- **
|
|
41
|
-
|
|
42
|
-
|
|
38
|
+
| Feature | Description |
|
|
39
|
+
| :--- | :--- |
|
|
40
|
+
| **[Context-Aware Queries](https://uql.app/querying/relations)** | Deep type-safety for operators and [relations](https://uql.app/querying/relations) at any depth. |
|
|
41
|
+
| **Serializable JSON** | 100% valid JSON queries for easy transport over HTTP/Websockets. |
|
|
42
|
+
| **Unified Dialects** | Write once, run anywhere: PostgreSQL, MySQL, SQLite, MongoDB, and more. |
|
|
43
|
+
| **Naming Strategies** | Pluggable system to translate between TypeScript `camelCase` and database `snake_case`. |
|
|
44
|
+
| **Smart SQL Engine** | Optimized sub-queries, placeholders ($1, $2), and minimal SQL generation via `QueryContext`. |
|
|
45
|
+
| **Thread-Safe by Design** | Centralized task queue and `@Serialized()` decorator prevent race conditions. |
|
|
46
|
+
| **Declarative Transactions** | Standard `@Transactional()` and `@InjectQuerier()` decorators for NestJS/DI. |
|
|
47
|
+
| **[Modern & Versatile](https://uql.app/entities/virtual-fields)** | **Pure ESM**, high-res timing, [Soft-delete](https://uql.app/entities/soft-delete), and **Vector/JSONB/JSON** support. |
|
|
48
|
+
| **Structured Logging** | Professional-grade monitoring with slow-query detection and colored output. |
|
|
43
49
|
|
|
44
50
|
|
|
45
51
|
|
|
46
52
|
## 1. Install
|
|
47
53
|
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
```sh
|
|
51
|
-
npm install @uql/core
|
|
52
|
-
# or
|
|
53
|
-
bun add @uql/core
|
|
54
|
-
```
|
|
55
|
-
|
|
56
|
-
2. Install one of the specific adapters for your database:
|
|
57
|
-
|
|
58
|
-
| Database | Driver
|
|
59
|
-
| :--- | :---
|
|
60
|
-
| `PostgreSQL` (incl. CockroachDB, YugabyteDB) | `pg`
|
|
61
|
-
| `MySQL` (incl. TiDB, Aurora) | `mysql2`
|
|
62
|
-
| `MariaDB` | `mariadb`
|
|
63
|
-
| `SQLite` | `better-sqlite3`
|
|
64
|
-
| `Cloudflare D1` | `Native Binding`
|
|
65
|
-
| `LibSQL` (Turso) | `@libsql/client`
|
|
66
|
-
| `Neon` (Serverless Postgres) | `@neondatabase/serverless`
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
For example, for `Postgres`, install the `pg` driver:
|
|
54
|
+
Install the core package and the driver for your database:
|
|
70
55
|
|
|
71
56
|
```sh
|
|
72
|
-
|
|
73
|
-
# or
|
|
74
|
-
|
|
57
|
+
# Core
|
|
58
|
+
npm install @uql/core # or bun add / pnpm add
|
|
59
|
+
|
|
60
|
+
# Potential Drivers (choose only ONE!)
|
|
61
|
+
npm install pg # PostgreSQL / Neon / Cockroach / Yugabyte
|
|
62
|
+
npm install mysql2 # MySQL / TiDB / Aurora
|
|
63
|
+
npm install mariadb # MariaDB
|
|
64
|
+
npm install better-sqlite3 # SQLite
|
|
65
|
+
npm install @libsql/client # LibSQL / Turso
|
|
66
|
+
npm install mongodb # MongoDB
|
|
67
|
+
# Cloudflare D1 uses native bindings (no extra driver needed)
|
|
75
68
|
```
|
|
76
69
|
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
```json
|
|
80
|
-
"target": "ES2024",
|
|
81
|
-
"experimentalDecorators": true,
|
|
82
|
-
"emitDecoratorMetadata": true
|
|
83
|
-
```
|
|
70
|
+
### TypeScript Configuration
|
|
84
71
|
|
|
85
|
-
|
|
72
|
+
Ensure your `tsconfig.json` is configured to support decorators and metadata:
|
|
86
73
|
|
|
87
|
-
|
|
74
|
+
```json
|
|
75
|
+
{
|
|
76
|
+
"compilerOptions": {
|
|
77
|
+
"experimentalDecorators": true,
|
|
78
|
+
"emitDecoratorMetadata": true,
|
|
79
|
+
"module": "NodeNext",
|
|
80
|
+
"target": "ESNext"
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
```
|
|
88
84
|
|
|
89
85
|
|
|
90
86
|
|
|
91
|
-
## 2. Define the
|
|
87
|
+
## 2. Define the Entities
|
|
92
88
|
|
|
93
|
-
Annotate your classes with decorators
|
|
89
|
+
Annotate your classes with decorators. UQL's engine uses this metadata for both type-safe querying and precise DDL generation.
|
|
90
|
+
|
|
91
|
+
### Core Decorators
|
|
92
|
+
|
|
93
|
+
| Decorator | Purpose |
|
|
94
|
+
| :--- | :--- |
|
|
95
|
+
| `@Entity()` | Marks a class as a database table/collection. |
|
|
96
|
+
| `@Id()` | Defines the Primary Key with support for `onInsert` generators (UUIDs, etc). |
|
|
97
|
+
| `@Field()` | Standard column with options for indexing, uniqueness, and custom comments. |
|
|
98
|
+
| `@Relation()` | (OneToOne, OneToMany, ManyToOne, ManyToMany) Defines type-safe relationships. |
|
|
94
99
|
|
|
95
100
|
```ts
|
|
96
101
|
import { v7 as uuidv7 } from 'uuid';
|
|
@@ -169,151 +174,88 @@ export class PostTag {
|
|
|
169
174
|
}
|
|
170
175
|
```
|
|
171
176
|
|
|
172
|
-
|
|
177
|
+
> **Pro Tip**: Use the `Relation<T>` utility type for relationship properties. It prevents TypeScript circular dependency errors while maintaining full type-safety.
|
|
173
178
|
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
A pool is an abstraction that manages connections (queriers) to your database. A querier is an abstraction that represents a connection to the database.
|
|
177
|
-
|
|
178
|
-
The pool can be set in any of the bootstrap files of your app (e.g., in `server.ts`).
|
|
179
|
-
|
|
180
|
-
### Available built-in QuerierPool classes per database
|
|
179
|
+
|
|
181
180
|
|
|
182
|
-
|
|
183
|
-
| :--- | :---
|
|
184
|
-
| `PostgreSQL` (incl. CockroachDB, YugabyteDB) | `@uql/core/postgres/PgQuerierPool`
|
|
185
|
-
| `MySQL` (incl. TiDB, Aurora) | `@uql/core/mysql/Mysql2QuerierPool`
|
|
186
|
-
| `MariaDB` | `@uql/core/maria/MariadbQuerierPool`
|
|
187
|
-
| `SQLite` | `@uql/core/sqlite/SqliteQuerierPool`
|
|
188
|
-
| `Cloudflare D1` | `@uql/core/d1/D1QuerierPool`
|
|
189
|
-
| `LibSQL` (Turso) | `@uql/core/libsql/LibsqlQuerierPool`
|
|
190
|
-
| `Neon` (Serverless Postgres) | `@uql/core/neon/NeonQuerierPool`
|
|
181
|
+
## 3. Set up a pool
|
|
191
182
|
|
|
192
|
-
|
|
183
|
+
A pool manages connections (queriers). Initialize it once at application bootstrap (e.g., in `server.ts`).
|
|
193
184
|
|
|
194
185
|
```ts
|
|
195
|
-
// file: ./shared/orm.ts
|
|
196
|
-
import { SnakeCaseNamingStrategy } from '@uql/core';
|
|
197
186
|
import { PgQuerierPool } from '@uql/core/postgres';
|
|
187
|
+
import { SnakeCaseNamingStrategy, type Config } from '@uql/core';
|
|
188
|
+
import { User, Profile, Post } from './entities';
|
|
198
189
|
|
|
199
190
|
export const pool = new PgQuerierPool(
|
|
191
|
+
{ host: 'localhost', database: 'uql_app', max: 10 },
|
|
200
192
|
{
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
password: 'thePassword',
|
|
204
|
-
database: 'theDatabase',
|
|
205
|
-
min: 1,
|
|
206
|
-
max: 10,
|
|
207
|
-
},
|
|
208
|
-
// Extra options (optional).
|
|
209
|
-
{
|
|
210
|
-
// Pass any custom logger function here (optional).
|
|
211
|
-
logger: console.debug,
|
|
212
|
-
// Pass a naming strategy here (optional, by default no automatic names translation).
|
|
213
|
-
// This affects both queries and schema generation.
|
|
214
|
-
// E.g. `SnakeCaseNamingStrategy` automatically translate between TypeScript camelCase and database snake_case.
|
|
193
|
+
logger: true,
|
|
194
|
+
slowQueryThreshold: 200,
|
|
215
195
|
namingStrategy: new SnakeCaseNamingStrategy()
|
|
216
|
-
}
|
|
196
|
+
}
|
|
217
197
|
);
|
|
198
|
+
|
|
199
|
+
export default {
|
|
200
|
+
pool,
|
|
201
|
+
// entities: [User, Profile, Post], // Optional: inferred from @Entity() decorators
|
|
202
|
+
migrationsPath: './migrations',
|
|
203
|
+
} satisfies Config;
|
|
218
204
|
```
|
|
219
205
|
|
|
206
|
+
> **Pro Tip**: Reusing the same connection pool for both your application and migrations is recommended. It reduces connection overhead and ensures consistent query settings (like naming strategies).
|
|
207
|
+
|
|
220
208
|
|
|
221
209
|
|
|
222
|
-
|
|
210
|
+
|
|
223
211
|
|
|
224
|
-
|
|
212
|
+
## 4. Manipulate the Data
|
|
225
213
|
|
|
226
|
-
|
|
227
|
-
import { User } from './shared/models/index.js';
|
|
228
|
-
import { pool } from './shared/orm.js';
|
|
214
|
+
UQL provides multiple ways to interact with your data. **Always ensure queriers are released back to the pool.**
|
|
229
215
|
|
|
230
|
-
|
|
216
|
+
```ts
|
|
231
217
|
const querier = await pool.getQuerier();
|
|
232
|
-
|
|
233
218
|
try {
|
|
234
|
-
// Advanced querying with relations and virtual fields
|
|
235
219
|
const users = await querier.findMany(User, {
|
|
236
220
|
$select: {
|
|
237
|
-
id: true,
|
|
238
221
|
name: true,
|
|
239
|
-
profile: ['
|
|
240
|
-
tagsCount: true // Virtual field (calculated at runtime)
|
|
222
|
+
profile: { $select: ['bio'], $required: true } // INNER JOIN
|
|
241
223
|
},
|
|
242
224
|
$where: {
|
|
243
|
-
|
|
244
|
-
|
|
225
|
+
status: 'active',
|
|
226
|
+
name: { $istartsWith: 'a' } // Case-insensitive search
|
|
245
227
|
},
|
|
246
|
-
$sort: { createdAt: 'desc' },
|
|
247
|
-
$skip: 10
|
|
248
228
|
$limit: 10,
|
|
229
|
+
$skip: 0
|
|
249
230
|
});
|
|
250
231
|
} finally {
|
|
251
|
-
|
|
252
|
-
await querier.release();
|
|
232
|
+
await querier.release(); // Essential for pool health
|
|
253
233
|
}
|
|
254
234
|
```
|
|
255
235
|
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
const querier = await pool.getQuerier();
|
|
265
|
-
|
|
266
|
-
try {
|
|
267
|
-
const authorsWithPopularPosts = await querier.findMany(User, {
|
|
268
|
-
$select: {
|
|
269
|
-
id: true,
|
|
270
|
-
name: true,
|
|
271
|
-
profile: {
|
|
272
|
-
$select: ['bio'],
|
|
273
|
-
// Filter related record and enforce INNER JOIN
|
|
274
|
-
$where: { bio: { $ne: null } },
|
|
275
|
-
$required: true
|
|
276
|
-
},
|
|
277
|
-
posts: {
|
|
278
|
-
$select: ['title', 'createdAt'],
|
|
279
|
-
// Filter the related collection directly
|
|
280
|
-
$where: { title: { $iincludes: 'typescript' } },
|
|
281
|
-
$sort: { createdAt: 'desc' },
|
|
282
|
-
}
|
|
283
|
-
},
|
|
284
|
-
$where: {
|
|
285
|
-
name: { $istartsWith: 'a' }
|
|
286
|
-
}
|
|
287
|
-
});
|
|
288
|
-
} finally {
|
|
289
|
-
await querier.release();
|
|
290
|
-
}
|
|
236
|
+
**Generated SQL (PostgreSQL):**
|
|
237
|
+
```sql
|
|
238
|
+
SELECT "User"."name", "profile"."id" AS "profile_id", "profile"."bio" AS "profile_bio"
|
|
239
|
+
FROM "User"
|
|
240
|
+
INNER JOIN "Profile" AS "profile" ON "profile"."userId" = "User"."id"
|
|
241
|
+
WHERE "User"."status" = 'active' AND "User"."name" ILIKE 'a%'
|
|
242
|
+
LIMIT 10 OFFSET 0
|
|
291
243
|
```
|
|
292
244
|
|
|
245
|
+
|
|
246
|
+
|
|
293
247
|
### Advanced: Virtual Fields & Raw SQL
|
|
294
248
|
|
|
295
|
-
Define complex logic directly in your entities using `raw` functions
|
|
249
|
+
Define complex logic directly in your entities using `raw` functions. These are resolved during SQL generation for peak efficiency.
|
|
296
250
|
|
|
297
251
|
```ts
|
|
298
|
-
import { v7 as uuidv7 } from 'uuid';
|
|
299
|
-
import { Entity, Id, Field, raw } from '@uql/core';
|
|
300
|
-
import { ItemTag } from './shared/models/index.js';
|
|
301
|
-
|
|
302
252
|
@Entity()
|
|
303
253
|
export class Item {
|
|
304
|
-
@Id()
|
|
305
|
-
id: number;
|
|
306
|
-
|
|
307
|
-
@Field()
|
|
308
|
-
name: string;
|
|
309
|
-
|
|
310
254
|
@Field({
|
|
311
255
|
virtual: raw(({ ctx, dialect, escapedPrefix }) => {
|
|
312
256
|
ctx.append('(');
|
|
313
257
|
dialect.count(ctx, ItemTag, {
|
|
314
|
-
$where: {
|
|
315
|
-
itemId: raw(({ ctx }) => ctx.append(`${escapedPrefix}.id`))
|
|
316
|
-
}
|
|
258
|
+
$where: { itemId: raw(({ ctx }) => ctx.append(`${escapedPrefix}.id`)) }
|
|
317
259
|
}, { autoPrefix: true });
|
|
318
260
|
ctx.append(')');
|
|
319
261
|
})
|
|
@@ -322,83 +264,140 @@ export class Item {
|
|
|
322
264
|
}
|
|
323
265
|
```
|
|
324
266
|
|
|
267
|
+
|
|
268
|
+
|
|
325
269
|
### Thread-Safe Transactions
|
|
326
270
|
|
|
327
|
-
UQL
|
|
271
|
+
UQL is one of the few ORMs with a **centralized serialization engine**. Transactions are guaranteed to be race-condition free.
|
|
328
272
|
|
|
273
|
+
#### Option A: Manual (Functional)
|
|
329
274
|
```ts
|
|
330
|
-
import { pool } from './shared/orm.js';
|
|
331
|
-
import { User, Profile } from './shared/models/index.js';
|
|
332
|
-
|
|
333
275
|
const result = await pool.transaction(async (querier) => {
|
|
334
276
|
const user = await querier.findOne(User, { $where: { email: '...' } });
|
|
335
|
-
|
|
336
|
-
return { userId: user.id, profileId };
|
|
277
|
+
await querier.insertOne(Profile, { userId: user.id, bio: '...' });
|
|
337
278
|
});
|
|
338
|
-
|
|
279
|
+
```
|
|
280
|
+
|
|
281
|
+
#### Option B: Declarative (Decorators)
|
|
282
|
+
Perfect for **NestJS** and other Dependency Injection frameworks. Use `@Transactional()` to wrap a method and `@InjectQuerier()` to access the managed connection.
|
|
283
|
+
|
|
284
|
+
```ts
|
|
285
|
+
import { Transactional, InjectQuerier, type Querier } from '@uql/core';
|
|
286
|
+
|
|
287
|
+
export class UserService {
|
|
288
|
+
@Transactional()
|
|
289
|
+
async register({picture, ...user}: UserProfile, @InjectQuerier() querier?: Querier) {
|
|
290
|
+
const userId = await querier.insertOne(User, user);
|
|
291
|
+
await querier.insertOne(Profile, { userId, picture });
|
|
292
|
+
}
|
|
293
|
+
}
|
|
339
294
|
```
|
|
340
295
|
|
|
341
296
|
|
|
342
297
|
|
|
343
|
-
## 5.
|
|
298
|
+
## 5. Repositories & Web Integration
|
|
344
299
|
|
|
345
|
-
|
|
300
|
+
### The Repository Pattern
|
|
346
301
|
|
|
347
|
-
|
|
302
|
+
For better abstraction, use the `GenericRepository`. It encapsulates the querier logic and provides a cleaner API for your business logic.
|
|
348
303
|
|
|
349
|
-
|
|
304
|
+
```ts
|
|
305
|
+
import { GenericRepository } from '@uql/core';
|
|
306
|
+
import { pool } from '../uql.config';
|
|
350
307
|
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
308
|
+
export class UserRepository extends GenericRepository<User> {
|
|
309
|
+
constructor() {
|
|
310
|
+
super(User, pool);
|
|
311
|
+
}
|
|
312
|
+
|
|
313
|
+
async findActiveUsers() {
|
|
314
|
+
return this.findMany({ $where: { status: 'active' } });
|
|
315
|
+
}
|
|
316
|
+
}
|
|
317
|
+
```
|
|
318
|
+
|
|
319
|
+
### Express Middleware
|
|
320
|
+
|
|
321
|
+
UQL provides built-in middleware to attach a querier to the request lifecycle, ensuring automatic cleanup.
|
|
322
|
+
|
|
323
|
+
```ts
|
|
324
|
+
import express from 'express';
|
|
325
|
+
import { querierMiddleware } from '@uql/core/express';
|
|
326
|
+
|
|
327
|
+
const app = express();
|
|
328
|
+
app.use(querierMiddleware(pool));
|
|
329
|
+
|
|
330
|
+
app.get('/users', async (req, res) => {
|
|
331
|
+
const users = await req.querier.findMany(User);
|
|
332
|
+
res.json(users);
|
|
333
|
+
});
|
|
334
|
+
```
|
|
335
|
+
|
|
336
|
+
|
|
337
|
+
|
|
338
|
+
## 6. Migrations & Synchronization
|
|
339
|
+
|
|
340
|
+
### 1. Unified Configuration
|
|
341
|
+
Ideally, use the same `uql.config.ts` for your application bootstrap and the CLI:
|
|
342
|
+
```ts
|
|
343
|
+
// uql.config.ts
|
|
344
|
+
import type { Config } from '@uql/core';
|
|
354
345
|
|
|
355
346
|
export default {
|
|
356
|
-
pool: new PgQuerierPool({ /*
|
|
357
|
-
//
|
|
358
|
-
entities: [User, Post],
|
|
347
|
+
pool: new PgQuerierPool({ /* ... */ }),
|
|
348
|
+
// entities: [User, Post], // Optional: inferred from @Entity() decorators
|
|
359
349
|
migrationsPath: './migrations',
|
|
360
|
-
};
|
|
350
|
+
} satisfies Config;
|
|
361
351
|
```
|
|
362
352
|
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
UQL provides a dedicated CLI tool for migrations.
|
|
353
|
+
**Why?** Using a single config for both your app and the CLI is recommended for consistency. It prevents bugs where your runtime uses one naming strategy (e.g. `camelCase`) but your migrations use another (e.g. `snake_case`), or where the CLI isn't aware of all your entities. It enforces a Single Source of Truth for your database connection and schema.
|
|
366
354
|
|
|
355
|
+
### 2. Manage via CLI
|
|
367
356
|
```bash
|
|
368
|
-
# Generate
|
|
357
|
+
# Generate from entities
|
|
369
358
|
npx uql-migrate generate:entities initial_schema
|
|
370
|
-
#
|
|
371
|
-
bunx uql-migrate generate:entities initial_schema
|
|
372
|
-
|
|
373
|
-
# Run pending migrations
|
|
359
|
+
# Run pending
|
|
374
360
|
npx uql-migrate up
|
|
375
|
-
#
|
|
376
|
-
bunx uql-migrate up
|
|
377
|
-
|
|
378
|
-
# Rollback the last migration
|
|
361
|
+
# Rollback last migration
|
|
379
362
|
npx uql-migrate down
|
|
380
|
-
#
|
|
381
|
-
|
|
363
|
+
# Using a custom config path
|
|
364
|
+
npx uql-migrate up --config ./configs/uql.config.ts
|
|
365
|
+
```
|
|
382
366
|
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
367
|
+
### 3. AutoSync (Development)
|
|
368
|
+
Keep your schema in sync without manual migrations. It safely adds missing tables/columns.
|
|
369
|
+
```ts
|
|
370
|
+
const migrator = new Migrator(pool);
|
|
371
|
+
await migrator.autoSync({ logging: true });
|
|
387
372
|
```
|
|
388
373
|
|
|
389
|
-
|
|
374
|
+
|
|
390
375
|
|
|
391
|
-
|
|
376
|
+
## 6. Logging & Monitoring
|
|
392
377
|
|
|
393
|
-
|
|
394
|
-
import { Migrator } from '@uql/core/migrate';
|
|
395
|
-
import { pool } from './shared/orm.js';
|
|
378
|
+
UQL features a professional-grade, structured logging system designed for high visibility and sub-millisecond performance monitoring.
|
|
396
379
|
|
|
397
|
-
|
|
398
|
-
|
|
380
|
+
### Log Levels
|
|
381
|
+
|
|
382
|
+
| Level | Description |
|
|
383
|
+
| :--- | :--- |
|
|
384
|
+
| `query` | **Standard Queries**: Beautifully formatted SQL/Command logs with execution time. |
|
|
385
|
+
| `slowQuery` | **Bottleneck Alerts**: Dedicated logging for queries exceeding your threshold. |
|
|
386
|
+
| `error` / `warn` | **System Health**: Detailed error traces and potential issue warnings. |
|
|
387
|
+
| `migration` | **Audit Trail**: Step-by-step history of schema changes. |
|
|
388
|
+
| `schema` / `info` | **Lifecycle**: Informative logs about ORM initialization and sync events. |
|
|
389
|
+
|
|
390
|
+
### Visual Feedback
|
|
391
|
+
|
|
392
|
+
The `DefaultLogger` provides high-contrast, colored output out of the box:
|
|
393
|
+
|
|
394
|
+
```text
|
|
395
|
+
query: SELECT * FROM "user" WHERE "id" = $1 -- [123] [2ms]
|
|
396
|
+
slow query: UPDATE "post" SET "title" = $1 -- ["New Title"] [1250ms]
|
|
397
|
+
error: Failed to connect to database: Connection timeout
|
|
399
398
|
```
|
|
400
399
|
|
|
401
|
-
|
|
400
|
+
> **Pro Tip**: Even if you disable general query logging in production (`logger: ['error', 'warn', 'slowQuery']`), UQL stays silent *until* a query exceeds your threshold.
|
|
402
401
|
|
|
403
402
|
|
|
404
403
|
|
|
@@ -417,16 +416,12 @@ For those who want to see the "engine under the hood," check out these resources
|
|
|
417
416
|
- **Entity Mocks**: See how complex entities and virtual fields are defined in [entityMock.ts](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/test/entityMock.ts).
|
|
418
417
|
- **Core Dialect Logic**: The foundation of our context-aware SQL generation in [abstractSqlDialect.ts](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/dialect/abstractSqlDialect.ts).
|
|
419
418
|
- **Comprehensive Test Suite**:
|
|
420
|
-
- [Abstract SQL Spec](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/dialect/abstractSqlDialect-spec.ts):
|
|
421
|
-
- [PostgreSQL
|
|
422
|
-
- [Querier Integration Tests](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/querier/abstractSqlQuerier-spec.ts):
|
|
419
|
+
- [Abstract SQL Spec](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/dialect/abstractSqlDialect-spec.ts): Base test suite for all dialects.
|
|
420
|
+
- [PostgreSQL](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/postgres/postgresDialect.spec.ts) \| [MySQL](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/mysql/mysqlDialect.spec.ts) \| [SQLite](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/sqlite/sqliteDialect.spec.ts) specs.
|
|
421
|
+
- [Querier Integration Tests](https://github.com/rogerpadilla/uql/blob/main/packages/core/src/querier/abstractSqlQuerier-spec.ts): SQL generation & connection management tests.
|
|
423
422
|
|
|
424
423
|
---
|
|
425
424
|
|
|
426
425
|
## Built with ❤️ and supported by
|
|
427
426
|
|
|
428
|
-
UQL is an open-source project
|
|
429
|
-
|
|
430
|
-
> "Intelligence in Every Fluctuation"
|
|
431
|
-
|
|
432
|
-
Their support helps us maintain and evolve the "Smartest ORM" for developers everywhere. Thank you for being part of our journey!
|
|
427
|
+
UQL is an open-source project proudly sponsored by **[Variability.ai](https://variability.ai)**.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"d1Querier.d.ts","sourceRoot":"","sources":["../../src/d1/d1Querier.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,qBAAqB,EAAE,MAAM,oCAAoC,CAAC;AAE3E,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAErD,MAAM,WAAW,MAAM;IACrB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED,MAAM,WAAW,QAAQ,CAAC,CAAC,GAAG,OAAO;IACnC,OAAO,EAAE,CAAC,EAAE,CAAC;IACb,OAAO,EAAE,OAAO,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,YAAY;IAC3B,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,mBAAmB;IAClC,IAAI,CAAC,GAAG,MAAM,EAAE,GAAG,EAAE,GAAG,mBAAmB,CAAC;IAC5C,KAAK,CAAC,CAAC,GAAG,OAAO,EAAE,OAAO,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC;IACxD,GAAG,IAAI,OAAO,CAAC,YAAY,CAAC,CAAC;IAC7B,GAAG,CAAC,CAAC,GAAG,OAAO,KAAK,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC;IACzC,GAAG,CAAC,CAAC,GAAG,OAAO,KAAK,OAAO,CAAC,CAAC,EAAE,CAAC,CAAC;CAClC;AAED,MAAM,WAAW,UAAU;IACzB,OAAO,CAAC,KAAK,EAAE,MAAM,GAAG,mBAAmB,CAAC;IAC5C,IAAI,IAAI,OAAO,CAAC,WAAW,CAAC,CAAC;IAC7B,KAAK,CAAC,CAAC,GAAG,OAAO,EAAE,UAAU,EAAE,mBAAmB,EAAE,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IAC9E,IAAI,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,YAAY,CAAC,CAAC;CAC5C;AAED,qBAAa,SAAU,SAAQ,qBAAqB;IAEhD,QAAQ,CAAC,EAAE,EAAE,UAAU;
|
|
1
|
+
{"version":3,"file":"d1Querier.d.ts","sourceRoot":"","sources":["../../src/d1/d1Querier.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,qBAAqB,EAAE,MAAM,oCAAoC,CAAC;AAE3E,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAErD,MAAM,WAAW,MAAM;IACrB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED,MAAM,WAAW,QAAQ,CAAC,CAAC,GAAG,OAAO;IACnC,OAAO,EAAE,CAAC,EAAE,CAAC;IACb,OAAO,EAAE,OAAO,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,YAAY;IAC3B,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,mBAAmB;IAClC,IAAI,CAAC,GAAG,MAAM,EAAE,GAAG,EAAE,GAAG,mBAAmB,CAAC;IAC5C,KAAK,CAAC,CAAC,GAAG,OAAO,EAAE,OAAO,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC;IACxD,GAAG,IAAI,OAAO,CAAC,YAAY,CAAC,CAAC;IAC7B,GAAG,CAAC,CAAC,GAAG,OAAO,KAAK,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC;IACzC,GAAG,CAAC,CAAC,GAAG,OAAO,KAAK,OAAO,CAAC,CAAC,EAAE,CAAC,CAAC;CAClC;AAED,MAAM,WAAW,UAAU;IACzB,OAAO,CAAC,KAAK,EAAE,MAAM,GAAG,mBAAmB,CAAC;IAC5C,IAAI,IAAI,OAAO,CAAC,WAAW,CAAC,CAAC;IAC7B,KAAK,CAAC,CAAC,GAAG,OAAO,EAAE,UAAU,EAAE,mBAAmB,EAAE,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IAC9E,IAAI,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,YAAY,CAAC,CAAC;CAC5C;AAED,qBAAa,SAAU,SAAQ,qBAAqB;IAEhD,QAAQ,CAAC,EAAE,EAAE,UAAU;aACL,KAAK,CAAC,EAAE,YAAY;gBAD7B,EAAE,EAAE,UAAU,EACL,KAAK,CAAC,EAAE,YAAY;IAKzB,WAAW,CAAC,CAAC,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,OAAO,EAAE;IAOhD,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,OAAO,EAAE;IAW7C,eAAe;CAG/B"}
|
package/dist/d1/d1Querier.js
CHANGED
|
@@ -4,19 +4,17 @@ export class D1Querier extends AbstractSqliteQuerier {
|
|
|
4
4
|
db;
|
|
5
5
|
extra;
|
|
6
6
|
constructor(db, extra) {
|
|
7
|
-
super(new SqliteDialect(extra?.namingStrategy));
|
|
7
|
+
super(new SqliteDialect(extra?.namingStrategy), extra);
|
|
8
8
|
this.db = db;
|
|
9
9
|
this.extra = extra;
|
|
10
10
|
}
|
|
11
11
|
async internalAll(query, values) {
|
|
12
|
-
this.extra?.logger?.(query, values);
|
|
13
12
|
const stmt = this.db.prepare(query);
|
|
14
13
|
const bound = values?.length ? stmt.bind(...values) : stmt;
|
|
15
14
|
const res = await bound.all();
|
|
16
15
|
return res.results;
|
|
17
16
|
}
|
|
18
17
|
async internalRun(query, values) {
|
|
19
|
-
this.extra?.logger?.(query, values);
|
|
20
18
|
const stmt = this.db.prepare(query);
|
|
21
19
|
const bound = values?.length ? stmt.bind(...values) : stmt;
|
|
22
20
|
const res = await bound.run();
|
package/dist/d1/d1Querier.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"d1Querier.js","sourceRoot":"","sources":["../../src/d1/d1Querier.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,qBAAqB,EAAE,MAAM,oCAAoC,CAAC;AAC3E,OAAO,EAAE,aAAa,EAAE,MAAM,oBAAoB,CAAC;AA0CnD,MAAM,OAAO,SAAU,SAAQ,qBAAqB;IAEvC;
|
|
1
|
+
{"version":3,"file":"d1Querier.js","sourceRoot":"","sources":["../../src/d1/d1Querier.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,qBAAqB,EAAE,MAAM,oCAAoC,CAAC;AAC3E,OAAO,EAAE,aAAa,EAAE,MAAM,oBAAoB,CAAC;AA0CnD,MAAM,OAAO,SAAU,SAAQ,qBAAqB;IAEvC;IACS;IAFpB,YACW,EAAc,EACL,KAAoB;QAEtC,KAAK,CAAC,IAAI,aAAa,CAAC,KAAK,EAAE,cAAc,CAAC,EAAE,KAAK,CAAC,CAAC;QAH9C,OAAE,GAAF,EAAE,CAAY;QACL,UAAK,GAAL,KAAK,CAAe;IAGxC,CAAC;IAEQ,KAAK,CAAC,WAAW,CAAI,KAAa,EAAE,MAAkB;QAC7D,MAAM,IAAI,GAAG,IAAI,CAAC,EAAE,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;QACpC,MAAM,KAAK,GAAG,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;QAC3D,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,GAAG,EAAK,CAAC;QACjC,OAAO,GAAG,CAAC,OAAO,CAAC;IACrB,CAAC;IAEQ,KAAK,CAAC,WAAW,CAAC,KAAa,EAAE,MAAkB;QAC1D,MAAM,IAAI,GAAG,IAAI,CAAC,EAAE,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;QACpC,MAAM,KAAK,GAAG,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;QAC3D,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,GAAG,EAAE,CAAC;QAC9B,yEAAyE;QACzE,wCAAwC;QACxC,MAAM,OAAO,GAAG,GAAG,CAAC,IAAI,EAAE,OAAO,IAAI,GAAG,CAAC,KAAK,IAAI,CAAC,CAAC;QACpD,MAAM,eAAe,GAAG,GAAG,CAAC,IAAI,EAAE,WAAW,CAAC;QAC9C,OAAO,IAAI,CAAC,iBAAiB,CAAC,OAAO,EAAE,eAAe,CAAC,CAAC;IAC1D,CAAC;IAEQ,KAAK,CAAC,eAAe;QAC5B,QAAQ;IACV,CAAC;CACF"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"libsqlQuerier.d.ts","sourceRoot":"","sources":["../../src/libsql/libsqlQuerier.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAwB,MAAM,gBAAgB,CAAC;AAEnE,OAAO,EAAE,qBAAqB,EAAE,MAAM,oCAAoC,CAAC;AAE3E,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAErD,qBAAa,aAAc,SAAQ,qBAAqB;IAIpD,QAAQ,CAAC,MAAM,EAAE,MAAM;
|
|
1
|
+
{"version":3,"file":"libsqlQuerier.d.ts","sourceRoot":"","sources":["../../src/libsql/libsqlQuerier.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAwB,MAAM,gBAAgB,CAAC;AAEnE,OAAO,EAAE,qBAAqB,EAAE,MAAM,oCAAoC,CAAC;AAE3E,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAErD,qBAAa,aAAc,SAAQ,qBAAqB;IAIpD,QAAQ,CAAC,MAAM,EAAE,MAAM;aACL,KAAK,CAAC,EAAE,YAAY;IAJxC,OAAO,CAAC,EAAE,CAAC,CAAc;gBAGd,MAAM,EAAE,MAAM,EACL,KAAK,CAAC,EAAE,YAAY;IAKzB,WAAW,CAAC,CAAC,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,OAAO,EAAE;IAMhD,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,OAAO,EAAE;IAM5D,IAAa,kBAAkB,YAE9B;IAGc,gBAAgB;IAQhB,iBAAiB;IASjB,mBAAmB;IAQnB,eAAe;CAK/B"}
|
|
@@ -7,18 +7,16 @@ export class LibsqlQuerier extends AbstractSqliteQuerier {
|
|
|
7
7
|
extra;
|
|
8
8
|
tx;
|
|
9
9
|
constructor(client, extra) {
|
|
10
|
-
super(new SqliteDialect(extra?.namingStrategy));
|
|
10
|
+
super(new SqliteDialect(extra?.namingStrategy), extra);
|
|
11
11
|
this.client = client;
|
|
12
12
|
this.extra = extra;
|
|
13
13
|
}
|
|
14
14
|
async internalAll(query, values) {
|
|
15
|
-
this.extra?.logger?.(query, values);
|
|
16
15
|
const target = this.tx || this.client;
|
|
17
16
|
const res = await target.execute({ sql: query, args: values });
|
|
18
17
|
return res.rows;
|
|
19
18
|
}
|
|
20
19
|
async internalRun(query, values) {
|
|
21
|
-
this.extra?.logger?.(query, values);
|
|
22
20
|
const target = this.tx || this.client;
|
|
23
21
|
const res = await target.execute({ sql: query, args: values });
|
|
24
22
|
return this.buildUpdateResult(res.rowsAffected, res.lastInsertRowid);
|