pg-query-sdk 1.0.0
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/README.md +553 -0
- package/dist/cjs/builders/ConditionBuilder.d.ts +11 -0
- package/dist/cjs/builders/ConditionBuilder.js +43 -0
- package/dist/cjs/builders/QueryBuilder.d.ts +31 -0
- package/dist/cjs/builders/QueryBuilder.js +88 -0
- package/dist/cjs/core/Database.d.ts +20 -0
- package/dist/cjs/core/Database.js +39 -0
- package/dist/cjs/core/ParamContext.d.ts +8 -0
- package/dist/cjs/core/ParamContext.js +16 -0
- package/dist/cjs/core/QueryExecutor.d.ts +14 -0
- package/dist/cjs/core/QueryExecutor.js +39 -0
- package/dist/cjs/core/TransactionManager.d.ts +6 -0
- package/dist/cjs/core/TransactionManager.js +24 -0
- package/dist/cjs/core/UnitOfWork.d.ts +10 -0
- package/dist/cjs/core/UnitOfWork.js +27 -0
- package/dist/cjs/dialects/Dialect.d.ts +4 -0
- package/dist/cjs/dialects/Dialect.js +2 -0
- package/dist/cjs/dialects/MysqlDialect.d.ts +5 -0
- package/dist/cjs/dialects/MysqlDialect.js +11 -0
- package/dist/cjs/dialects/PostgresDialect.d.ts +5 -0
- package/dist/cjs/dialects/PostgresDialect.js +11 -0
- package/dist/cjs/index.d.ts +7 -0
- package/dist/cjs/index.js +20 -0
- package/dist/cjs/orm/EntityManager.d.ts +0 -0
- package/dist/cjs/orm/EntityManager.js +1 -0
- package/dist/cjs/orm/Repository.d.ts +13 -0
- package/dist/cjs/orm/Repository.js +30 -0
- package/dist/cjs/query/ConditionBuilder.d.ts +11 -0
- package/dist/cjs/query/ConditionBuilder.js +67 -0
- package/dist/cjs/query/QueryBuilder.d.ts +43 -0
- package/dist/cjs/query/QueryBuilder.js +152 -0
- package/dist/esm/builders/ConditionBuilder.d.ts +11 -0
- package/dist/esm/builders/ConditionBuilder.js +40 -0
- package/dist/esm/builders/QueryBuilder.d.ts +31 -0
- package/dist/esm/builders/QueryBuilder.js +82 -0
- package/dist/esm/core/Database.d.ts +20 -0
- package/dist/esm/core/Database.js +33 -0
- package/dist/esm/core/ParamContext.d.ts +8 -0
- package/dist/esm/core/ParamContext.js +13 -0
- package/dist/esm/core/QueryExecutor.d.ts +14 -0
- package/dist/esm/core/QueryExecutor.js +36 -0
- package/dist/esm/core/TransactionManager.d.ts +6 -0
- package/dist/esm/core/TransactionManager.js +21 -0
- package/dist/esm/core/UnitOfWork.d.ts +10 -0
- package/dist/esm/core/UnitOfWork.js +24 -0
- package/dist/esm/dialects/Dialect.d.ts +4 -0
- package/dist/esm/dialects/Dialect.js +1 -0
- package/dist/esm/dialects/MysqlDialect.d.ts +5 -0
- package/dist/esm/dialects/MysqlDialect.js +8 -0
- package/dist/esm/dialects/PostgresDialect.d.ts +5 -0
- package/dist/esm/dialects/PostgresDialect.js +8 -0
- package/dist/esm/index.d.ts +7 -0
- package/dist/esm/index.js +7 -0
- package/dist/esm/orm/EntityManager.d.ts +0 -0
- package/dist/esm/orm/EntityManager.js +1 -0
- package/dist/esm/orm/Repository.d.ts +13 -0
- package/dist/esm/orm/Repository.js +27 -0
- package/dist/esm/query/ConditionBuilder.d.ts +11 -0
- package/dist/esm/query/ConditionBuilder.js +64 -0
- package/dist/esm/query/QueryBuilder.d.ts +43 -0
- package/dist/esm/query/QueryBuilder.js +146 -0
- package/package.json +45 -0
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const ParamContext_1 = __importDefault(require("../core/ParamContext"));
|
|
7
|
+
const ConditionBuilder_1 = __importDefault(require("./ConditionBuilder"));
|
|
8
|
+
class QueryBuilder {
|
|
9
|
+
constructor(table, executor, dialect) {
|
|
10
|
+
this.executor = executor;
|
|
11
|
+
this.fields = [];
|
|
12
|
+
this.joins = [];
|
|
13
|
+
this.groupByFields = [];
|
|
14
|
+
this.orderByFields = [];
|
|
15
|
+
this.ctes = [];
|
|
16
|
+
this.fromClause = table;
|
|
17
|
+
this.ctx = new ParamContext_1.default(dialect);
|
|
18
|
+
this.condition = new ConditionBuilder_1.default(this.ctx);
|
|
19
|
+
this.havingCondition = new ConditionBuilder_1.default(this.ctx);
|
|
20
|
+
}
|
|
21
|
+
select(fields) {
|
|
22
|
+
this.fields = fields;
|
|
23
|
+
return this;
|
|
24
|
+
}
|
|
25
|
+
addJoin(type, table, localKey, foreignKey) {
|
|
26
|
+
this.joins.push(`${type} JOIN ${table} ON ${localKey} = ${foreignKey}`);
|
|
27
|
+
return this;
|
|
28
|
+
}
|
|
29
|
+
join(table, localKey, foreignKey) {
|
|
30
|
+
return this.addJoin('INNER', table, localKey, foreignKey);
|
|
31
|
+
}
|
|
32
|
+
leftJoin(table, localKey, foreignKey) {
|
|
33
|
+
return this.addJoin('LEFT', table, localKey, foreignKey);
|
|
34
|
+
}
|
|
35
|
+
rightJoin(table, localKey, foreignKey) {
|
|
36
|
+
return this.addJoin('RIGHT', table, localKey, foreignKey);
|
|
37
|
+
}
|
|
38
|
+
fromSubquery(sub, alias) {
|
|
39
|
+
const { query, params } = sub.build();
|
|
40
|
+
params.forEach(p => this.ctx.add(p));
|
|
41
|
+
this.fromClause = `(${query}) AS ${alias}`;
|
|
42
|
+
return this;
|
|
43
|
+
}
|
|
44
|
+
where(obj) {
|
|
45
|
+
this.condition.where(obj);
|
|
46
|
+
return this;
|
|
47
|
+
}
|
|
48
|
+
whereSub(column, operator, sub) {
|
|
49
|
+
const { query, params } = sub.build();
|
|
50
|
+
params.forEach(p => this.ctx.add(p));
|
|
51
|
+
this.condition.raw(`${column} ${operator} (${query})`);
|
|
52
|
+
return this;
|
|
53
|
+
}
|
|
54
|
+
limit(limit) {
|
|
55
|
+
this.limitCount = limit;
|
|
56
|
+
return this;
|
|
57
|
+
}
|
|
58
|
+
build() {
|
|
59
|
+
const select = this.fields.length
|
|
60
|
+
? this.fields.join(', ')
|
|
61
|
+
: '*';
|
|
62
|
+
let query = `SELECT ${select}
|
|
63
|
+
FROM ${this.fromClause}`;
|
|
64
|
+
if (this.joins.length) {
|
|
65
|
+
query += ' ' + this.joins.join(' ');
|
|
66
|
+
}
|
|
67
|
+
const whereClause = this.condition.build();
|
|
68
|
+
if (whereClause)
|
|
69
|
+
query += ' ' + whereClause;
|
|
70
|
+
if (this.limitCount) {
|
|
71
|
+
query += ` LIMIT ${this.limitCount}`;
|
|
72
|
+
}
|
|
73
|
+
return {
|
|
74
|
+
query,
|
|
75
|
+
params: this.ctx.getParams()
|
|
76
|
+
};
|
|
77
|
+
}
|
|
78
|
+
async execute() {
|
|
79
|
+
if (!this.executor) {
|
|
80
|
+
throw new Error('No QueryExecutor provided');
|
|
81
|
+
}
|
|
82
|
+
const { query, params } = this.build();
|
|
83
|
+
// @ts-ignore
|
|
84
|
+
const result = await this.executor.execute(query, params);
|
|
85
|
+
return result.rows;
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
exports.default = QueryBuilder;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { Dialect } from '../dialects/Dialect';
|
|
2
|
+
import QueryExecutor from './QueryExecutor';
|
|
3
|
+
import QueryBuilder from '../query/QueryBuilder';
|
|
4
|
+
interface DatabaseOptions {
|
|
5
|
+
connectionString: string;
|
|
6
|
+
dialect?: Dialect;
|
|
7
|
+
defaultCacheTTL?: number;
|
|
8
|
+
}
|
|
9
|
+
export default class Database {
|
|
10
|
+
private executor;
|
|
11
|
+
private dialect;
|
|
12
|
+
private transactionManager;
|
|
13
|
+
private defaultCacheTTL?;
|
|
14
|
+
constructor(options: DatabaseOptions);
|
|
15
|
+
table<T = any>(name: string): QueryBuilder<T>;
|
|
16
|
+
transaction<T>(callback: (trxDb: Database) => Promise<T>): Promise<T>;
|
|
17
|
+
setExecutor(executor: QueryExecutor): void;
|
|
18
|
+
repository<R>(RepoClass: new (executor: QueryExecutor, dialect: Dialect) => R): R;
|
|
19
|
+
}
|
|
20
|
+
export {};
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const PostgresDialect_1 = __importDefault(require("../dialects/PostgresDialect"));
|
|
7
|
+
const QueryExecutor_1 = __importDefault(require("./QueryExecutor"));
|
|
8
|
+
const QueryBuilder_1 = __importDefault(require("../query/QueryBuilder"));
|
|
9
|
+
const TransactionManager_1 = __importDefault(require("./TransactionManager"));
|
|
10
|
+
class Database {
|
|
11
|
+
constructor(options) {
|
|
12
|
+
this.dialect = options.dialect ?? new PostgresDialect_1.default();
|
|
13
|
+
this.executor = new QueryExecutor_1.default(options);
|
|
14
|
+
this.transactionManager = new TransactionManager_1.default(this.executor.getPool());
|
|
15
|
+
this.defaultCacheTTL = options.defaultCacheTTL;
|
|
16
|
+
}
|
|
17
|
+
table(name) {
|
|
18
|
+
return new QueryBuilder_1.default(name, this.executor, this.dialect, this.defaultCacheTTL);
|
|
19
|
+
}
|
|
20
|
+
async transaction(callback) {
|
|
21
|
+
return this.transactionManager.transaction(async (trxClient) => {
|
|
22
|
+
const trxExecutor = new QueryExecutor_1.default(undefined, trxClient);
|
|
23
|
+
const trxDb = new Database({
|
|
24
|
+
connectionString: '',
|
|
25
|
+
dialect: this.dialect,
|
|
26
|
+
defaultCacheTTL: this.defaultCacheTTL
|
|
27
|
+
});
|
|
28
|
+
trxDb.setExecutor(trxExecutor);
|
|
29
|
+
return callback(trxDb);
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
setExecutor(executor) {
|
|
33
|
+
this.executor = executor;
|
|
34
|
+
}
|
|
35
|
+
repository(RepoClass) {
|
|
36
|
+
return new RepoClass(this.executor, this.dialect);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
exports.default = Database;
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
class ParamContext {
|
|
4
|
+
constructor(dialect) {
|
|
5
|
+
this.dialect = dialect;
|
|
6
|
+
this.params = [];
|
|
7
|
+
}
|
|
8
|
+
add(value) {
|
|
9
|
+
this.params.push(value);
|
|
10
|
+
return this.dialect.placeholder(this.params.length);
|
|
11
|
+
}
|
|
12
|
+
getParams() {
|
|
13
|
+
return this.params;
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
exports.default = ParamContext;
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { Pool, PoolClient, QueryResult } from 'pg';
|
|
2
|
+
interface ExecutorOptions {
|
|
3
|
+
connectionString: string;
|
|
4
|
+
}
|
|
5
|
+
export default class QueryExecutor {
|
|
6
|
+
private pool?;
|
|
7
|
+
private client?;
|
|
8
|
+
constructor(options?: ExecutorOptions, client?: PoolClient);
|
|
9
|
+
execute(query: string, params: any[] | undefined, cacheTTL: number | undefined): Promise<QueryResult>;
|
|
10
|
+
getPool(): Pool | undefined;
|
|
11
|
+
getClient(): PoolClient | undefined;
|
|
12
|
+
close(): Promise<void>;
|
|
13
|
+
}
|
|
14
|
+
export {};
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const pg_1 = require("pg");
|
|
4
|
+
class QueryExecutor {
|
|
5
|
+
constructor(options, client) {
|
|
6
|
+
if (client) {
|
|
7
|
+
this.client = client;
|
|
8
|
+
return;
|
|
9
|
+
}
|
|
10
|
+
if (options?.connectionString) {
|
|
11
|
+
this.pool = new pg_1.Pool({
|
|
12
|
+
connectionString: options.connectionString
|
|
13
|
+
});
|
|
14
|
+
return;
|
|
15
|
+
}
|
|
16
|
+
throw new Error('Invalid QueryExecutor initialization');
|
|
17
|
+
}
|
|
18
|
+
async execute(query, params = [], cacheTTL) {
|
|
19
|
+
if (this.client) {
|
|
20
|
+
return this.client.query(query, params);
|
|
21
|
+
}
|
|
22
|
+
if (this.pool) {
|
|
23
|
+
return this.pool.query(query, params);
|
|
24
|
+
}
|
|
25
|
+
throw new Error('Executor not initialized');
|
|
26
|
+
}
|
|
27
|
+
getPool() {
|
|
28
|
+
return this.pool;
|
|
29
|
+
}
|
|
30
|
+
getClient() {
|
|
31
|
+
return this.client;
|
|
32
|
+
}
|
|
33
|
+
async close() {
|
|
34
|
+
if (this.pool) {
|
|
35
|
+
await this.pool.end();
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
exports.default = QueryExecutor;
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
class TransactionManager {
|
|
4
|
+
constructor(pool) {
|
|
5
|
+
this.pool = pool;
|
|
6
|
+
}
|
|
7
|
+
async transaction(callback) {
|
|
8
|
+
const client = await this.pool.connect();
|
|
9
|
+
try {
|
|
10
|
+
await client.query('BEGIN');
|
|
11
|
+
const result = await callback(client);
|
|
12
|
+
await client.query('COMMIT');
|
|
13
|
+
return result;
|
|
14
|
+
}
|
|
15
|
+
catch (error) {
|
|
16
|
+
await client.query('ROLLBACK');
|
|
17
|
+
throw error;
|
|
18
|
+
}
|
|
19
|
+
finally {
|
|
20
|
+
client.release();
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
exports.default = TransactionManager;
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import Repository from "../orm/Repository";
|
|
2
|
+
export default class UnitOfWork {
|
|
3
|
+
private newEntities;
|
|
4
|
+
private dirtyEntities;
|
|
5
|
+
private removedEntities;
|
|
6
|
+
registerNew(entity: any): void;
|
|
7
|
+
registerDirty(entity: any): void;
|
|
8
|
+
registerRemoved(entity: any): void;
|
|
9
|
+
commit(repository: Repository<any>): Promise<void>;
|
|
10
|
+
}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
class UnitOfWork {
|
|
4
|
+
constructor() {
|
|
5
|
+
this.newEntities = [];
|
|
6
|
+
this.dirtyEntities = [];
|
|
7
|
+
this.removedEntities = [];
|
|
8
|
+
}
|
|
9
|
+
registerNew(entity) {
|
|
10
|
+
this.newEntities.push(entity);
|
|
11
|
+
}
|
|
12
|
+
registerDirty(entity) {
|
|
13
|
+
this.dirtyEntities.push(entity);
|
|
14
|
+
}
|
|
15
|
+
registerRemoved(entity) {
|
|
16
|
+
this.removedEntities.push(entity);
|
|
17
|
+
}
|
|
18
|
+
async commit(repository) {
|
|
19
|
+
for (const e of this.newEntities)
|
|
20
|
+
await repository.insert(e);
|
|
21
|
+
for (const e of this.dirtyEntities)
|
|
22
|
+
await repository.update(e);
|
|
23
|
+
for (const e of this.removedEntities)
|
|
24
|
+
await repository.delete(e);
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
exports.default = UnitOfWork;
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
export { default as QueryExecutor } from './core/QueryExecutor';
|
|
2
|
+
export { default as QueryBuilder } from './builders/QueryBuilder';
|
|
3
|
+
export { default as ConditionBuilder } from './builders/ConditionBuilder';
|
|
4
|
+
export { default as Database } from './core/Database';
|
|
5
|
+
export { default as TransactionManager } from './core/TransactionManager';
|
|
6
|
+
export { default as PostgresDialect } from './dialects/PostgresDialect';
|
|
7
|
+
export { default as Repository } from './orm/Repository';
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.Repository = exports.PostgresDialect = exports.TransactionManager = exports.Database = exports.ConditionBuilder = exports.QueryBuilder = exports.QueryExecutor = void 0;
|
|
7
|
+
var QueryExecutor_1 = require("./core/QueryExecutor");
|
|
8
|
+
Object.defineProperty(exports, "QueryExecutor", { enumerable: true, get: function () { return __importDefault(QueryExecutor_1).default; } });
|
|
9
|
+
var QueryBuilder_1 = require("./builders/QueryBuilder");
|
|
10
|
+
Object.defineProperty(exports, "QueryBuilder", { enumerable: true, get: function () { return __importDefault(QueryBuilder_1).default; } });
|
|
11
|
+
var ConditionBuilder_1 = require("./builders/ConditionBuilder");
|
|
12
|
+
Object.defineProperty(exports, "ConditionBuilder", { enumerable: true, get: function () { return __importDefault(ConditionBuilder_1).default; } });
|
|
13
|
+
var Database_1 = require("./core/Database");
|
|
14
|
+
Object.defineProperty(exports, "Database", { enumerable: true, get: function () { return __importDefault(Database_1).default; } });
|
|
15
|
+
var TransactionManager_1 = require("./core/TransactionManager");
|
|
16
|
+
Object.defineProperty(exports, "TransactionManager", { enumerable: true, get: function () { return __importDefault(TransactionManager_1).default; } });
|
|
17
|
+
var PostgresDialect_1 = require("./dialects/PostgresDialect");
|
|
18
|
+
Object.defineProperty(exports, "PostgresDialect", { enumerable: true, get: function () { return __importDefault(PostgresDialect_1).default; } });
|
|
19
|
+
var Repository_1 = require("./orm/Repository");
|
|
20
|
+
Object.defineProperty(exports, "Repository", { enumerable: true, get: function () { return __importDefault(Repository_1).default; } });
|
|
File without changes
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { QueryBuilder, QueryExecutor } from "../index";
|
|
2
|
+
import { Dialect } from "../dialects/Dialect";
|
|
3
|
+
export default abstract class Repository<T> {
|
|
4
|
+
protected table: string;
|
|
5
|
+
protected executor: QueryExecutor;
|
|
6
|
+
protected dialect: Dialect;
|
|
7
|
+
constructor(table: string, executor: QueryExecutor, dialect: Dialect);
|
|
8
|
+
qb(): QueryBuilder<T>;
|
|
9
|
+
findById(id: number): Promise<T | null>;
|
|
10
|
+
insert(data: Partial<T>): Promise<void>;
|
|
11
|
+
update(data: Partial<T>): Promise<void>;
|
|
12
|
+
delete(data: Partial<T>): Promise<void>;
|
|
13
|
+
}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const index_1 = require("../index");
|
|
4
|
+
class Repository {
|
|
5
|
+
constructor(table, executor, dialect) {
|
|
6
|
+
this.table = table;
|
|
7
|
+
this.executor = executor;
|
|
8
|
+
this.dialect = dialect;
|
|
9
|
+
}
|
|
10
|
+
qb() {
|
|
11
|
+
return new index_1.QueryBuilder(this.table, this.executor, this.dialect);
|
|
12
|
+
}
|
|
13
|
+
async findById(id) {
|
|
14
|
+
const rows = await this.qb()
|
|
15
|
+
.where({ id })
|
|
16
|
+
.limit(1)
|
|
17
|
+
.execute();
|
|
18
|
+
return rows[0] ?? null;
|
|
19
|
+
}
|
|
20
|
+
async insert(data) {
|
|
21
|
+
// implementação insert segura
|
|
22
|
+
}
|
|
23
|
+
async update(data) {
|
|
24
|
+
// implementação update segura
|
|
25
|
+
}
|
|
26
|
+
async delete(data) {
|
|
27
|
+
// soft delete opcional
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
exports.default = Repository;
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import ParamContext from '../core/ParamContext';
|
|
2
|
+
export default class ConditionBuilder {
|
|
3
|
+
private ctx;
|
|
4
|
+
private parts;
|
|
5
|
+
constructor(ctx: ParamContext);
|
|
6
|
+
where(obj: Record<string, any>): this;
|
|
7
|
+
raw(expression: string): this;
|
|
8
|
+
andGroup(cb: (qb: ConditionBuilder) => void): this;
|
|
9
|
+
orGroup(cb: (qb: ConditionBuilder) => void): this;
|
|
10
|
+
build(prefix?: string): string;
|
|
11
|
+
}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
class ConditionBuilder {
|
|
4
|
+
constructor(ctx) {
|
|
5
|
+
this.ctx = ctx;
|
|
6
|
+
this.parts = [];
|
|
7
|
+
}
|
|
8
|
+
where(obj) {
|
|
9
|
+
Object.entries(obj).forEach(([key, value]) => {
|
|
10
|
+
if (value === null) {
|
|
11
|
+
this.parts.push(`${key} IS NULL`);
|
|
12
|
+
return;
|
|
13
|
+
}
|
|
14
|
+
if (typeof value === 'object' && value !== null && 'op' in value) {
|
|
15
|
+
const { op, value: v } = value;
|
|
16
|
+
const placeholder = this.ctx.add(v);
|
|
17
|
+
this.parts.push(`${key} ${op} ${placeholder}`);
|
|
18
|
+
return;
|
|
19
|
+
}
|
|
20
|
+
const placeholder = this.ctx.add(value);
|
|
21
|
+
this.parts.push(`${key} = ${placeholder}`);
|
|
22
|
+
});
|
|
23
|
+
return this;
|
|
24
|
+
}
|
|
25
|
+
raw(expression) {
|
|
26
|
+
this.parts.push(expression);
|
|
27
|
+
return this;
|
|
28
|
+
}
|
|
29
|
+
andGroup(cb) {
|
|
30
|
+
const nested = new ConditionBuilder(this.ctx);
|
|
31
|
+
cb(nested);
|
|
32
|
+
const built = nested.build();
|
|
33
|
+
if (built) {
|
|
34
|
+
this.parts.push(`(${built.replace(/^WHERE\s/, '')})`);
|
|
35
|
+
}
|
|
36
|
+
return this;
|
|
37
|
+
}
|
|
38
|
+
orGroup(cb) {
|
|
39
|
+
const nested = new ConditionBuilder(this.ctx);
|
|
40
|
+
cb(nested);
|
|
41
|
+
const built = nested.build();
|
|
42
|
+
if (built) {
|
|
43
|
+
const clean = built.replace(/^WHERE\s/, '');
|
|
44
|
+
this.parts.push(`OR (${clean})`);
|
|
45
|
+
}
|
|
46
|
+
return this;
|
|
47
|
+
}
|
|
48
|
+
build(prefix = 'WHERE') {
|
|
49
|
+
if (!this.parts.length)
|
|
50
|
+
return '';
|
|
51
|
+
const normalized = [];
|
|
52
|
+
this.parts.forEach((part, index) => {
|
|
53
|
+
if (index === 0) {
|
|
54
|
+
normalized.push(part);
|
|
55
|
+
return;
|
|
56
|
+
}
|
|
57
|
+
if (part.startsWith('OR ')) {
|
|
58
|
+
normalized.push(part);
|
|
59
|
+
}
|
|
60
|
+
else {
|
|
61
|
+
normalized.push(`AND ${part}`);
|
|
62
|
+
}
|
|
63
|
+
});
|
|
64
|
+
return `${prefix} ${normalized.join(' ')}`;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
exports.default = ConditionBuilder;
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import ConditionBuilder from './ConditionBuilder';
|
|
2
|
+
import QueryExecutor from '../core/QueryExecutor';
|
|
3
|
+
import { Dialect } from '../dialects/Dialect';
|
|
4
|
+
export default class QueryBuilder<T = any> {
|
|
5
|
+
private executor;
|
|
6
|
+
private dialect;
|
|
7
|
+
private cacheTTL?;
|
|
8
|
+
private fields;
|
|
9
|
+
private joins;
|
|
10
|
+
private groupByFields;
|
|
11
|
+
private orderByFields;
|
|
12
|
+
private limitCount?;
|
|
13
|
+
private offsetCount?;
|
|
14
|
+
private ctes;
|
|
15
|
+
private fromClause;
|
|
16
|
+
private ctx;
|
|
17
|
+
private condition;
|
|
18
|
+
private havingCondition;
|
|
19
|
+
constructor(table: string, executor: QueryExecutor, dialect: Dialect, cacheTTL?: number | 0 | undefined);
|
|
20
|
+
select(fields: (keyof T | string)[]): this;
|
|
21
|
+
private addJoin;
|
|
22
|
+
join(table: string, localKey: string, foreignKey: string): this;
|
|
23
|
+
leftJoin(table: string, localKey: string, foreignKey: string): this;
|
|
24
|
+
rightJoin(table: string, localKey: string, foreignKey: string): this;
|
|
25
|
+
where(obj: Partial<T>): this;
|
|
26
|
+
whereRaw(expression: string): this;
|
|
27
|
+
andGroup(cb: (qb: ConditionBuilder) => void): this;
|
|
28
|
+
orGroup(cb: (qb: ConditionBuilder) => void): this;
|
|
29
|
+
groupBy(fields: string | string[]): this;
|
|
30
|
+
having(obj: Record<string, any>): this;
|
|
31
|
+
havingRaw(expr: string): this;
|
|
32
|
+
orderBy(column: string, direction?: 'ASC' | 'DESC'): this;
|
|
33
|
+
limit(value: number): this;
|
|
34
|
+
offset(value: number): this;
|
|
35
|
+
with(name: string, subQuery: QueryBuilder<any>, recursive?: boolean): this;
|
|
36
|
+
fromSubquery(sub: QueryBuilder<any>, alias: string): this;
|
|
37
|
+
clone(): QueryBuilder<T>;
|
|
38
|
+
build(): {
|
|
39
|
+
query: string;
|
|
40
|
+
params: any[];
|
|
41
|
+
};
|
|
42
|
+
execute(): Promise<T[]>;
|
|
43
|
+
}
|