Update to NPM version
This commit is contained in:
21
ProjectSourceCode/node_modules/pg-promise/LICENSE
generated
vendored
Normal file
21
ProjectSourceCode/node_modules/pg-promise/LICENSE
generated
vendored
Normal file
@@ -0,0 +1,21 @@
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2015-2018 Vitaly Tomilov
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
1136
ProjectSourceCode/node_modules/pg-promise/README.md
generated
vendored
Normal file
1136
ProjectSourceCode/node_modules/pg-promise/README.md
generated
vendored
Normal file
File diff suppressed because it is too large
Load Diff
10
ProjectSourceCode/node_modules/pg-promise/lib/assert.js
generated
vendored
Normal file
10
ProjectSourceCode/node_modules/pg-promise/lib/assert.js
generated
vendored
Normal file
@@ -0,0 +1,10 @@
|
||||
const {assertOptions} = require(`assert-options`);
|
||||
|
||||
// this to allow override options-related errors globally (for pg-promise)
|
||||
global.pgPromiseAssert = assertOptions;
|
||||
|
||||
module.exports = {
|
||||
assert() {
|
||||
return global.pgPromiseAssert.apply(null, [...arguments]);
|
||||
}
|
||||
};
|
||||
178
ProjectSourceCode/node_modules/pg-promise/lib/connect.js
generated
vendored
Normal file
178
ProjectSourceCode/node_modules/pg-promise/lib/connect.js
generated
vendored
Normal file
@@ -0,0 +1,178 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {Events} = require(`./events`);
|
||||
const {ColorConsole} = require(`./utils/color`);
|
||||
|
||||
const npm = {
|
||||
utils: require(`./utils`),
|
||||
text: require(`./text`),
|
||||
formatting: require(`./formatting`)
|
||||
};
|
||||
|
||||
function poolConnect(ctx, db, config) {
|
||||
return config.promise((resolve, reject) => {
|
||||
const p = db.$pool;
|
||||
if (p.ending) {
|
||||
db.$destroy();
|
||||
const err = new Error(npm.text.poolDestroyed);
|
||||
Events.error(ctx.options, err, {
|
||||
dc: ctx.dc
|
||||
});
|
||||
reject(err);
|
||||
return;
|
||||
}
|
||||
p.connect((err, client) => {
|
||||
if (err) {
|
||||
Events.error(ctx.options, err, {
|
||||
cn: npm.utils.getSafeConnection(ctx.cn),
|
||||
dc: ctx.dc
|
||||
});
|
||||
reject(err);
|
||||
} else {
|
||||
if (`$useCount` in client) {
|
||||
// Make sure useCount drops to 1, if it ever reaches maximum integer number;
|
||||
// We do not drop it to zero, to avoid rerun of initialization queries that
|
||||
// usually check for useCount === 0;
|
||||
// istanbul ignore if
|
||||
if (client.$useCount >= Number.MAX_SAFE_INTEGER) {
|
||||
client.$useCount = 1; // resetting; cannot auto-test this
|
||||
} else {
|
||||
client.$useCount = ++client.$useCount;
|
||||
}
|
||||
} else {
|
||||
Object.defineProperty(client, `$useCount`, {
|
||||
value: 0,
|
||||
configurable: false,
|
||||
enumerable: false,
|
||||
writable: true
|
||||
});
|
||||
setSchema(client, ctx);
|
||||
}
|
||||
setCtx(client, ctx);
|
||||
const end = lockClientEnd(client);
|
||||
client.on(`error`, onError);
|
||||
resolve({
|
||||
client,
|
||||
useCount: client.$useCount,
|
||||
release(kill) {
|
||||
client.end = end;
|
||||
client.release(kill || client.$connectionError);
|
||||
Events.disconnect(ctx, client);
|
||||
client.removeListener(`error`, onError);
|
||||
}
|
||||
});
|
||||
Events.connect(ctx, client, client.$useCount);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function directConnect(ctx, config) {
|
||||
return config.promise((resolve, reject) => {
|
||||
const client = new config.pgp.pg.Client(ctx.cn);
|
||||
client.connect(err => {
|
||||
if (err) {
|
||||
Events.error(ctx.options, err, {
|
||||
cn: npm.utils.getSafeConnection(ctx.cn),
|
||||
dc: ctx.dc
|
||||
});
|
||||
reject(err);
|
||||
} else {
|
||||
setSchema(client, ctx);
|
||||
setCtx(client, ctx);
|
||||
const end = lockClientEnd(client);
|
||||
client.on(`error`, onError);
|
||||
resolve({
|
||||
client,
|
||||
useCount: 0,
|
||||
release() {
|
||||
client.end = end;
|
||||
const p = config.promise((res, rej) => client.end().then(res).catch(rej));
|
||||
Events.disconnect(ctx, client);
|
||||
client.removeListener(`error`, onError);
|
||||
return p;
|
||||
}
|
||||
});
|
||||
Events.connect(ctx, client, 0);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
// this event only happens when the connection is lost physically,
|
||||
// which cannot be tested automatically; removing from coverage:
|
||||
// istanbul ignore next
|
||||
function onError(err) {
|
||||
const ctx = this.$ctx;
|
||||
const cn = npm.utils.getSafeConnection(ctx.cn);
|
||||
Events.error(ctx.options, err, {cn, dc: ctx.dc});
|
||||
if (ctx.cnOptions && typeof ctx.cnOptions.onLost === `function` && !ctx.notified) {
|
||||
try {
|
||||
ctx.cnOptions.onLost.call(this, err, {
|
||||
cn,
|
||||
dc: ctx.dc,
|
||||
start: ctx.start,
|
||||
client: this
|
||||
});
|
||||
} catch (e) {
|
||||
ColorConsole.error(e && e.stack || e);
|
||||
}
|
||||
ctx.notified = true;
|
||||
}
|
||||
}
|
||||
|
||||
function lockClientEnd(client) {
|
||||
const end = client.end;
|
||||
client.end = doNotCall => {
|
||||
// This call can happen only in the following two cases:
|
||||
// 1. the client made the call directly, against the library's documentation (invalid code)
|
||||
// 2. connection with the server broke, and the pool is terminating all clients forcefully.
|
||||
ColorConsole.error(`${npm.text.clientEnd}\n${npm.utils.getLocalStack(1, 3)}\n`);
|
||||
if (!doNotCall) {
|
||||
end.call(client);
|
||||
}
|
||||
};
|
||||
return end;
|
||||
}
|
||||
|
||||
function setCtx(client, ctx) {
|
||||
Object.defineProperty(client, `$ctx`, {
|
||||
value: ctx,
|
||||
writable: true
|
||||
});
|
||||
}
|
||||
|
||||
function setSchema(client, ctx) {
|
||||
let s = ctx.options.schema;
|
||||
if (!s) {
|
||||
return;
|
||||
}
|
||||
if (typeof s === `function`) {
|
||||
s = s.call(ctx.dc, ctx.dc);
|
||||
}
|
||||
if (Array.isArray(s)) {
|
||||
s = s.filter(a => a && typeof a === `string`);
|
||||
}
|
||||
if (typeof s === `string` || (Array.isArray(s) && s.length)) {
|
||||
client.query(npm.formatting.as.format(`SET search_path TO $1:name`, [s]), err => {
|
||||
// istanbul ignore if;
|
||||
if (err) {
|
||||
// This is unlikely to ever happen, unless the connection is created faulty,
|
||||
// and fails on the very first query, which is impossible to test automatically.
|
||||
throw err;
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = config => ({
|
||||
pool: (ctx, db) => poolConnect(ctx, db, config),
|
||||
direct: ctx => directConnect(ctx, config)
|
||||
});
|
||||
93
ProjectSourceCode/node_modules/pg-promise/lib/context.js
generated
vendored
Normal file
93
ProjectSourceCode/node_modules/pg-promise/lib/context.js
generated
vendored
Normal file
@@ -0,0 +1,93 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @class ConnectionContext
|
||||
* @private
|
||||
* @summary Internal connection context.
|
||||
*
|
||||
* @param {object} cc
|
||||
* Connection Context.
|
||||
*
|
||||
* @param {object} cc.cn
|
||||
* Connection details
|
||||
*
|
||||
* @param {*} cc.dc
|
||||
* Database Context
|
||||
*
|
||||
* @param {object} cc.options
|
||||
* Library's Initialization Options
|
||||
*
|
||||
* @param {object} cc.db
|
||||
* Database Session we're attached to, if any.
|
||||
*
|
||||
* @param {number} cc.level
|
||||
* Task Level
|
||||
*
|
||||
* @param {number} cc.txLevel
|
||||
* Transaction Level
|
||||
*
|
||||
* @param {object} cc.parentCtx
|
||||
* Connection Context of the parent operation, if any.
|
||||
*
|
||||
*/
|
||||
class ConnectionContext {
|
||||
|
||||
constructor(cc) {
|
||||
this.cn = cc.cn; // connection details;
|
||||
this.dc = cc.dc; // database context;
|
||||
this.options = cc.options; // library options;
|
||||
this.db = cc.db; // database session;
|
||||
this.level = cc.level; // task level;
|
||||
this.txLevel = cc.txLevel; // transaction level;
|
||||
this.parentCtx = null; // parent context
|
||||
this.taskCtx = null; // task context
|
||||
this.start = null; // Date/Time when connected
|
||||
this.txCount = 0;
|
||||
}
|
||||
|
||||
connect(db) {
|
||||
this.db = db;
|
||||
this.start = new Date();
|
||||
}
|
||||
|
||||
disconnect(kill) {
|
||||
if (this.db) {
|
||||
const p = this.db.release(kill);
|
||||
this.db = null;
|
||||
return p;
|
||||
}
|
||||
}
|
||||
|
||||
clone() {
|
||||
const obj = new ConnectionContext(this);
|
||||
obj.parent = this;
|
||||
obj.parentCtx = this.taskCtx;
|
||||
return obj;
|
||||
}
|
||||
|
||||
get nextTxCount() {
|
||||
let txCurrent = this, txTop = this;
|
||||
while (txCurrent.parent) {
|
||||
txCurrent = txCurrent.parent;
|
||||
if (txCurrent.taskCtx && txCurrent.taskCtx.isTX) {
|
||||
txTop = txCurrent;
|
||||
}
|
||||
}
|
||||
return txTop.txCount++;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Connection Context
|
||||
* @module context
|
||||
* @author Vitaly Tomilov
|
||||
* @private
|
||||
*/
|
||||
module.exports = {ConnectionContext};
|
||||
115
ProjectSourceCode/node_modules/pg-promise/lib/database-pool.js
generated
vendored
Normal file
115
ProjectSourceCode/node_modules/pg-promise/lib/database-pool.js
generated
vendored
Normal file
@@ -0,0 +1,115 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {ColorConsole} = require(`./utils/color`);
|
||||
|
||||
const npm = {
|
||||
utils: require(`./utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @class DatabasePool
|
||||
* @static
|
||||
* @private
|
||||
*/
|
||||
class DatabasePool {
|
||||
|
||||
/**
|
||||
* Global instance of the database pool repository.
|
||||
*
|
||||
* @returns {{dbMap: {}, dbs: Array}}
|
||||
*/
|
||||
static get instance() {
|
||||
const s = Symbol.for(`pgPromiseDatabasePool`);
|
||||
let scope = global[s];
|
||||
if (!scope) {
|
||||
scope = {
|
||||
dbMap: {}, // map of used database context keys (connection + dc)
|
||||
dbs: [] // all database objects
|
||||
};
|
||||
global[s] = scope;
|
||||
}
|
||||
return scope;
|
||||
}
|
||||
|
||||
/**
|
||||
* @method DatabasePool.register
|
||||
* @static
|
||||
* @description
|
||||
* - Registers each database object, to make sure no duplicates connections are used,
|
||||
* and if they are, produce a warning;
|
||||
* - Registers each Pool object, to be able to release them all when requested.
|
||||
*
|
||||
* @param {Database} db - The new Database object being registered.
|
||||
*/
|
||||
static register(db) {
|
||||
const cnKey = DatabasePool.createContextKey(db);
|
||||
npm.utils.addReadProp(db, `$cnKey`, cnKey, true);
|
||||
const {dbMap, dbs} = DatabasePool.instance;
|
||||
if (cnKey in dbMap) {
|
||||
dbMap[cnKey]++;
|
||||
/* istanbul ignore if */
|
||||
if (!db.$config.options.noWarnings) {
|
||||
ColorConsole.warn(`WARNING: Creating a duplicate database object for the same connection.\n${npm.utils.getLocalStack(4, 3)}\n`);
|
||||
}
|
||||
} else {
|
||||
dbMap[cnKey] = 1;
|
||||
}
|
||||
dbs.push(db);
|
||||
}
|
||||
|
||||
/**
|
||||
* @method DatabasePool.unregister
|
||||
* @static
|
||||
* @param db
|
||||
*/
|
||||
static unregister(db) {
|
||||
const cnKey = db.$cnKey;
|
||||
const {dbMap} = DatabasePool.instance;
|
||||
if (!--dbMap[cnKey]) {
|
||||
delete dbMap[cnKey];
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @method DatabasePool.shutDown
|
||||
* @static
|
||||
*/
|
||||
static shutDown() {
|
||||
const {instance} = DatabasePool;
|
||||
instance.dbs.forEach(db => {
|
||||
db.$destroy();
|
||||
});
|
||||
instance.dbs.length = 0;
|
||||
instance.dbMap = {};
|
||||
}
|
||||
|
||||
/**
|
||||
* @method DatabasePool.createContextKey
|
||||
* @static
|
||||
* @description
|
||||
* For connections that are objects it reorders the keys alphabetically,
|
||||
* and then serializes the result into a JSON string.
|
||||
*
|
||||
* @param {Database} db - Database instance.
|
||||
*/
|
||||
static createContextKey(db) {
|
||||
let cn = db.$cn;
|
||||
if (typeof cn === `object`) {
|
||||
const obj = {}, keys = Object.keys(cn).sort();
|
||||
keys.forEach(name => {
|
||||
obj[name] = cn[name];
|
||||
});
|
||||
cn = obj;
|
||||
}
|
||||
return npm.utils.toJson(npm.utils.getSafeConnection(cn)) + npm.utils.toJson(db.$dc);
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {DatabasePool};
|
||||
1691
ProjectSourceCode/node_modules/pg-promise/lib/database.js
generated
vendored
Normal file
1691
ProjectSourceCode/node_modules/pg-promise/lib/database.js
generated
vendored
Normal file
File diff suppressed because it is too large
Load Diff
13
ProjectSourceCode/node_modules/pg-promise/lib/errors/README.md
generated
vendored
Normal file
13
ProjectSourceCode/node_modules/pg-promise/lib/errors/README.md
generated
vendored
Normal file
@@ -0,0 +1,13 @@
|
||||
### `errors` namespace
|
||||
|
||||
This folder contains everything that's available via the [errors] namespace, before and after initialization:
|
||||
|
||||
```js
|
||||
const pgpLib = require('pg-promise');
|
||||
const pgp = pgpLib(/*initialization options*/);
|
||||
|
||||
pgpLib.errors; // `errors` namespace
|
||||
pgp.errors; // `errors` namespace
|
||||
```
|
||||
|
||||
[errors]:http://vitaly-t.github.io/pg-promise/errors.html
|
||||
51
ProjectSourceCode/node_modules/pg-promise/lib/errors/index.js
generated
vendored
Normal file
51
ProjectSourceCode/node_modules/pg-promise/lib/errors/index.js
generated
vendored
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {QueryResultError, queryResultErrorCode} = require(`./query-result-error`);
|
||||
const {PreparedStatementError} = require(`./prepared-statement-error`);
|
||||
const {ParameterizedQueryError} = require(`./parameterized-query-error`);
|
||||
const {QueryFileError} = require(`./query-file-error`);
|
||||
|
||||
/**
|
||||
* @namespace errors
|
||||
* @description
|
||||
* Error types namespace, available as `pgp.errors`, before and after initializing the library.
|
||||
*
|
||||
* @property {function} PreparedStatementError
|
||||
* {@link errors.PreparedStatementError PreparedStatementError} class constructor.
|
||||
*
|
||||
* Represents all errors that can be reported by class {@link PreparedStatement}.
|
||||
*
|
||||
* @property {function} ParameterizedQueryError
|
||||
* {@link errors.ParameterizedQueryError ParameterizedQueryError} class constructor.
|
||||
*
|
||||
* Represents all errors that can be reported by class {@link ParameterizedQuery}.
|
||||
*
|
||||
* @property {function} QueryFileError
|
||||
* {@link errors.QueryFileError QueryFileError} class constructor.
|
||||
*
|
||||
* Represents all errors that can be reported by class {@link QueryFile}.
|
||||
*
|
||||
* @property {function} QueryResultError
|
||||
* {@link errors.QueryResultError QueryResultError} class constructor.
|
||||
*
|
||||
* Represents all result-specific errors from query methods.
|
||||
*
|
||||
* @property {errors.queryResultErrorCode} queryResultErrorCode
|
||||
* Error codes `enum` used by class {@link errors.QueryResultError QueryResultError}.
|
||||
*
|
||||
*/
|
||||
|
||||
module.exports = {
|
||||
QueryResultError,
|
||||
queryResultErrorCode,
|
||||
PreparedStatementError,
|
||||
ParameterizedQueryError,
|
||||
QueryFileError
|
||||
};
|
||||
95
ProjectSourceCode/node_modules/pg-promise/lib/errors/parameterized-query-error.js
generated
vendored
Normal file
95
ProjectSourceCode/node_modules/pg-promise/lib/errors/parameterized-query-error.js
generated
vendored
Normal file
@@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {QueryFileError} = require(`./query-file-error`);
|
||||
|
||||
const npm = {
|
||||
os: require(`os`),
|
||||
utils: require(`../utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @class errors.ParameterizedQueryError
|
||||
* @augments external:Error
|
||||
* @description
|
||||
* {@link errors.ParameterizedQueryError ParameterizedQueryError} class, available from the {@link errors} namespace.
|
||||
*
|
||||
* This type represents all errors that can be reported by class {@link ParameterizedQuery}, whether it is used
|
||||
* explicitly or implicitly (via a simple `{text, values}` object).
|
||||
*
|
||||
* @property {string} name
|
||||
* Standard {@link external:Error Error} property - error type name = `ParameterizedQueryError`.
|
||||
*
|
||||
* @property {string} message
|
||||
* Standard {@link external:Error Error} property - the error message.
|
||||
*
|
||||
* @property {string} stack
|
||||
* Standard {@link external:Error Error} property - the stack trace.
|
||||
*
|
||||
* @property {errors.QueryFileError} error
|
||||
* Internal {@link errors.QueryFileError} object.
|
||||
*
|
||||
* It is set only when the source {@link ParameterizedQuery} used a {@link QueryFile} which threw the error.
|
||||
*
|
||||
* @property {object} result
|
||||
* Resulting Parameterized Query object.
|
||||
*
|
||||
* @see ParameterizedQuery
|
||||
*/
|
||||
class ParameterizedQueryError extends Error {
|
||||
constructor(error, pq) {
|
||||
const isQueryFileError = error instanceof QueryFileError;
|
||||
const message = isQueryFileError ? `Failed to initialize 'text' from a QueryFile.` : error;
|
||||
super(message);
|
||||
this.name = this.constructor.name;
|
||||
if (isQueryFileError) {
|
||||
this.error = error;
|
||||
}
|
||||
this.result = pq;
|
||||
Error.captureStackTrace(this, this.constructor);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @method errors.ParameterizedQueryError#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the error.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
ParameterizedQueryError.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap0 = npm.utils.messageGap(level),
|
||||
gap1 = npm.utils.messageGap(level + 1),
|
||||
gap2 = npm.utils.messageGap(level + 2),
|
||||
lines = [
|
||||
`ParameterizedQueryError {`,
|
||||
gap1 + `message: "` + this.message + `"`,
|
||||
gap1 + `result: {`,
|
||||
gap2 + `text: ` + npm.utils.toJson(this.result.text),
|
||||
gap2 + `values: ` + npm.utils.toJson(this.result.values),
|
||||
gap1 + `}`
|
||||
];
|
||||
if (this.error) {
|
||||
lines.push(gap1 + `error: ` + this.error.toString(level + 1));
|
||||
}
|
||||
lines.push(gap0 + `}`);
|
||||
return lines.join(npm.os.EOL);
|
||||
};
|
||||
|
||||
npm.utils.addInspection(ParameterizedQueryError, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
module.exports = {ParameterizedQueryError};
|
||||
96
ProjectSourceCode/node_modules/pg-promise/lib/errors/prepared-statement-error.js
generated
vendored
Normal file
96
ProjectSourceCode/node_modules/pg-promise/lib/errors/prepared-statement-error.js
generated
vendored
Normal file
@@ -0,0 +1,96 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {QueryFileError} = require(`./query-file-error`);
|
||||
|
||||
const npm = {
|
||||
os: require(`os`),
|
||||
utils: require(`../utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @class errors.PreparedStatementError
|
||||
* @augments external:Error
|
||||
* @description
|
||||
* {@link errors.PreparedStatementError PreparedStatementError} class, available from the {@link errors} namespace.
|
||||
*
|
||||
* This type represents all errors that can be reported by class {@link PreparedStatement}, whether it is used
|
||||
* explicitly or implicitly (via a simple `{name, text, values}` object).
|
||||
*
|
||||
* @property {string} name
|
||||
* Standard {@link external:Error Error} property - error type name = `PreparedStatementError`.
|
||||
*
|
||||
* @property {string} message
|
||||
* Standard {@link external:Error Error} property - the error message.
|
||||
*
|
||||
* @property {string} stack
|
||||
* Standard {@link external:Error Error} property - the stack trace.
|
||||
*
|
||||
* @property {errors.QueryFileError} error
|
||||
* Internal {@link errors.QueryFileError} object.
|
||||
*
|
||||
* It is set only when the source {@link PreparedStatement} used a {@link QueryFile} which threw the error.
|
||||
*
|
||||
* @property {object} result
|
||||
* Resulting Prepared Statement object.
|
||||
*
|
||||
* @see PreparedStatement
|
||||
*/
|
||||
class PreparedStatementError extends Error {
|
||||
constructor(error, ps) {
|
||||
const isQueryFileError = error instanceof QueryFileError;
|
||||
const message = isQueryFileError ? `Failed to initialize 'text' from a QueryFile.` : error;
|
||||
super(message);
|
||||
this.name = this.constructor.name;
|
||||
if (isQueryFileError) {
|
||||
this.error = error;
|
||||
}
|
||||
this.result = ps;
|
||||
Error.captureStackTrace(this, this.constructor);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @method errors.PreparedStatementError#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the error.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
PreparedStatementError.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap0 = npm.utils.messageGap(level),
|
||||
gap1 = npm.utils.messageGap(level + 1),
|
||||
gap2 = npm.utils.messageGap(level + 2),
|
||||
lines = [
|
||||
`PreparedStatementError {`,
|
||||
gap1 + `message: "` + this.message + `"`,
|
||||
gap1 + `result: {`,
|
||||
gap2 + `name: ` + npm.utils.toJson(this.result.name),
|
||||
gap2 + `text: ` + npm.utils.toJson(this.result.text),
|
||||
gap2 + `values: ` + npm.utils.toJson(this.result.values),
|
||||
gap1 + `}`
|
||||
];
|
||||
if (this.error) {
|
||||
lines.push(gap1 + `error: ` + this.error.toString(level + 1));
|
||||
}
|
||||
lines.push(gap0 + `}`);
|
||||
return lines.join(npm.os.EOL);
|
||||
};
|
||||
|
||||
npm.utils.addInspection(PreparedStatementError, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
module.exports = {PreparedStatementError};
|
||||
95
ProjectSourceCode/node_modules/pg-promise/lib/errors/query-file-error.js
generated
vendored
Normal file
95
ProjectSourceCode/node_modules/pg-promise/lib/errors/query-file-error.js
generated
vendored
Normal file
@@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const npm = {
|
||||
os: require(`os`),
|
||||
utils: require(`../utils`),
|
||||
minify: require(`pg-minify`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @class errors.QueryFileError
|
||||
* @augments external:Error
|
||||
* @description
|
||||
* {@link errors.QueryFileError QueryFileError} class, available from the {@link errors} namespace.
|
||||
*
|
||||
* This type represents all errors related to {@link QueryFile}.
|
||||
*
|
||||
* @property {string} name
|
||||
* Standard {@link external:Error Error} property - error type name = `QueryFileError`.
|
||||
*
|
||||
* @property {string} message
|
||||
* Standard {@link external:Error Error} property - the error message.
|
||||
*
|
||||
* @property {string} stack
|
||||
* Standard {@link external:Error Error} property - the stack trace.
|
||||
*
|
||||
* @property {string} file
|
||||
* File path/name that was passed into the {@link QueryFile} constructor.
|
||||
*
|
||||
* @property {object} options
|
||||
* Set of options that was used by the {@link QueryFile} object.
|
||||
*
|
||||
* @property {SQLParsingError} error
|
||||
* Internal $[SQLParsingError] object.
|
||||
*
|
||||
* It is set only when the error was thrown by $[pg-minify] while parsing the SQL file.
|
||||
*
|
||||
* @see QueryFile
|
||||
*
|
||||
*/
|
||||
class QueryFileError extends Error {
|
||||
constructor(error, qf) {
|
||||
const isSqlError = error instanceof npm.minify.SQLParsingError;
|
||||
const message = isSqlError ? `Failed to parse the SQL.` : error.message;
|
||||
super(message);
|
||||
this.name = this.constructor.name;
|
||||
if (isSqlError) {
|
||||
this.error = error;
|
||||
}
|
||||
this.file = qf.file;
|
||||
this.options = qf.options;
|
||||
Error.captureStackTrace(this, this.constructor);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @method errors.QueryFileError#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the error.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
QueryFileError.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap0 = npm.utils.messageGap(level),
|
||||
gap1 = npm.utils.messageGap(level + 1),
|
||||
lines = [
|
||||
`QueryFileError {`,
|
||||
gap1 + `message: "` + this.message + `"`,
|
||||
gap1 + `options: ` + npm.utils.toJson(this.options),
|
||||
gap1 + `file: "` + this.file + `"`
|
||||
];
|
||||
if (this.error) {
|
||||
lines.push(gap1 + `error: ` + this.error.toString(level + 1));
|
||||
}
|
||||
lines.push(gap0 + `}`);
|
||||
return lines.join(npm.os.EOL);
|
||||
};
|
||||
|
||||
npm.utils.addInspection(QueryFileError, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
module.exports = {QueryFileError};
|
||||
177
ProjectSourceCode/node_modules/pg-promise/lib/errors/query-result-error.js
generated
vendored
Normal file
177
ProjectSourceCode/node_modules/pg-promise/lib/errors/query-result-error.js
generated
vendored
Normal file
@@ -0,0 +1,177 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const npm = {
|
||||
os: require(`os`),
|
||||
utils: require(`../utils`),
|
||||
text: require(`../text`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @enum {number}
|
||||
* @alias errors.queryResultErrorCode
|
||||
* @readonly
|
||||
* @description
|
||||
* `queryResultErrorCode` enumerator, available from the {@link errors} namespace.
|
||||
*
|
||||
* Represents an integer code for each type of error supported by type {@link errors.QueryResultError}.
|
||||
*
|
||||
* @see {@link errors.QueryResultError}
|
||||
*/
|
||||
const queryResultErrorCode = {
|
||||
/** No data returned from the query. */
|
||||
noData: 0,
|
||||
|
||||
/** No return data was expected. */
|
||||
notEmpty: 1,
|
||||
|
||||
/** Multiple rows were not expected. */
|
||||
multiple: 2
|
||||
};
|
||||
|
||||
const errorMessages = [
|
||||
{name: `noData`, message: npm.text.noData},
|
||||
{name: `notEmpty`, message: npm.text.notEmpty},
|
||||
{name: `multiple`, message: npm.text.multiple}
|
||||
];
|
||||
|
||||
/**
|
||||
* @class errors.QueryResultError
|
||||
* @augments external:Error
|
||||
* @description
|
||||
*
|
||||
* This error is specified as the rejection reason for all result-specific methods when the result doesn't match
|
||||
* the expectation, i.e. when a query result doesn't match its Query Result Mask - the value of {@link queryResult}.
|
||||
*
|
||||
* The error applies to the result from the following methods: {@link Database#none none},
|
||||
* {@link Database#one one}, {@link Database#oneOrNone oneOrNone} and {@link Database#many many}.
|
||||
*
|
||||
* Supported errors:
|
||||
*
|
||||
* - `No return data was expected.`, method {@link Database#none none}
|
||||
* - `No data returned from the query.`, methods {@link Database#one one} and {@link Database#many many}
|
||||
* - `Multiple rows were not expected.`, methods {@link Database#one one} and {@link Database#oneOrNone oneOrNone}
|
||||
*
|
||||
* Like any other error, this one is notified with through the global event {@link event:error error}.
|
||||
*
|
||||
* The type is available from the {@link errors} namespace.
|
||||
*
|
||||
* @property {string} name
|
||||
* Standard {@link external:Error Error} property - error type name = `QueryResultError`.
|
||||
*
|
||||
* @property {string} message
|
||||
* Standard {@link external:Error Error} property - the error message.
|
||||
*
|
||||
* @property {string} stack
|
||||
* Standard {@link external:Error Error} property - the stack trace.
|
||||
*
|
||||
* @property {object} result
|
||||
* The original $[Result] object that was received.
|
||||
*
|
||||
* @property {number} received
|
||||
* Total number of rows received. It is simply the value of `result.rows.length`.
|
||||
*
|
||||
* @property {number} code
|
||||
* Error code - {@link errors.queryResultErrorCode queryResultErrorCode} value.
|
||||
*
|
||||
* @property {string} query
|
||||
* Query that was executed.
|
||||
*
|
||||
* Normally, it is the query already formatted with values, if there were any.
|
||||
* But if you are using initialization option `pgFormatting`, then the query string is before formatting.
|
||||
*
|
||||
* @property {*} values
|
||||
* Values passed in as query parameters. Available only when initialization option `pgFormatting` is used.
|
||||
* Otherwise, the values are within the pre-formatted `query` string.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const QueryResultError = pgp.errors.QueryResultError;
|
||||
* const qrec = pgp.errors.queryResultErrorCode;
|
||||
*
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* error: (err, e) => {
|
||||
* if (err instanceof QueryResultError) {
|
||||
* // A query returned unexpected number of records, and thus rejected;
|
||||
*
|
||||
* // we can check the error code, if we want specifics:
|
||||
* if(err.code === qrec.noData) {
|
||||
* // expected some data, but received none;
|
||||
* }
|
||||
*
|
||||
* // If you write QueryResultError into the console,
|
||||
* // you will get a nicely formatted output.
|
||||
*
|
||||
* console.log(err);
|
||||
*
|
||||
* // See also: err, e.query, e.params, etc.
|
||||
* }
|
||||
* }
|
||||
* };
|
||||
*
|
||||
* @see
|
||||
* {@link queryResult}, {@link Database#none none}, {@link Database#one one},
|
||||
* {@link Database#oneOrNone oneOrNone}, {@link Database#many many}
|
||||
*
|
||||
*/
|
||||
class QueryResultError extends Error {
|
||||
constructor(code, result, query, values) {
|
||||
const message = errorMessages[code].message;
|
||||
super(message);
|
||||
this.name = this.constructor.name;
|
||||
this.code = code;
|
||||
this.result = result;
|
||||
this.query = query;
|
||||
this.values = values;
|
||||
this.received = result.rows.length;
|
||||
Error.captureStackTrace(this, this.constructor);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @method errors.QueryResultError#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the error.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
QueryResultError.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap0 = npm.utils.messageGap(level),
|
||||
gap1 = npm.utils.messageGap(level + 1),
|
||||
lines = [
|
||||
`QueryResultError {`,
|
||||
gap1 + `code: queryResultErrorCode.` + errorMessages[this.code].name,
|
||||
gap1 + `message: "` + this.message + `"`,
|
||||
gap1 + `received: ` + this.received,
|
||||
gap1 + `query: ` + (typeof this.query === `string` ? `"` + this.query + `"` : npm.utils.toJson(this.query))
|
||||
];
|
||||
if (this.values !== undefined) {
|
||||
lines.push(gap1 + `values: ` + npm.utils.toJson(this.values));
|
||||
}
|
||||
lines.push(gap0 + `}`);
|
||||
return lines.join(npm.os.EOL);
|
||||
};
|
||||
|
||||
npm.utils.addInspection(QueryResultError, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
module.exports = {
|
||||
QueryResultError,
|
||||
queryResultErrorCode
|
||||
};
|
||||
531
ProjectSourceCode/node_modules/pg-promise/lib/events.js
generated
vendored
Normal file
531
ProjectSourceCode/node_modules/pg-promise/lib/events.js
generated
vendored
Normal file
@@ -0,0 +1,531 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {ColorConsole} = require(`./utils/color`);
|
||||
|
||||
const npm = {
|
||||
main: require(`./`),
|
||||
utils: require(`./utils`)
|
||||
};
|
||||
|
||||
/////////////////////////////////
|
||||
// Client notification helpers;
|
||||
class Events {
|
||||
|
||||
/**
|
||||
* @event connect
|
||||
* @description
|
||||
* Global notification of acquiring a new database connection from the connection pool, i.e. a virtual connection.
|
||||
*
|
||||
* However, for direct calls to method {@link Database#connect Database.connect} with parameter `{direct: true}`,
|
||||
* this event represents a physical connection.
|
||||
*
|
||||
* The library will suppress any error thrown by the handler and write it into the console.
|
||||
*
|
||||
* @param {external:Client} client
|
||||
* $[pg.Client] object that represents the connection.
|
||||
*
|
||||
* @param {*} dc
|
||||
* Database Context that was used when creating the database object (see {@link Database}).
|
||||
*
|
||||
* @param {number} useCount
|
||||
* Number of times the connection has been previously used, starting with 0 for a freshly
|
||||
* allocated physical connection.
|
||||
*
|
||||
* This parameter is always 0 for direct connections (created by calling {@link Database#connect Database.connect}
|
||||
* with parameter `{direct: true}`).
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* connect(client, dc, useCount) {
|
||||
* const cp = client.connectionParameters;
|
||||
* console.log('Connected to database:', cp.database);
|
||||
* }
|
||||
*
|
||||
* };
|
||||
*/
|
||||
static connect(ctx, client, useCount) {
|
||||
if (typeof ctx.options.connect === `function`) {
|
||||
try {
|
||||
ctx.options.connect(client, ctx.dc, useCount);
|
||||
} catch (e) {
|
||||
// have to silence errors here;
|
||||
// cannot allow unhandled errors while connecting to the database,
|
||||
// as it will break the connection logic;
|
||||
Events.unexpected(`connect`, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @event disconnect
|
||||
* @description
|
||||
* Global notification of releasing a database connection back to the connection pool, i.e. releasing the virtual connection.
|
||||
*
|
||||
* However, when releasing a direct connection (created by calling {@link Database#connect Database.connect} with parameter
|
||||
* `{direct: true}`), this event represents a physical disconnection.
|
||||
*
|
||||
* The library will suppress any error thrown by the handler and write it into the console.
|
||||
*
|
||||
* @param {external:Client} client - $[pg.Client] object that represents connection with the database.
|
||||
*
|
||||
* @param {*} dc - Database Context that was used when creating the database object (see {@link Database}).
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* disconnect(client, dc) {
|
||||
* const cp = client.connectionParameters;
|
||||
* console.log('Disconnecting from database:', cp.database);
|
||||
* }
|
||||
*
|
||||
* };
|
||||
*/
|
||||
static disconnect(ctx, client) {
|
||||
if (typeof ctx.options.disconnect === `function`) {
|
||||
try {
|
||||
ctx.options.disconnect(client, ctx.dc);
|
||||
} catch (e) {
|
||||
// have to silence errors here;
|
||||
// cannot allow unhandled errors while disconnecting from the database,
|
||||
// as it will break the disconnection logic;
|
||||
Events.unexpected(`disconnect`, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @event query
|
||||
* @description
|
||||
*
|
||||
* Global notification of a query that's about to execute.
|
||||
*
|
||||
* Notification happens just before the query execution. And if the handler throws an error, the query execution
|
||||
* will be rejected with that error.
|
||||
*
|
||||
* @param {EventContext} e
|
||||
* Event Context Object.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* query(e) {
|
||||
* console.log('QUERY:', e.query);
|
||||
* }
|
||||
* };
|
||||
*/
|
||||
static query(options, context) {
|
||||
if (typeof options.query === `function`) {
|
||||
try {
|
||||
options.query(context);
|
||||
} catch (e) {
|
||||
// throwing an error during event 'query'
|
||||
// will result in a reject for the request.
|
||||
return e instanceof Error ? e : new npm.utils.InternalError(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @event receive
|
||||
* @description
|
||||
* Global notification of any data received from the database, coming from a regular query or from a stream.
|
||||
*
|
||||
* The event is fired before the data reaches the client, and it serves two purposes:
|
||||
* - Providing selective data logging for debugging;
|
||||
* - Pre-processing data before it reaches the client.
|
||||
*
|
||||
* **NOTES:**
|
||||
* - If you alter the size of `data` directly or through the `result` object, it may affect `QueryResultMask`
|
||||
* validation for regular queries, which is executed right after.
|
||||
* - Any data pre-processing needs to be fast here, to avoid performance penalties.
|
||||
* - If the event handler throws an error, the original request will be rejected with that error.
|
||||
*
|
||||
* For methods {@link Database#multi Database.multi} and {@link Database#multiResult Database.multiResult},
|
||||
* this event is called for every result that's returned. And for method {@link Database#stream Database.stream},
|
||||
* the event occurs for every record.
|
||||
*
|
||||
* @param {Array<Object>} data
|
||||
* Array of received objects/rows.
|
||||
*
|
||||
* If any of those objects are modified during notification, the client will receive the modified data.
|
||||
*
|
||||
* @param {external:Result} result
|
||||
* - Original $[Result] object, if the data is from a non-stream query, in which case `data = result.rows`.
|
||||
* For single-query requests, $[Result] object is extended with property `duration` - number of milliseconds
|
||||
* it took to send the query, execute it and get the result back.
|
||||
* - It is `undefined` when the data comes from a stream (method {@link Database#stream Database.stream}).
|
||||
*
|
||||
* @param {EventContext} e
|
||||
* Event Context Object.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Example below shows the fastest way to camelize all column names.
|
||||
* // NOTE: The example does not do processing for nested JSON objects.
|
||||
*
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* receive(data, result, e) {
|
||||
* camelizeColumns(data);
|
||||
* }
|
||||
* };
|
||||
*
|
||||
* function camelizeColumns(data) {
|
||||
* const tmp = data[0];
|
||||
* for (const prop in tmp) {
|
||||
* const camel = pgp.utils.camelize(prop);
|
||||
* if (!(camel in tmp)) {
|
||||
* for (let i = 0; i < data.length; i++) {
|
||||
* const d = data[i];
|
||||
* d[camel] = d[prop];
|
||||
* delete d[prop];
|
||||
* }
|
||||
* }
|
||||
* }
|
||||
* }
|
||||
*/
|
||||
static receive(options, data, result, context) {
|
||||
if (typeof options.receive === `function`) {
|
||||
try {
|
||||
options.receive(data, result, context);
|
||||
} catch (e) {
|
||||
// throwing an error during event 'receive'
|
||||
// will result in a reject for the request.
|
||||
return e instanceof Error ? e : new npm.utils.InternalError(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @event task
|
||||
* @description
|
||||
* Global notification of a task start / finish events, as executed via
|
||||
* {@link Database#task Database.task} or {@link Database#taskIf Database.taskIf}.
|
||||
*
|
||||
* The library will suppress any error thrown by the handler and write it into the console.
|
||||
*
|
||||
* @param {EventContext} e
|
||||
* Event Context Object.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* task(e) {
|
||||
* if (e.ctx.finish) {
|
||||
* // this is a task->finish event;
|
||||
* console.log('Duration:', e.ctx.duration);
|
||||
* if (e.ctx.success) {
|
||||
* // e.ctx.result = resolved data;
|
||||
* } else {
|
||||
* // e.ctx.result = error/rejection reason;
|
||||
* }
|
||||
* } else {
|
||||
* // this is a task->start event;
|
||||
* console.log('Start Time:', e.ctx.start);
|
||||
* }
|
||||
* }
|
||||
* };
|
||||
*
|
||||
*/
|
||||
static task(options, context) {
|
||||
if (typeof options.task === `function`) {
|
||||
try {
|
||||
options.task(context);
|
||||
} catch (e) {
|
||||
// silencing the error, to avoid breaking the task;
|
||||
Events.unexpected(`task`, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @event transact
|
||||
* @description
|
||||
* Global notification of a transaction start / finish events, as executed via {@link Database#tx Database.tx}
|
||||
* or {@link Database#txIf Database.txIf}.
|
||||
*
|
||||
* The library will suppress any error thrown by the handler and write it into the console.
|
||||
*
|
||||
* @param {EventContext} e
|
||||
* Event Context Object.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* transact(e) {
|
||||
* if (e.ctx.finish) {
|
||||
* // this is a transaction->finish event;
|
||||
* console.log('Duration:', e.ctx.duration);
|
||||
* if (e.ctx.success) {
|
||||
* // e.ctx.result = resolved data;
|
||||
* } else {
|
||||
* // e.ctx.result = error/rejection reason;
|
||||
* }
|
||||
* } else {
|
||||
* // this is a transaction->start event;
|
||||
* console.log('Start Time:', e.ctx.start);
|
||||
* }
|
||||
* }
|
||||
* };
|
||||
*
|
||||
*/
|
||||
static transact(options, context) {
|
||||
if (typeof options.transact === `function`) {
|
||||
try {
|
||||
options.transact(context);
|
||||
} catch (e) {
|
||||
// silencing the error, to avoid breaking the transaction;
|
||||
Events.unexpected(`transact`, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @event error
|
||||
* @description
|
||||
* Global notification of every error encountered by this library.
|
||||
*
|
||||
* The library will suppress any error thrown by the handler and write it into the console.
|
||||
*
|
||||
* @param {*} err
|
||||
* The error encountered, of the same value and type as it was reported.
|
||||
*
|
||||
* @param {EventContext} e
|
||||
* Event Context Object.
|
||||
*
|
||||
* @example
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* error(err, e) {
|
||||
*
|
||||
* if (e.cn) {
|
||||
* // this is a connection-related error
|
||||
* // cn = safe connection details passed into the library:
|
||||
* // if password is present, it is masked by #
|
||||
* }
|
||||
*
|
||||
* if (e.query) {
|
||||
* // query string is available
|
||||
* if (e.params) {
|
||||
* // query parameters are available
|
||||
* }
|
||||
* }
|
||||
*
|
||||
* if (e.ctx) {
|
||||
* // occurred inside a task or transaction
|
||||
* }
|
||||
* }
|
||||
* };
|
||||
*
|
||||
*/
|
||||
static error(options, err, context) {
|
||||
if (typeof options.error === `function`) {
|
||||
try {
|
||||
options.error(err, context);
|
||||
} catch (e) {
|
||||
// have to silence errors here;
|
||||
// throwing unhandled errors while handling an error
|
||||
// notification is simply not acceptable.
|
||||
Events.unexpected(`error`, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @event extend
|
||||
* @description
|
||||
* Extends {@link Database} protocol with custom methods and properties.
|
||||
*
|
||||
* Override this event to extend the existing access layer with your own functions and
|
||||
* properties best suited for your application.
|
||||
*
|
||||
* The extension thus becomes available across all access layers:
|
||||
*
|
||||
* - Within the root/default database protocol;
|
||||
* - Inside transactions, including nested ones;
|
||||
* - Inside tasks, including nested ones.
|
||||
*
|
||||
* All pre-defined methods and properties are read-only, so you will get an error,
|
||||
* if you try overriding them.
|
||||
*
|
||||
* The library will suppress any error thrown by the handler and write it into the console.
|
||||
*
|
||||
* @param {object} obj - Protocol object to be extended.
|
||||
*
|
||||
* @param {*} dc - Database Context that was used when creating the {@link Database} object.
|
||||
*
|
||||
* @see $[pg-promise-demo]
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // In the example below we extend the protocol with function `addImage`
|
||||
* // that will insert one binary image and resolve with the new record id.
|
||||
*
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* extend(obj, dc) {
|
||||
* // dc = database context;
|
||||
* obj.addImage = data => {
|
||||
* // adds a new image and resolves with its record id:
|
||||
* return obj.one('INSERT INTO images(data) VALUES($1) RETURNING id', data, a => a.id);
|
||||
* }
|
||||
* }
|
||||
* };
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // It is best to extend the protocol by adding whole entity repositories to it as shown in the following example.
|
||||
* // For a comprehensive example see https://github.com/vitaly-t/pg-promise-demo
|
||||
*
|
||||
* class UsersRepository {
|
||||
* constructor(rep, pgp) {
|
||||
* this.rep = rep;
|
||||
* this.pgp = pgp;
|
||||
* }
|
||||
*
|
||||
* add(name) {
|
||||
* return this.rep.one('INSERT INTO users(name) VALUES($1) RETURNING id', name, a => a.id);
|
||||
* }
|
||||
*
|
||||
* remove(id) {
|
||||
* return this.rep.none('DELETE FROM users WHERE id = $1', id);
|
||||
* }
|
||||
* }
|
||||
*
|
||||
* // Overriding 'extend' event;
|
||||
* const initOptions = {
|
||||
*
|
||||
* // pg-promise initialization options...
|
||||
*
|
||||
* extend(obj, dc) {
|
||||
* // dc = database context;
|
||||
* obj.users = new UsersRepository(obj, pgp);
|
||||
* // You can set different repositories based on `dc`
|
||||
* }
|
||||
* };
|
||||
*
|
||||
* // Usage example:
|
||||
* db.users.add('John', true)
|
||||
* .then(id => {
|
||||
* // user added successfully, id = new user's id
|
||||
* })
|
||||
* .catch(error => {
|
||||
* // failed to add the user;
|
||||
* });
|
||||
*
|
||||
*/
|
||||
static extend(options, obj, dc) {
|
||||
if (typeof options.extend === `function`) {
|
||||
try {
|
||||
options.extend.call(obj, obj, dc);
|
||||
} catch (e) {
|
||||
// have to silence errors here;
|
||||
// the result of throwing unhandled errors while
|
||||
// extending the protocol would be unpredictable.
|
||||
Events.unexpected(`extend`, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @event unexpected
|
||||
* @param {string} event - unhandled event name.
|
||||
* @param {string|Error} e - unhandled error.
|
||||
* @private
|
||||
*/
|
||||
static unexpected(event, e) {
|
||||
// If you should ever get here, your app is definitely broken, and you need to fix
|
||||
// your event handler to prevent unhandled errors during event notifications.
|
||||
//
|
||||
// Console output is suppressed when running tests, to avoid polluting test output
|
||||
// with error messages that are intentional and of no value to the test.
|
||||
|
||||
/* istanbul ignore if */
|
||||
if (!npm.main.suppressErrors) {
|
||||
const stack = e instanceof Error ? e.stack : new Error().stack;
|
||||
ColorConsole.error(`Unexpected error in '${event}' event handler.\n${stack}\n`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {Events};
|
||||
|
||||
/**
|
||||
* @typedef EventContext
|
||||
* @description
|
||||
* This common type is used for the following events: {@link event:query query}, {@link event:receive receive},
|
||||
* {@link event:error error}, {@link event:task task} and {@link event:transact transact}.
|
||||
*
|
||||
* @property {string|object} cn
|
||||
*
|
||||
* Set only for event {@link event:error error}, and only when the error is connection-related.
|
||||
*
|
||||
* It is a safe copy of the connection string/object that was used when initializing `db` - the database instance.
|
||||
*
|
||||
* If the original connection contains a password, the safe copy contains it masked with symbol `#`, so the connection
|
||||
* can be logged safely, without exposing the password.
|
||||
*
|
||||
* @property {*} dc
|
||||
* Database Context that was used when creating the database object (see {@link Database}). It is set for all events.
|
||||
*
|
||||
* @property {string|object} query
|
||||
*
|
||||
* Query string/object that was passed into the query method. This property is only set during events {@link event:query query},
|
||||
* {@link event:receive receive} and {@link event:error error} (only when the error is query-related).
|
||||
*
|
||||
* @property {external:Client} client
|
||||
*
|
||||
* $[pg.Client] object that represents the connection. It is set for all events, except for event {@link event:error error}
|
||||
* when it is connection-related. Note that sometimes the value may be unset when the connection is lost.
|
||||
*
|
||||
* @property {*} params - Formatting parameters for the query.
|
||||
*
|
||||
* It is set only for events {@link event:query query}, {@link event:receive receive} and {@link event:error error}, and only
|
||||
* when it is needed for logging. This library takes an extra step in figuring out when formatting parameters are of any value
|
||||
* to the event logging:
|
||||
* - when an error occurs related to the query formatting, event {@link event:error error} is sent with the property set.
|
||||
* - when initialization parameter `pgFormat` is used, and all query formatting is done within the $[PG] library, events
|
||||
* {@link event:query query} and {@link event:receive receive} will have this property set also, since this library no longer
|
||||
* handles the query formatting.
|
||||
*
|
||||
* When this parameter is not set, it means one of the two things:
|
||||
* - there were no parameters passed into the query method;
|
||||
* - property `query` of this object already contains all the formatting values in it, so logging only the query is sufficient.
|
||||
*
|
||||
* @property {TaskContext} ctx
|
||||
* _Task/Transaction Context_ object.
|
||||
*
|
||||
* This property is always set for events {@link event:task task} and {@link event:transact transact}, while for events
|
||||
* {@link event:query query}, {@link event:receive receive} and {@link event:error error} it is only set when they occur
|
||||
* inside a task or transaction.
|
||||
*
|
||||
*/
|
||||
931
ProjectSourceCode/node_modules/pg-promise/lib/formatting.js
generated
vendored
Normal file
931
ProjectSourceCode/node_modules/pg-promise/lib/formatting.js
generated
vendored
Normal file
@@ -0,0 +1,931 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {assert} = require(`./assert`);
|
||||
|
||||
const npm = {
|
||||
pgUtils: require(`pg/lib/utils`),
|
||||
patterns: require(`./patterns`),
|
||||
utils: require(`./utils`)
|
||||
};
|
||||
|
||||
// Format Modification Flags;
|
||||
const fmFlags = {
|
||||
raw: 1, // Raw-Text variable
|
||||
alias: 2, // SQL Alias
|
||||
name: 4, // SQL Name/Identifier
|
||||
json: 8, // JSON modifier
|
||||
csv: 16, // CSV modifier
|
||||
value: 32 // escaped, but without ''
|
||||
};
|
||||
|
||||
// Format Modification Map;
|
||||
const fmMap = {
|
||||
'^': fmFlags.raw,
|
||||
':raw': fmFlags.raw,
|
||||
':alias': fmFlags.alias,
|
||||
'~': fmFlags.name,
|
||||
':name': fmFlags.name,
|
||||
':json': fmFlags.json,
|
||||
':csv': fmFlags.csv,
|
||||
':list': fmFlags.csv,
|
||||
':value': fmFlags.value,
|
||||
'#': fmFlags.value
|
||||
};
|
||||
|
||||
// Global symbols for Custom Type Formatting:
|
||||
const ctfSymbols = {
|
||||
toPostgres: Symbol.for(`ctf.toPostgres`),
|
||||
rawType: Symbol.for(`ctf.rawType`)
|
||||
};
|
||||
|
||||
const maxVariable = 100000; // maximum supported variable is '$100000'
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
// Converts a single value into its Postgres format.
|
||||
function formatValue({value, fm, cc, options}) {
|
||||
|
||||
if (typeof value === `function`) {
|
||||
return formatValue({value: resolveFunc(value, cc), fm, cc});
|
||||
}
|
||||
|
||||
const ctf = getCTF(value); // Custom Type Formatting
|
||||
if (ctf) {
|
||||
fm |= ctf.rawType ? fmFlags.raw : 0;
|
||||
return formatValue({value: resolveFunc(ctf.toPostgres, value), fm, cc});
|
||||
}
|
||||
|
||||
const isRaw = !!(fm & fmFlags.raw);
|
||||
fm &= ~fmFlags.raw;
|
||||
|
||||
switch (fm) {
|
||||
case fmFlags.alias:
|
||||
return $as.alias(value);
|
||||
case fmFlags.name:
|
||||
return $as.name(value);
|
||||
case fmFlags.json:
|
||||
return $as.json(value, isRaw);
|
||||
case fmFlags.csv:
|
||||
return $to.csv(value, options);
|
||||
case fmFlags.value:
|
||||
return $as.value(value);
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (isNull(value)) {
|
||||
throwIfRaw(isRaw);
|
||||
return `null`;
|
||||
}
|
||||
|
||||
switch (typeof value) {
|
||||
case `string`:
|
||||
return $to.text(value, isRaw);
|
||||
case `boolean`:
|
||||
return $to.bool(value);
|
||||
case `number`:
|
||||
case `bigint`:
|
||||
return $to.number(value);
|
||||
case `symbol`:
|
||||
throw new TypeError(`Type Symbol has no meaning for PostgreSQL: ${value.toString()}`);
|
||||
default:
|
||||
if (value instanceof Date) {
|
||||
return $to.date(value, isRaw);
|
||||
}
|
||||
if (Array.isArray(value)) {
|
||||
return $to.array(value, options);
|
||||
}
|
||||
if (Buffer.isBuffer(value)) {
|
||||
return $to.buffer(value, isRaw);
|
||||
}
|
||||
return $to.json(value, isRaw);
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Converts array of values into PostgreSQL Array Constructor: array[...], as per PostgreSQL documentation:
|
||||
// http://www.postgresql.org/docs/9.6/static/arrays.html
|
||||
//
|
||||
// Arrays of any depth/dimension are supported.
|
||||
//
|
||||
// Top-level empty arrays are formatted as literal '{}' to avoid the necessity of explicit type casting,
|
||||
// as the server cannot automatically infer the type of empty non-literal array.
|
||||
function formatArray(array, options) {
|
||||
const loop = a => `[` + a.map(value => Array.isArray(value) ? loop(value) : formatValue({
|
||||
value,
|
||||
options
|
||||
})).join() + `]`;
|
||||
const prefix = options && options.capSQL ? `ARRAY` : `array`;
|
||||
return array.length ? (prefix + loop(array)) : `'{}'`;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////
|
||||
// Formats array/object/value as a list of comma-separated values.
|
||||
function formatCSV(values, options) {
|
||||
if (Array.isArray(values)) {
|
||||
return values.map(value => formatValue({value, options})).join();
|
||||
}
|
||||
if (typeof values === `object` && values !== null) {
|
||||
return Object.keys(values).map(v => formatValue({value: values[v], options})).join();
|
||||
}
|
||||
return values === undefined ? `` : formatValue({value: values, options});
|
||||
}
|
||||
|
||||
///////////////////////////////
|
||||
// Query formatting helpers;
|
||||
const formatAs = {
|
||||
|
||||
object({query, obj, raw, options}) {
|
||||
options = options && typeof options === `object` ? options : {};
|
||||
return query.replace(npm.patterns.namedParameters, name => {
|
||||
const v = formatAs.stripName(name.replace(/^\$[{(<[/]|[\s})>\]/]/g, ``), raw),
|
||||
c = npm.utils.getIfHas(obj, v.name);
|
||||
if (!c.valid) {
|
||||
throw new Error(`Invalid property name '${v.name}'.`);
|
||||
}
|
||||
if (c.has) {
|
||||
return formatValue({value: c.value, fm: v.fm, cc: c.target, options});
|
||||
}
|
||||
if (v.name === `this`) {
|
||||
return formatValue({value: obj, fm: v.fm, options});
|
||||
}
|
||||
if (`def` in options) {
|
||||
const d = options.def, value = typeof d === `function` ? d.call(obj, v.name, obj) : d;
|
||||
return formatValue({value, fm: v.fm, cc: obj, options});
|
||||
}
|
||||
if (options.partial) {
|
||||
return name;
|
||||
}
|
||||
// property must exist as the object's own or inherited;
|
||||
throw new Error(`Property '${v.name}' doesn't exist.`);
|
||||
});
|
||||
},
|
||||
|
||||
array({query, array, raw, options}) {
|
||||
options = options && typeof options === `object` ? options : {};
|
||||
return query.replace(npm.patterns.multipleValues, name => {
|
||||
const v = formatAs.stripName(name.substr(1), raw);
|
||||
const idx = v.name - 1;
|
||||
if (idx >= maxVariable) {
|
||||
throw new RangeError(`Variable $${v.name} exceeds supported maximum of $${maxVariable}`);
|
||||
}
|
||||
if (idx < array.length) {
|
||||
return formatValue({value: array[idx], fm: v.fm, options});
|
||||
}
|
||||
if (`def` in options) {
|
||||
const d = options.def, value = typeof d === `function` ? d.call(array, idx, array) : d;
|
||||
return formatValue({value, fm: v.fm, options});
|
||||
}
|
||||
if (options.partial) {
|
||||
return name;
|
||||
}
|
||||
throw new RangeError(`Variable $${v.name} out of range. Parameters array length: ${array.length}`);
|
||||
});
|
||||
},
|
||||
|
||||
value({query, value, raw, options}) {
|
||||
return query.replace(npm.patterns.singleValue, name => {
|
||||
const v = formatAs.stripName(name, raw);
|
||||
return formatValue({value, fm: v.fm, options});
|
||||
});
|
||||
},
|
||||
|
||||
stripName(name, raw) {
|
||||
const mod = name.match(npm.patterns.hasValidModifier);
|
||||
if (mod) {
|
||||
return {
|
||||
name: name.substr(0, mod.index),
|
||||
fm: fmMap[mod[0]] | (raw ? fmFlags.raw : 0)
|
||||
};
|
||||
}
|
||||
return {
|
||||
name,
|
||||
fm: raw ? fmFlags.raw : null
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
////////////////////////////////////////////
|
||||
// Simpler check for null/undefined;
|
||||
function isNull(value) {
|
||||
return value === undefined || value === null;
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
// Checks if the value supports Custom Type Formatting,
|
||||
// to return {toPostgres, rawType}, if it does, or null otherwise.
|
||||
function getCTF(value) {
|
||||
if (!isNull(value)) {
|
||||
let toPostgres = value[ctfSymbols.toPostgres], rawType = !!value[ctfSymbols.rawType];
|
||||
if (typeof toPostgres !== `function`) {
|
||||
toPostgres = value.toPostgres;
|
||||
rawType = !!value.rawType;
|
||||
}
|
||||
if (typeof toPostgres === `function`) {
|
||||
if (toPostgres.constructor.name !== `Function`) {
|
||||
throw new Error(`CTF does not support asynchronous toPostgres functions.`);
|
||||
}
|
||||
return {toPostgres, rawType};
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////
|
||||
// Wraps a text string in single quotes;
|
||||
function wrapText(text) {
|
||||
return `'${text}'`;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////
|
||||
// Replaces each single-quote symbol ' with two,
|
||||
// for compliance with PostgreSQL strings.
|
||||
function safeText(text) {
|
||||
return text.replace(/'/g, `''`);
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////
|
||||
// Throws an exception, if flag 'raw' is set.
|
||||
function throwIfRaw(raw) {
|
||||
if (raw) {
|
||||
throw new TypeError(`Values null/undefined cannot be used as raw text.`);
|
||||
}
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Recursively resolves parameter-function, with an optional Calling Context.
|
||||
function resolveFunc(value, cc) {
|
||||
while (typeof value === `function`) {
|
||||
if (value.constructor.name !== `Function`) {
|
||||
// Constructor name for asynchronous functions have different names:
|
||||
// - 'GeneratorFunction' for ES6 generators
|
||||
// - 'AsyncFunction' for ES7 async functions
|
||||
throw new Error(`Cannot use asynchronous functions with query formatting.`);
|
||||
}
|
||||
value = value.call(cc, cc);
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
// It implements two types of formatting, depending on the 'values' passed:
|
||||
//
|
||||
// 1. format '$1, $2, etc', when 'values' is of type string, boolean, number, date,
|
||||
// function or null (or an array of the same types, plus undefined values);
|
||||
// 2. format $*propName*, when 'values' is an object (not null and not Date),
|
||||
// and where * is any of the supported open-close pairs: {}, (), [], <>, //
|
||||
//
|
||||
function formatQuery(query, values, raw, options) {
|
||||
if (typeof query !== `string`) {
|
||||
throw new TypeError(`Parameter 'query' must be a text string.`);
|
||||
}
|
||||
const ctf = getCTF(values);
|
||||
if (ctf) {
|
||||
// Custom Type Formatting
|
||||
return formatQuery(query, resolveFunc(ctf.toPostgres, values), raw || ctf.rawType, options);
|
||||
}
|
||||
if (typeof values === `object` && values !== null) {
|
||||
if (Array.isArray(values)) {
|
||||
// $1, $2,... formatting to be applied;
|
||||
return formatAs.array({query, array: values, raw, options});
|
||||
}
|
||||
if (!(values instanceof Date || values instanceof Buffer)) {
|
||||
// $*propName* formatting to be applied;
|
||||
return formatAs.object({query, obj: values, raw, options});
|
||||
}
|
||||
}
|
||||
// $1 formatting to be applied, if values != undefined;
|
||||
return values === undefined ? query : formatAs.value({query, value: values, raw, options});
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////
|
||||
// Formats a function or stored procedure call query;
|
||||
function formatEntity(entity, values, {capSQL, type}) {
|
||||
let prefix = type === `func` ? `select * from` : `call`;
|
||||
if (capSQL) {
|
||||
prefix = prefix.toUpperCase();
|
||||
}
|
||||
return `${prefix} ${$as.alias(entity)}(${formatCSV(values, {capSQL})})`;
|
||||
}
|
||||
|
||||
function formatSqlName(name) {
|
||||
return `"${name.replace(/"/g, `""`)}"`;
|
||||
}
|
||||
|
||||
/**
|
||||
* @namespace formatting
|
||||
* @description
|
||||
* Namespace for all query-formatting functions, available from `pgp.as` before and after initializing the library.
|
||||
*
|
||||
* @property {formatting.ctf} ctf
|
||||
* Namespace for symbols used by $[Custom Type Formatting].
|
||||
*
|
||||
* @property {function} alias
|
||||
* {@link formatting.alias alias} - formats an SQL alias.
|
||||
*
|
||||
* @property {function} name
|
||||
* {@link formatting.name name} - formats an SQL Name/Identifier.
|
||||
*
|
||||
* @property {function} text
|
||||
* {@link formatting.text text} - formats a text string.
|
||||
*
|
||||
* @property {function} number
|
||||
* {@link formatting.number number} - formats a number.
|
||||
*
|
||||
* @property {function} buffer
|
||||
* {@link formatting.buffer buffer} - formats a `Buffer` object.
|
||||
*
|
||||
* @property {function} value
|
||||
* {@link formatting.value value} - formats text as an open value.
|
||||
*
|
||||
* @property {function} json
|
||||
* {@link formatting.json json} - formats any value as JSON.
|
||||
*
|
||||
* @property {function} array
|
||||
* {@link formatting.array array} - formats an array of any depth.
|
||||
*
|
||||
* @property {function} csv
|
||||
* {@link formatting.csv csv} - formats an array as a list of comma-separated values.
|
||||
*
|
||||
* @property {function} func
|
||||
* {@link formatting.func func} - formats the value returned from a function.
|
||||
*
|
||||
* @property {function} format
|
||||
* {@link formatting.format format} - formats a query, according to parameters.
|
||||
*
|
||||
*/
|
||||
const $as = {
|
||||
|
||||
/**
|
||||
* @namespace formatting.ctf
|
||||
* @description
|
||||
* Namespace for ES6 symbols used by $[Custom Type Formatting], available from `pgp.as.ctf` before and after initializing the library.
|
||||
*
|
||||
* It was added to avoid explicit/enumerable extension of types that need to be used as formatting parameters, to keep their type signature intact.
|
||||
*
|
||||
* @property {external:Symbol} toPostgres
|
||||
* Property name for the $[Custom Type Formatting] callback function `toPostgres`.
|
||||
*
|
||||
* @property {external:Symbol} rawType
|
||||
* Property name for the $[Custom Type Formatting] flag `rawType`.
|
||||
*
|
||||
* @example
|
||||
* const ctf = pgp.as.ctf; // Custom Type Formatting symbols
|
||||
*
|
||||
* class MyType {
|
||||
* constructor() {
|
||||
* this[ctf.rawType] = true; // set it only when toPostgres returns a pre-formatted result
|
||||
* }
|
||||
*
|
||||
* [ctf.toPostgres](self) {
|
||||
* // self = this
|
||||
*
|
||||
* // return the custom/actual value here
|
||||
* }
|
||||
* }
|
||||
*
|
||||
* const a = new MyType();
|
||||
*
|
||||
* const s = pgp.as.format('$1', a); // will be custom-formatted
|
||||
*/
|
||||
ctf: ctfSymbols,
|
||||
|
||||
/**
|
||||
* @method formatting.text
|
||||
* @description
|
||||
* Converts a value into PostgreSQL text presentation, escaped as required.
|
||||
*
|
||||
* Escaping the result means:
|
||||
* 1. Every single-quote (apostrophe) is replaced with two
|
||||
* 2. The resulting text is wrapped in apostrophes
|
||||
*
|
||||
* @param {value|function} value
|
||||
* Value to be converted, or a function that returns the value.
|
||||
*
|
||||
* If the `value` resolves as `null` or `undefined`, while `raw`=`true`,
|
||||
* it will throw {@link external:TypeError TypeError} = `Values null/undefined cannot be used as raw text.`
|
||||
*
|
||||
* @param {boolean} [raw=false]
|
||||
* Indicates when not to escape the resulting text.
|
||||
*
|
||||
* @returns {string}
|
||||
*
|
||||
* - `null` string, if the `value` resolves as `null` or `undefined`
|
||||
* - escaped result of `value.toString()`, if the `value` isn't a string
|
||||
* - escaped string version, if `value` is a string.
|
||||
*
|
||||
* The result is not escaped, if `raw` was passed in as `true`.
|
||||
*/
|
||||
text(value, raw) {
|
||||
value = resolveFunc(value);
|
||||
if (isNull(value)) {
|
||||
throwIfRaw(raw);
|
||||
return `null`;
|
||||
}
|
||||
if (typeof value !== `string`) {
|
||||
value = value.toString();
|
||||
}
|
||||
return $to.text(value, raw);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.name
|
||||
* @description
|
||||
* Properly escapes an sql name or identifier, fixing double-quote symbols and wrapping the result in double quotes.
|
||||
*
|
||||
* Implements a safe way to format $[SQL Names] that neutralizes SQL Injection.
|
||||
*
|
||||
* When formatting a query, a variable makes use of this method via modifier `:name` or `~`. See method {@link formatting.format format}.
|
||||
*
|
||||
* @param {string|function|array|object} name
|
||||
* SQL name or identifier, or a function that returns it.
|
||||
*
|
||||
* The name must be at least 1 character long.
|
||||
*
|
||||
* If `name` doesn't resolve into a non-empty string, it throws {@link external:TypeError TypeError} = `Invalid sql name: ...`
|
||||
*
|
||||
* If the `name` contains only a single `*` (trailing spaces are ignored), then `name` is returned exactly as is (unescaped).
|
||||
*
|
||||
* - If `name` is an Array, it is formatted as a comma-separated list of $[SQL Names]
|
||||
* - If `name` is a non-Array object, its keys are formatted as a comma-separated list of $[SQL Names]
|
||||
*
|
||||
* Passing in an empty array/object will throw {@link external:Error Error} = `Cannot retrieve sql names from an empty array/object.`
|
||||
*
|
||||
* @returns {string}
|
||||
* The SQL Name/Identifier, properly escaped for compliance with the PostgreSQL standard for $[SQL Names] and identifiers.
|
||||
*
|
||||
* @see
|
||||
* {@link formatting.alias alias},
|
||||
* {@link formatting.format format}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // automatically list object properties as sql names:
|
||||
* format('INSERT INTO table(${this~}) VALUES(${one}, ${two})', {
|
||||
* one: 1,
|
||||
* two: 2
|
||||
* });
|
||||
* //=> INSERT INTO table("one","two") VALUES(1, 2)
|
||||
*
|
||||
*/
|
||||
name(name) {
|
||||
name = resolveFunc(name);
|
||||
if (name) {
|
||||
if (typeof name === `string`) {
|
||||
return /^\s*\*(\s*)$/.test(name) ? name : formatSqlName(name);
|
||||
}
|
||||
if (typeof name === `object`) {
|
||||
const keys = Array.isArray(name) ? name : Object.keys(name);
|
||||
if (!keys.length) {
|
||||
throw new Error(`Cannot retrieve sql names from an empty array/object.`);
|
||||
}
|
||||
return keys.map(value => {
|
||||
if (!value || typeof value !== `string`) {
|
||||
throw new Error(`Invalid sql name: ${npm.utils.toJson(value)}`);
|
||||
}
|
||||
return formatSqlName(value);
|
||||
}).join();
|
||||
}
|
||||
}
|
||||
throw new TypeError(`Invalid sql name: ${npm.utils.toJson(name)}`);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.alias
|
||||
* @description
|
||||
* Simpler (non-verbose) version of method {@link formatting.name name}, to handle only a regular string-identifier
|
||||
* that's mostly used as an SQL alias, i.e. it doesn't support `*` or an array/object of names, which in the context of
|
||||
* an SQL alias would be incorrect. However, it supports `.` as name-separator, for simpler escaping of composite names.
|
||||
*
|
||||
* The surrounding double quotes are not added when the alias uses a simple syntax:
|
||||
* - it is a same-case single word, without spaces
|
||||
* - it can contain underscores, and can even start with them
|
||||
* - it can contain digits and `$`, but cannot start with those
|
||||
*
|
||||
* The method will automatically split the string with `.`, to support composite SQL names.
|
||||
*
|
||||
* When formatting a query, a variable makes use of this method via modifier `:alias`. See method {@link formatting.format format}.
|
||||
*
|
||||
* @param {string|function} name
|
||||
* SQL alias name, or a function that returns it.
|
||||
*
|
||||
* The name must be at least 1 character long. And it can contain `.`, to split into multiple SQL names.
|
||||
*
|
||||
* If `name` doesn't resolve into a non-empty string, it throws {@link external:TypeError TypeError} = `Invalid sql alias: ...`
|
||||
*
|
||||
* @returns {string}
|
||||
* The SQL alias, properly escaped for compliance with the PostgreSQL standard for $[SQL Names] and identifiers.
|
||||
*
|
||||
* @see
|
||||
* {@link formatting.name name},
|
||||
* {@link formatting.format format}
|
||||
*
|
||||
*/
|
||||
alias(name) {
|
||||
name = resolveFunc(name);
|
||||
if (name && typeof name === `string`) {
|
||||
return name.split(`.`)
|
||||
.filter(f => f)
|
||||
.map(a => {
|
||||
const m = a.match(/^([a-z_][a-z0-9_$]*|[A-Z_][A-Z0-9_$]*)$/);
|
||||
if (m && m[0] === a) {
|
||||
return a;
|
||||
}
|
||||
return `"${a.replace(/"/g, `""`)}"`;
|
||||
}).join(`.`);
|
||||
}
|
||||
throw new TypeError(`Invalid sql alias: ${npm.utils.toJson(name)}`);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.value
|
||||
* @description
|
||||
* Represents an open value, one to be formatted according to its type, properly escaped, but without surrounding quotes for text types.
|
||||
*
|
||||
* When formatting a query, a variable makes use of this method via modifier `:value` or `#`. See method {@link formatting.format format}.
|
||||
*
|
||||
* @param {value|function} value
|
||||
* Value to be converted, or a function that returns the value.
|
||||
*
|
||||
* If `value` resolves as `null` or `undefined`, it will throw {@link external:TypeError TypeError} = `Open values cannot be null or undefined.`
|
||||
*
|
||||
* @returns {string}
|
||||
* Formatted and properly escaped string, but without surrounding quotes for text types.
|
||||
*
|
||||
* @see {@link formatting.format format}
|
||||
*
|
||||
*/
|
||||
value(value) {
|
||||
value = resolveFunc(value);
|
||||
if (isNull(value)) {
|
||||
throw new TypeError(`Open values cannot be null or undefined.`);
|
||||
}
|
||||
return safeText(formatValue({value, fm: fmFlags.raw}));
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.buffer
|
||||
* @description
|
||||
* Converts an object of type `Buffer` into a hex string compatible with PostgreSQL type `bytea`.
|
||||
*
|
||||
* @param {Buffer|function} obj
|
||||
* Object to be converted, or a function that returns one.
|
||||
*
|
||||
* @param {boolean} [raw=false]
|
||||
* Indicates when not to wrap the resulting string in quotes.
|
||||
*
|
||||
* The generated hex string doesn't need to be escaped.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
buffer(obj, raw) {
|
||||
obj = resolveFunc(obj);
|
||||
if (isNull(obj)) {
|
||||
throwIfRaw(raw);
|
||||
return `null`;
|
||||
}
|
||||
if (obj instanceof Buffer) {
|
||||
return $to.buffer(obj, raw);
|
||||
}
|
||||
throw new TypeError(`${wrapText(obj)} is not a Buffer object.`);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.bool
|
||||
* @description
|
||||
* Converts a truthy value into PostgreSQL boolean presentation.
|
||||
*
|
||||
* @param {boolean|function} value
|
||||
* Value to be converted, or a function that returns the value.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
bool(value) {
|
||||
value = resolveFunc(value);
|
||||
if (isNull(value)) {
|
||||
return `null`;
|
||||
}
|
||||
return $to.bool(value);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.date
|
||||
* @description
|
||||
* Converts a `Date`-type value into PostgreSQL date/time presentation,
|
||||
* wrapped in quotes (unless flag `raw` is set).
|
||||
*
|
||||
* @param {Date|function} d
|
||||
* Date object to be converted, or a function that returns one.
|
||||
*
|
||||
* @param {boolean} [raw=false]
|
||||
* Indicates when not to escape the value.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
date(d, raw) {
|
||||
d = resolveFunc(d);
|
||||
if (isNull(d)) {
|
||||
throwIfRaw(raw);
|
||||
return `null`;
|
||||
}
|
||||
if (d instanceof Date) {
|
||||
return $to.date(d, raw);
|
||||
}
|
||||
throw new TypeError(`${wrapText(d)} is not a Date object.`);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.number
|
||||
* @description
|
||||
* Converts a numeric value into its PostgreSQL number presentation, with support
|
||||
* for special values of `NaN`, `+Infinity` and `-Infinity`.
|
||||
*
|
||||
* @param {number|bigint|function} num
|
||||
* Number to be converted, or a function that returns one.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
number(num) {
|
||||
num = resolveFunc(num);
|
||||
if (isNull(num)) {
|
||||
return `null`;
|
||||
}
|
||||
const t = typeof num;
|
||||
if (t !== `number` && t !== `bigint`) {
|
||||
throw new TypeError(`${wrapText(num)} is not a number.`);
|
||||
}
|
||||
return $to.number(num);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.array
|
||||
* @description
|
||||
* Converts an array of values into its PostgreSQL presentation as an Array-Type constructor string: `array[]`.
|
||||
*
|
||||
* Top-level empty arrays are formatted as literal `{}`, to avoid the necessity of explicit type casting,
|
||||
* as the server cannot automatically infer type of an empty non-literal array.
|
||||
*
|
||||
* @param {Array|function} arr
|
||||
* Array to be converted, or a function that returns one.
|
||||
*
|
||||
* @param {{}} [options]
|
||||
* Array-Formatting Options.
|
||||
*
|
||||
* @param {boolean} [options.capSQL=false]
|
||||
* When `true`, outputs `ARRAY` instead of `array`.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
array(arr, options) {
|
||||
options = assert(options, [`capSQL`]);
|
||||
arr = resolveFunc(arr);
|
||||
if (isNull(arr)) {
|
||||
return `null`;
|
||||
}
|
||||
if (Array.isArray(arr)) {
|
||||
return $to.array(arr, options);
|
||||
}
|
||||
throw new TypeError(`${wrapText(arr)} is not an Array object.`);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.csv
|
||||
* @description
|
||||
* Converts a single value or an array of values into a CSV (comma-separated values) string, with all values formatted
|
||||
* according to their JavaScript type.
|
||||
*
|
||||
* When formatting a query, a variable makes use of this method via modifier `:csv` or its alias `:list`.
|
||||
*
|
||||
* When `values` is an object that's not `null` or `Array`, its properties are enumerated for the actual values.
|
||||
*
|
||||
* @param {Array|Object|value|function} values
|
||||
* Value(s) to be converted, or a function that returns it.
|
||||
*
|
||||
* @returns {string}
|
||||
*
|
||||
* @see {@link formatting.format format}
|
||||
*/
|
||||
csv(values) {
|
||||
return $to.csv(values);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.json
|
||||
* @description
|
||||
* Converts any value into JSON (includes `BigInt` support), and returns it as a valid string,
|
||||
* with single-quote symbols fixed, unless flag `raw` is set.
|
||||
*
|
||||
* When formatting a query, a variable makes use of this method via modifier `:json`. See method {@link formatting.format format}.
|
||||
*
|
||||
* @param {*} data
|
||||
* Object/value to be converted, or a function that returns it.
|
||||
*
|
||||
* @param {boolean} [raw=false]
|
||||
* Indicates when not to escape the result.
|
||||
*
|
||||
* @returns {string}
|
||||
*
|
||||
* @see {@link formatting.format format}
|
||||
*/
|
||||
json(data, raw) {
|
||||
data = resolveFunc(data);
|
||||
if (isNull(data)) {
|
||||
throwIfRaw(raw);
|
||||
return `null`;
|
||||
}
|
||||
return $to.json(data, raw);
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.func
|
||||
* @description
|
||||
* Calls the function to get the actual value, and then formats the result according to its type + `raw` flag.
|
||||
*
|
||||
* @param {function} func
|
||||
* Function to be called, with support for nesting.
|
||||
*
|
||||
* @param {boolean} [raw=false]
|
||||
* Indicates when not to escape the result.
|
||||
*
|
||||
* @param {*} [cc]
|
||||
* Calling Context: `this` + the only value to be passed into the function on all nested levels.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
func(func, raw, cc) {
|
||||
if (isNull(func)) {
|
||||
throwIfRaw(raw);
|
||||
return `null`;
|
||||
}
|
||||
if (typeof func !== `function`) {
|
||||
throw new TypeError(`${wrapText(func)} is not a function.`);
|
||||
}
|
||||
const fm = raw ? fmFlags.raw : null;
|
||||
return formatValue({value: resolveFunc(func, cc), fm, cc});
|
||||
},
|
||||
|
||||
/**
|
||||
* @method formatting.format
|
||||
* @description
|
||||
* Replaces variables in a string according to the type of `values`:
|
||||
*
|
||||
* - Replaces `$1` occurrences when `values` is of type `string`, `boolean`, `number`, `bigint`, `Date`, `Buffer` or when it is `null`.
|
||||
*
|
||||
* - Replaces variables `$1`, `$2`, ...`$100000` when `values` is an array of parameters. It throws a {@link external:RangeError RangeError}
|
||||
* when the values or variables are out of range.
|
||||
*
|
||||
* - Replaces `$*propName*`, where `*` is any of `{}`, `()`, `[]`, `<>`, `//`, when `values` is an object that's not a
|
||||
* `Date`, `Buffer`, {@link QueryFile} or `null`. Special property name `this` refers to the formatting object itself,
|
||||
* to be injected as a JSON string. When referencing a property that doesn't exist in the formatting object, it throws
|
||||
* {@link external:Error Error} = `Property 'PropName' doesn't exist`, unless option `partial` is used.
|
||||
*
|
||||
* - Supports $[Nested Named Parameters] of any depth.
|
||||
*
|
||||
* By default, each variable is automatically formatted according to its type, unless it is a special variable:
|
||||
*
|
||||
* - Raw-text variables end with `:raw` or symbol `^`, and prevent escaping the text. Such variables are not
|
||||
* allowed to be `null` or `undefined`, or the method will throw {@link external:TypeError TypeError} = `Values null/undefined cannot be used as raw text.`
|
||||
* - `$1:raw`, `$2:raw`,..., and `$*propName:raw*` (see `*` above)
|
||||
* - `$1^`, `$2^`,..., and `$*propName^*` (see `*` above)
|
||||
*
|
||||
* - Open-value variables end with `:value` or symbol `#`, to be escaped, but not wrapped in quotes. Such variables are
|
||||
* not allowed to be `null` or `undefined`, or the method will throw {@link external:TypeError TypeError} = `Open values cannot be null or undefined.`
|
||||
* - `$1:value`, `$2:value`,..., and `$*propName:value*` (see `*` above)
|
||||
* - `$1#`, `$2#`,..., and `$*propName#*` (see `*` above)
|
||||
*
|
||||
* - SQL name variables end with `:name` or symbol `~` (tilde), and provide proper escaping for SQL names/identifiers:
|
||||
* - `$1:name`, `$2:name`,..., and `$*propName:name*` (see `*` above)
|
||||
* - `$1~`, `$2~`,..., and `$*propName~*` (see `*` above)
|
||||
*
|
||||
* - Modifier `:alias` - non-verbose $[SQL Names] escaping.
|
||||
*
|
||||
* - JSON override ends with `:json` to format the value of any type as a JSON string
|
||||
*
|
||||
* - CSV override ends with `:csv` or `:list` to format an array as a properly escaped comma-separated list of values.
|
||||
*
|
||||
* @param {string|QueryFile|object} query
|
||||
* A query string, a {@link QueryFile} or any object that implements $[Custom Type Formatting], to be formatted according to `values`.
|
||||
*
|
||||
* @param {array|object|value} [values]
|
||||
* Formatting parameter(s) / variable value(s).
|
||||
*
|
||||
* @param {{}} [options]
|
||||
* Formatting Options.
|
||||
*
|
||||
* @param {boolean} [options.capSQL=false]
|
||||
* Formats reserved SQL words capitalized. Presently, this only concerns arrays, to output `ARRAY` when required.
|
||||
*
|
||||
* @param {boolean} [options.partial=false]
|
||||
* Indicates that we intend to do only a partial replacement, i.e. throw no error when encountering a variable or
|
||||
* property name that's missing within the formatting parameters.
|
||||
*
|
||||
* **NOTE:** This option has no meaning when option `def` is used.
|
||||
*
|
||||
* @param {*} [options.def]
|
||||
* Sets default value for every variable that's missing, consequently preventing errors when encountering a variable
|
||||
* or property name that's missing within the formatting parameters.
|
||||
*
|
||||
* It can also be set to a function, to be called with two parameters that depend on the type of formatting being used,
|
||||
* and to return the actual default value:
|
||||
*
|
||||
* - For $[Named Parameters] formatting:
|
||||
* - `name` - name of the property missing in the formatting object
|
||||
* - `obj` - the formatting object, and is the same as `this` context
|
||||
*
|
||||
* - For $[Index Variables] formatting:
|
||||
* - `index` - element's index (starts with 1) that's outside of the input array
|
||||
* - `arr` - the formatting/input array, and is the same as `this` context
|
||||
*
|
||||
* You can tell which type of call it is by checking the type of the first parameter.
|
||||
*
|
||||
* @returns {string}
|
||||
* Formatted query string.
|
||||
*
|
||||
* The function will throw an error, if any occurs during formatting.
|
||||
*/
|
||||
format(query, values, options) {
|
||||
options = assert(options, [`capSQL`, `partial`, `def`]);
|
||||
const ctf = getCTF(query);
|
||||
if (ctf) {
|
||||
query = ctf.toPostgres.call(query, query);
|
||||
}
|
||||
return formatQuery(query, values, false, options);
|
||||
}
|
||||
};
|
||||
|
||||
/* Pre-parsed type formatting */
|
||||
const $to = {
|
||||
array(arr, options) {
|
||||
return formatArray(arr, options);
|
||||
},
|
||||
csv(values, options) {
|
||||
return formatCSV(resolveFunc(values), options);
|
||||
},
|
||||
bool(value) {
|
||||
return value ? `true` : `false`;
|
||||
},
|
||||
buffer(obj, raw) {
|
||||
const s = `\\x${obj.toString(`hex`)}`;
|
||||
return raw ? s : wrapText(s);
|
||||
},
|
||||
date(d, raw) {
|
||||
const s = npm.pgUtils.prepareValue(d);
|
||||
return raw ? s : wrapText(s);
|
||||
},
|
||||
json(data, raw) {
|
||||
const s = npm.utils.toJson(data);
|
||||
return raw ? s : wrapText(safeText(s));
|
||||
},
|
||||
number(num) {
|
||||
if (typeof num === `bigint` || Number.isFinite(num)) {
|
||||
return num.toString();
|
||||
}
|
||||
// Converting NaN/+Infinity/-Infinity according to Postgres documentation:
|
||||
// http://www.postgresql.org/docs/9.6/static/datatype-numeric.html#DATATYPE-FLOAT
|
||||
//
|
||||
// NOTE: strings for 'NaN'/'+Infinity'/'-Infinity' are not case-sensitive.
|
||||
if (num === Number.POSITIVE_INFINITY) {
|
||||
return wrapText(`+Infinity`);
|
||||
}
|
||||
if (num === Number.NEGATIVE_INFINITY) {
|
||||
return wrapText(`-Infinity`);
|
||||
}
|
||||
return wrapText(`NaN`);
|
||||
},
|
||||
text(value, raw) {
|
||||
return raw ? value : wrapText(safeText(value));
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = {
|
||||
formatQuery,
|
||||
formatEntity,
|
||||
resolveFunc,
|
||||
as: $as
|
||||
};
|
||||
|
||||
/**
|
||||
* @external Error
|
||||
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error
|
||||
*/
|
||||
|
||||
/**
|
||||
* @external TypeError
|
||||
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/TypeError
|
||||
*/
|
||||
|
||||
/**
|
||||
* @external RangeError
|
||||
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RangeError
|
||||
*/
|
||||
|
||||
/**
|
||||
* @external Symbol
|
||||
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol
|
||||
*/
|
||||
10
ProjectSourceCode/node_modules/pg-promise/lib/helpers/README.md
generated
vendored
Normal file
10
ProjectSourceCode/node_modules/pg-promise/lib/helpers/README.md
generated
vendored
Normal file
@@ -0,0 +1,10 @@
|
||||
### `helpers` namespace
|
||||
|
||||
This folder contains everything that's available via the [helpers] namespace, after initializing the library:
|
||||
|
||||
```js
|
||||
const pgp = require('pg-promise')(/*initialization options*/);
|
||||
const helpers = pgp.helpers; // `helpers` namespace
|
||||
```
|
||||
|
||||
[helpers]:http://vitaly-t.github.io/pg-promise/helpers.html
|
||||
647
ProjectSourceCode/node_modules/pg-promise/lib/helpers/column-set.js
generated
vendored
Normal file
647
ProjectSourceCode/node_modules/pg-promise/lib/helpers/column-set.js
generated
vendored
Normal file
@@ -0,0 +1,647 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {InnerState} = require(`../inner-state`);
|
||||
const {assert} = require(`../assert`);
|
||||
const {TableName} = require(`./table-name`);
|
||||
const {Column} = require(`./column`);
|
||||
|
||||
const npm = {
|
||||
os: require(`os`),
|
||||
utils: require(`../utils`),
|
||||
formatting: require(`../formatting`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @class helpers.ColumnSet
|
||||
* @description
|
||||
* Performance-optimized, read-only structure with query-formatting columns.
|
||||
*
|
||||
* In order to avail from performance optimization provided by this class, it should be created
|
||||
* only once, statically, and then reused.
|
||||
*
|
||||
* @param {object|helpers.Column|array} columns
|
||||
* Columns information object, depending on the type:
|
||||
*
|
||||
* - When it is a simple object, its properties are enumerated to represent both column names and property names
|
||||
* within the source objects. See also option `inherit` that's applicable in this case.
|
||||
*
|
||||
* - When it is a single {@link helpers.Column Column} object, property {@link helpers.ColumnSet#columns columns} is initialized with
|
||||
* just a single column. It is not a unique situation when only a single column is required for an update operation.
|
||||
*
|
||||
* - When it is an array, each element is assumed to represent details for a column. If the element is already of type {@link helpers.Column Column},
|
||||
* it is used directly; otherwise the element is passed into {@link helpers.Column Column} constructor for initialization.
|
||||
* On any duplicate column name (case-sensitive) it will throw {@link external:Error Error} = `Duplicate column name "name".`
|
||||
*
|
||||
* - When it is none of the above, it will throw {@link external:TypeError TypeError} = `Invalid parameter 'columns' specified.`
|
||||
*
|
||||
* @param {object} [options]
|
||||
*
|
||||
* @param {helpers.TableName|string|{table,schema}} [options.table]
|
||||
* Table details.
|
||||
*
|
||||
* When it is a non-null value, and not a {@link helpers.TableName TableName} object, a new {@link helpers.TableName TableName} is constructed from the value.
|
||||
*
|
||||
* It can be used as the default for methods {@link helpers.insert insert} and {@link helpers.update update} when their parameter
|
||||
* `table` is omitted, and for logging purposes.
|
||||
*
|
||||
* @param {boolean} [options.inherit = false]
|
||||
* Use inherited properties in addition to the object's own properties.
|
||||
*
|
||||
* By default, only the object's own properties are enumerated for column names.
|
||||
*
|
||||
* @returns {helpers.ColumnSet}
|
||||
*
|
||||
* @see
|
||||
*
|
||||
* {@link helpers.ColumnSet#columns columns},
|
||||
* {@link helpers.ColumnSet#names names},
|
||||
* {@link helpers.ColumnSet#table table},
|
||||
* {@link helpers.ColumnSet#variables variables} |
|
||||
* {@link helpers.ColumnSet#assign assign},
|
||||
* {@link helpers.ColumnSet#assignColumns assignColumns},
|
||||
* {@link helpers.ColumnSet#extend extend},
|
||||
* {@link helpers.ColumnSet#merge merge},
|
||||
* {@link helpers.ColumnSet#prepare prepare}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // A complex insert/update object scenario for table 'purchases' in schema 'fiscal'.
|
||||
* // For a good performance, you should declare such objects once and then reuse them.
|
||||
* //
|
||||
* // Column Requirements:
|
||||
* //
|
||||
* // 1. Property 'id' is only to be used for a WHERE condition in updates
|
||||
* // 2. Property 'list' needs to be formatted as a csv
|
||||
* // 3. Property 'code' is to be used as raw text, and to be defaulted to 0 when the
|
||||
* // property is missing in the source object
|
||||
* // 4. Property 'log' is a JSON object with 'log-entry' for the column name
|
||||
* // 5. Property 'data' requires SQL type casting '::int[]'
|
||||
* // 6. Property 'amount' needs to be set to 100, if it is 0
|
||||
* // 7. Property 'total' must be skipped during updates, if 'amount' was 0, plus its
|
||||
* // column name is 'total-val'
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet([
|
||||
* '?id', // ColumnConfig equivalent: {name: 'id', cnd: true}
|
||||
* 'list:csv', // ColumnConfig equivalent: {name: 'list', mod: ':csv'}
|
||||
* {
|
||||
* name: 'code',
|
||||
* mod: '^', // format as raw text
|
||||
* def: 0 // default to 0 when the property doesn't exist
|
||||
* },
|
||||
* {
|
||||
* name: 'log-entry',
|
||||
* prop: 'log',
|
||||
* mod: ':json' // format as JSON
|
||||
* },
|
||||
* {
|
||||
* name: 'data',
|
||||
* cast: 'int[]' // use SQL type casting '::int[]'
|
||||
* },
|
||||
* {
|
||||
* name: 'amount',
|
||||
* init(col) {
|
||||
* // set to 100, if the value is 0:
|
||||
* return col.value === 0 ? 100 : col.value;
|
||||
* }
|
||||
* },
|
||||
* {
|
||||
* name: 'total-val',
|
||||
* prop: 'total',
|
||||
* skip(col) {
|
||||
* // skip from updates, if 'amount' is 0:
|
||||
* return col.source.amount === 0;
|
||||
* }
|
||||
* }
|
||||
* ], {table: {table: 'purchases', schema: 'fiscal'}});
|
||||
*
|
||||
* // Alternatively, you could take the table declaration out:
|
||||
* // const table = new pgp.helpers.TableName('purchases', 'fiscal');
|
||||
*
|
||||
* console.log(cs); // console output for the object:
|
||||
* //=>
|
||||
* // ColumnSet {
|
||||
* // table: "fiscal"."purchases"
|
||||
* // columns: [
|
||||
* // Column {
|
||||
* // name: "id"
|
||||
* // cnd: true
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "list"
|
||||
* // mod: ":csv"
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "code"
|
||||
* // mod: "^"
|
||||
* // def: 0
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "log-entry"
|
||||
* // prop: "log"
|
||||
* // mod: ":json"
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "data"
|
||||
* // cast: "int[]"
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "amount"
|
||||
* // init: [Function]
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "total-val"
|
||||
* // prop: "total"
|
||||
* // skip: [Function]
|
||||
* // }
|
||||
* // ]
|
||||
* // }
|
||||
*/
|
||||
class ColumnSet extends InnerState {
|
||||
|
||||
constructor(columns, opt) {
|
||||
super();
|
||||
|
||||
if (!columns || typeof columns !== `object`) {
|
||||
throw new TypeError(`Invalid parameter 'columns' specified.`);
|
||||
}
|
||||
|
||||
opt = assert(opt, [`table`, `inherit`]);
|
||||
|
||||
if (!npm.utils.isNull(opt.table)) {
|
||||
this.table = (opt.table instanceof TableName) ? opt.table : new TableName(opt.table);
|
||||
}
|
||||
|
||||
/**
|
||||
* @name helpers.ColumnSet#table
|
||||
* @type {helpers.TableName}
|
||||
* @readonly
|
||||
* @description
|
||||
* Destination table. It can be specified for two purposes:
|
||||
*
|
||||
* - **primary:** to be used as the default table when it is omitted during a call into methods {@link helpers.insert insert} and {@link helpers.update update}
|
||||
* - **secondary:** to be automatically written into the console (for logging purposes).
|
||||
*/
|
||||
|
||||
|
||||
/**
|
||||
* @name helpers.ColumnSet#columns
|
||||
* @type helpers.Column[]
|
||||
* @readonly
|
||||
* @description
|
||||
* Array of {@link helpers.Column Column} objects.
|
||||
*/
|
||||
if (Array.isArray(columns)) {
|
||||
const colNames = {};
|
||||
this.columns = columns.map(c => {
|
||||
const col = (c instanceof Column) ? c : new Column(c);
|
||||
if (col.name in colNames) {
|
||||
throw new Error(`Duplicate column name "${col.name}".`);
|
||||
}
|
||||
colNames[col.name] = true;
|
||||
return col;
|
||||
});
|
||||
} else {
|
||||
if (columns instanceof Column) {
|
||||
this.columns = [columns];
|
||||
} else {
|
||||
this.columns = [];
|
||||
for (const name in columns) {
|
||||
if (opt.inherit || Object.prototype.hasOwnProperty.call(columns, name)) {
|
||||
this.columns.push(new Column(name));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Object.freeze(this.columns);
|
||||
Object.freeze(this);
|
||||
|
||||
this.extendState({
|
||||
names: undefined,
|
||||
variables: undefined,
|
||||
updates: undefined,
|
||||
isSimple: true
|
||||
});
|
||||
|
||||
for (let i = 0; i < this.columns.length; i++) {
|
||||
const c = this.columns[i];
|
||||
// ColumnSet is simple when the source objects require no preparation,
|
||||
// and should be used directly:
|
||||
if (c.prop || c.init || `def` in c) {
|
||||
this._inner.isSimple = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @name helpers.ColumnSet#names
|
||||
* @type string
|
||||
* @readonly
|
||||
* @description
|
||||
* Returns a string - comma-separated list of all column names, properly escaped.
|
||||
*
|
||||
* @example
|
||||
* const cs = new ColumnSet(['id^', {name: 'cells', cast: 'int[]'}, 'doc:json']);
|
||||
* console.log(cs.names);
|
||||
* //=> "id","cells","doc"
|
||||
*/
|
||||
get names() {
|
||||
const _i = this._inner;
|
||||
if (!_i.names) {
|
||||
_i.names = this.columns.map(c => c.escapedName).join();
|
||||
}
|
||||
return _i.names;
|
||||
}
|
||||
|
||||
/**
|
||||
* @name helpers.ColumnSet#variables
|
||||
* @type string
|
||||
* @readonly
|
||||
* @description
|
||||
* Returns a string - formatting template for all column values.
|
||||
*
|
||||
* @see {@link helpers.ColumnSet#assign assign}
|
||||
*
|
||||
* @example
|
||||
* const cs = new ColumnSet(['id^', {name: 'cells', cast: 'int[]'}, 'doc:json']);
|
||||
* console.log(cs.variables);
|
||||
* //=> ${id^},${cells}::int[],${doc:json}
|
||||
*/
|
||||
get variables() {
|
||||
const _i = this._inner;
|
||||
if (!_i.variables) {
|
||||
_i.variables = this.columns.map(c => c.variable + c.castText).join();
|
||||
}
|
||||
return _i.variables;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @method helpers.ColumnSet#assign
|
||||
* @description
|
||||
* Returns a formatting template of SET assignments, either generic or for a single object.
|
||||
*
|
||||
* The method is optimized to cache the output string when there are no columns that can be skipped dynamically.
|
||||
*
|
||||
* This method is primarily for internal use, that's why it does not validate the input.
|
||||
*
|
||||
* @param {object} [options]
|
||||
* Assignment/formatting options.
|
||||
*
|
||||
* @param {object} [options.source]
|
||||
* Source - a single object that contains values for columns.
|
||||
*
|
||||
* The object is only necessary to correctly apply the logic of skipping columns dynamically, based on the source data
|
||||
* and the rules defined in the {@link helpers.ColumnSet ColumnSet}. If, however, you do not care about that, then you do not need to specify any object.
|
||||
*
|
||||
* Note that even if you do not specify the object, the columns marked as conditional (`cnd: true`) will always be skipped.
|
||||
*
|
||||
* @param {string} [options.prefix]
|
||||
* In cases where needed, an alias prefix to be added before each column.
|
||||
*
|
||||
* @returns {string}
|
||||
* Comma-separated list of variable-to-column assignments.
|
||||
*
|
||||
* @see {@link helpers.ColumnSet#variables variables}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet([
|
||||
* '?first', // = {name: 'first', cnd: true}
|
||||
* 'second:json',
|
||||
* {name: 'third', mod: ':raw', cast: 'text'}
|
||||
* ]);
|
||||
*
|
||||
* cs.assign();
|
||||
* //=> "second"=${second:json},"third"=${third:raw}::text
|
||||
*
|
||||
* cs.assign({prefix: 'a b c'});
|
||||
* //=> "a b c"."second"=${second:json},"a b c"."third"=${third:raw}::text
|
||||
*/
|
||||
ColumnSet.prototype.assign = function (options) {
|
||||
const _i = this._inner;
|
||||
const hasPrefix = options && options.prefix && typeof options.prefix === `string`;
|
||||
if (_i.updates && !hasPrefix) {
|
||||
return _i.updates;
|
||||
}
|
||||
let dynamic = hasPrefix;
|
||||
const hasSource = options && options.source && typeof options.source === `object`;
|
||||
let list = this.columns.filter(c => {
|
||||
if (c.cnd) {
|
||||
return false;
|
||||
}
|
||||
if (c.skip) {
|
||||
dynamic = true;
|
||||
if (hasSource) {
|
||||
const a = colDesc(c, options.source);
|
||||
if (c.skip.call(options.source, a)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
});
|
||||
|
||||
const prefix = hasPrefix ? npm.formatting.as.alias(options.prefix) + `.` : ``;
|
||||
list = list.map(c => prefix + c.escapedName + `=` + c.variable + c.castText).join();
|
||||
|
||||
if (!dynamic) {
|
||||
_i.updates = list;
|
||||
}
|
||||
return list;
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.ColumnSet#assignColumns
|
||||
* @description
|
||||
* Generates assignments for all columns in the set, with support for aliases and column-skipping logic.
|
||||
* Aliases are set by using method {@link formatting.alias as.alias}.
|
||||
*
|
||||
* @param {{}} [options]
|
||||
* Optional Parameters.
|
||||
*
|
||||
* @param {string} [options.from]
|
||||
* Alias for the source columns.
|
||||
*
|
||||
* @param {string} [options.to]
|
||||
* Alias for the destination columns.
|
||||
*
|
||||
* @param {string | Array<string> | function} [options.skip]
|
||||
* Name(s) of the column(s) to be skipped (case-sensitive). It can be either a single string or an array of strings.
|
||||
*
|
||||
* It can also be a function - iterator, to be called for every column, passing in {@link helpers.Column Column} as
|
||||
* `this` context, and plus as a single parameter. The function would return a truthy value for every column that needs to be skipped.
|
||||
*
|
||||
* @returns {string}
|
||||
* A string of comma-separated column assignments.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['id', 'city', 'street']);
|
||||
*
|
||||
* cs.assignColumns({from: 'EXCLUDED', skip: 'id'})
|
||||
* //=> "city"=EXCLUDED."city","street"=EXCLUDED."street"
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['?id', 'city', 'street']);
|
||||
*
|
||||
* cs.assignColumns({from: 'source', to: 'target', skip: c => c.cnd})
|
||||
* //=> target."city"=source."city",target."street"=source."street"
|
||||
*
|
||||
*/
|
||||
ColumnSet.prototype.assignColumns = function (options) {
|
||||
options = assert(options, [`from`, `to`, `skip`]);
|
||||
const skip = (typeof options.skip === `string` && [options.skip]) || ((Array.isArray(options.skip) || typeof options.skip === `function`) && options.skip);
|
||||
const from = (typeof options.from === `string` && options.from && (npm.formatting.as.alias(options.from) + `.`)) || ``;
|
||||
const to = (typeof options.to === `string` && options.to && (npm.formatting.as.alias(options.to) + `.`)) || ``;
|
||||
const iterator = typeof skip === `function` ? c => !skip.call(c, c) : c => skip.indexOf(c.name) === -1;
|
||||
const cols = skip ? this.columns.filter(iterator) : this.columns;
|
||||
return cols.map(c => to + c.escapedName + `=` + from + c.escapedName).join();
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.ColumnSet#extend
|
||||
* @description
|
||||
* Creates a new {@link helpers.ColumnSet ColumnSet}, by joining the two sets of columns.
|
||||
*
|
||||
* If the two sets contain a column with the same `name` (case-sensitive), an error is thrown.
|
||||
*
|
||||
* @param {helpers.Column|helpers.ColumnSet|array} columns
|
||||
* Columns to be appended, of the same type as parameter `columns` during {@link helpers.ColumnSet ColumnSet} construction, except:
|
||||
* - it can also be of type {@link helpers.ColumnSet ColumnSet}
|
||||
* - it cannot be a simple object (properties enumeration is not supported here)
|
||||
*
|
||||
* @returns {helpers.ColumnSet}
|
||||
* New {@link helpers.ColumnSet ColumnSet} object with the extended/concatenated list of columns.
|
||||
*
|
||||
* @see
|
||||
* {@link helpers.Column Column},
|
||||
* {@link helpers.ColumnSet#merge merge}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const pgp = require('pg-promise')();
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['one', 'two'], {table: 'my-table'});
|
||||
* console.log(cs);
|
||||
* //=>
|
||||
* // ColumnSet {
|
||||
* // table: "my-table"
|
||||
* // columns: [
|
||||
* // Column {
|
||||
* // name: "one"
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "two"
|
||||
* // }
|
||||
* // ]
|
||||
* // }
|
||||
* const csExtended = cs.extend(['three']);
|
||||
* console.log(csExtended);
|
||||
* //=>
|
||||
* // ColumnSet {
|
||||
* // table: "my-table"
|
||||
* // columns: [
|
||||
* // Column {
|
||||
* // name: "one"
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "two"
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "three"
|
||||
* // }
|
||||
* // ]
|
||||
* // }
|
||||
*/
|
||||
ColumnSet.prototype.extend = function (columns) {
|
||||
let cs = columns;
|
||||
if (!(cs instanceof ColumnSet)) {
|
||||
cs = new ColumnSet(columns);
|
||||
}
|
||||
// Any duplicate column will throw Error = 'Duplicate column name "name".',
|
||||
return new ColumnSet(this.columns.concat(cs.columns), {table: this.table});
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.ColumnSet#merge
|
||||
* @description
|
||||
* Creates a new {@link helpers.ColumnSet ColumnSet}, by joining the two sets of columns.
|
||||
*
|
||||
* Items in `columns` with the same `name` (case-sensitive) override the original columns.
|
||||
*
|
||||
* @param {helpers.Column|helpers.ColumnSet|array} columns
|
||||
* Columns to be appended, of the same type as parameter `columns` during {@link helpers.ColumnSet ColumnSet} construction, except:
|
||||
* - it can also be of type {@link helpers.ColumnSet ColumnSet}
|
||||
* - it cannot be a simple object (properties enumeration is not supported here)
|
||||
*
|
||||
* @see
|
||||
* {@link helpers.Column Column},
|
||||
* {@link helpers.ColumnSet#extend extend}
|
||||
*
|
||||
* @returns {helpers.ColumnSet}
|
||||
* New {@link helpers.ColumnSet ColumnSet} object with the merged list of columns.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const pgp = require('pg-promise')();
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['?one', 'two:json'], {table: 'my-table'});
|
||||
* console.log(cs);
|
||||
* //=>
|
||||
* // ColumnSet {
|
||||
* // table: "my-table"
|
||||
* // columns: [
|
||||
* // Column {
|
||||
* // name: "one"
|
||||
* // cnd: true
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "two"
|
||||
* // mod: ":json"
|
||||
* // }
|
||||
* // ]
|
||||
* // }
|
||||
* const csMerged = cs.merge(['two', 'three^']);
|
||||
* console.log(csMerged);
|
||||
* //=>
|
||||
* // ColumnSet {
|
||||
* // table: "my-table"
|
||||
* // columns: [
|
||||
* // Column {
|
||||
* // name: "one"
|
||||
* // cnd: true
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "two"
|
||||
* // }
|
||||
* // Column {
|
||||
* // name: "three"
|
||||
* // mod: "^"
|
||||
* // }
|
||||
* // ]
|
||||
* // }
|
||||
*
|
||||
*/
|
||||
ColumnSet.prototype.merge = function (columns) {
|
||||
let cs = columns;
|
||||
if (!(cs instanceof ColumnSet)) {
|
||||
cs = new ColumnSet(columns);
|
||||
}
|
||||
const colNames = {}, cols = [];
|
||||
this.columns.forEach((c, idx) => {
|
||||
cols.push(c);
|
||||
colNames[c.name] = idx;
|
||||
});
|
||||
cs.columns.forEach(c => {
|
||||
if (c.name in colNames) {
|
||||
cols[colNames[c.name]] = c;
|
||||
} else {
|
||||
cols.push(c);
|
||||
}
|
||||
});
|
||||
return new ColumnSet(cols, {table: this.table});
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.ColumnSet#prepare
|
||||
* @description
|
||||
* Prepares a source object to be formatted, by cloning it and applying the rules as set by the
|
||||
* columns configuration.
|
||||
*
|
||||
* This method is primarily for internal use, that's why it does not validate the input parameters.
|
||||
*
|
||||
* @param {object} source
|
||||
* The source object to be prepared, if required.
|
||||
*
|
||||
* It must be a non-`null` object, which the method does not validate, as it is
|
||||
* intended primarily for internal use by the library.
|
||||
*
|
||||
* @returns {object}
|
||||
* When the object needs to be prepared, the method returns a clone of the source object,
|
||||
* with all properties and values set according to the columns configuration.
|
||||
*
|
||||
* When the object does not need to be prepared, the original object is returned.
|
||||
*/
|
||||
ColumnSet.prototype.prepare = function (source) {
|
||||
if (this._inner.isSimple) {
|
||||
return source; // a simple ColumnSet requires no object preparation;
|
||||
}
|
||||
const target = {};
|
||||
this.columns.forEach(c => {
|
||||
const a = colDesc(c, source);
|
||||
if (c.init) {
|
||||
target[a.name] = c.init.call(source, a);
|
||||
} else {
|
||||
if (a.exists || `def` in c) {
|
||||
target[a.name] = a.value;
|
||||
}
|
||||
}
|
||||
});
|
||||
return target;
|
||||
};
|
||||
|
||||
function colDesc(column, source) {
|
||||
const a = {
|
||||
source,
|
||||
name: column.prop || column.name
|
||||
};
|
||||
a.exists = a.name in source;
|
||||
if (a.exists) {
|
||||
a.value = source[a.name];
|
||||
} else {
|
||||
a.value = `def` in column ? column.def : undefined;
|
||||
}
|
||||
return a;
|
||||
}
|
||||
|
||||
/**
|
||||
* @method helpers.ColumnSet#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the object.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
ColumnSet.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap0 = npm.utils.messageGap(level),
|
||||
gap1 = npm.utils.messageGap(level + 1),
|
||||
lines = [
|
||||
`ColumnSet {`
|
||||
];
|
||||
if (this.table) {
|
||||
lines.push(gap1 + `table: ` + this.table);
|
||||
}
|
||||
if (this.columns.length) {
|
||||
lines.push(gap1 + `columns: [`);
|
||||
this.columns.forEach(c => {
|
||||
lines.push(c.toString(2));
|
||||
});
|
||||
lines.push(gap1 + `]`);
|
||||
} else {
|
||||
lines.push(gap1 + `columns: []`);
|
||||
}
|
||||
lines.push(gap0 + `}`);
|
||||
return lines.join(npm.os.EOL);
|
||||
};
|
||||
|
||||
npm.utils.addInspection(ColumnSet, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
module.exports = {ColumnSet};
|
||||
455
ProjectSourceCode/node_modules/pg-promise/lib/helpers/column.js
generated
vendored
Normal file
455
ProjectSourceCode/node_modules/pg-promise/lib/helpers/column.js
generated
vendored
Normal file
@@ -0,0 +1,455 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {InnerState} = require(`../inner-state`);
|
||||
const {assert} = require(`../assert`);
|
||||
|
||||
const npm = {
|
||||
os: require(`os`),
|
||||
utils: require(`../utils`),
|
||||
formatting: require(`../formatting`),
|
||||
patterns: require(`../patterns`)
|
||||
};
|
||||
|
||||
/**
|
||||
*
|
||||
* @class helpers.Column
|
||||
* @description
|
||||
*
|
||||
* Read-only structure with details for a single column. Used primarily by {@link helpers.ColumnSet ColumnSet}.
|
||||
*
|
||||
* The class parses details into a template, to be used for query generation.
|
||||
*
|
||||
* @param {string|helpers.ColumnConfig} col
|
||||
* Column details, depending on the type.
|
||||
*
|
||||
* When it is a string, it is expected to contain a name for both the column and the source property, assuming that the two are the same.
|
||||
* The name must adhere to JavaScript syntax for variable names. The name can be appended with any format modifier as supported by
|
||||
* {@link formatting.format as.format} (`^`, `~`, `#`, `:csv`, `:list`, `:json`, `:alias`, `:name`, `:raw`, `:value`), which is then removed from the name and put
|
||||
* into property `mod`. If the name starts with `?`, it is removed, while setting flag `cnd` = `true`.
|
||||
*
|
||||
* If the string doesn't adhere to the above requirements, the method will throw {@link external:TypeError TypeError} = `Invalid column syntax`.
|
||||
*
|
||||
* When `col` is a simple {@link helpers.ColumnConfig ColumnConfig}-like object, it is used as an input configurator to set all the properties
|
||||
* of the class.
|
||||
*
|
||||
* @property {string} name
|
||||
* Destination column name + source property name (if `prop` is skipped). The name must adhere to JavaScript syntax for variables,
|
||||
* unless `prop` is specified, in which case `name` represents only the column name, and therefore can be any non-empty string.
|
||||
*
|
||||
* @property {string} [prop]
|
||||
* Source property name, if different from the column's name. It must adhere to JavaScript syntax for variables.
|
||||
*
|
||||
* It is ignored when it is the same as `name`.
|
||||
*
|
||||
* @property {string} [mod]
|
||||
* Formatting modifier, as supported by method {@link formatting.format as.format}: `^`, `~`, `#`, `:csv`, `:list`, `:json`, `:alias`, `:name`, `:raw`, `:value`.
|
||||
*
|
||||
* @property {string} [cast]
|
||||
* Server-side type casting, without `::` in front.
|
||||
*
|
||||
* @property {boolean} [cnd]
|
||||
* Conditional column flag.
|
||||
*
|
||||
* Used by methods {@link helpers.update update} and {@link helpers.sets sets}, ignored by methods {@link helpers.insert insert} and
|
||||
* {@link helpers.values values}. It indicates that the column is reserved for a `WHERE` condition, not to be set or updated.
|
||||
*
|
||||
* It can be set from a string initialization, by adding `?` in front of the name.
|
||||
*
|
||||
* @property {*} [def]
|
||||
* Default value for the property, to be used only when the source object doesn't have the property.
|
||||
* It is ignored when property `init` is set.
|
||||
*
|
||||
* @property {helpers.initCB} [init]
|
||||
* Override callback for the value.
|
||||
*
|
||||
* @property {helpers.skipCB} [skip]
|
||||
* An override for skipping columns dynamically.
|
||||
*
|
||||
* Used by methods {@link helpers.update update} (for a single object) and {@link helpers.sets sets}, ignored by methods
|
||||
* {@link helpers.insert insert} and {@link helpers.values values}.
|
||||
*
|
||||
* It is also ignored when conditional flag `cnd` is set.
|
||||
*
|
||||
* @returns {helpers.Column}
|
||||
*
|
||||
* @see
|
||||
* {@link helpers.ColumnConfig ColumnConfig},
|
||||
* {@link helpers.Column#castText castText},
|
||||
* {@link helpers.Column#escapedName escapedName},
|
||||
* {@link helpers.Column#variable variable}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const pgp = require('pg-promise')({
|
||||
* capSQL: true // if you want all generated SQL capitalized
|
||||
* });
|
||||
*
|
||||
* const Column = pgp.helpers.Column;
|
||||
*
|
||||
* // creating a column from just a name:
|
||||
* const col1 = new Column('colName');
|
||||
* console.log(col1);
|
||||
* //=>
|
||||
* // Column {
|
||||
* // name: "colName"
|
||||
* // }
|
||||
*
|
||||
* // creating a column from a name + modifier:
|
||||
* const col2 = new Column('colName:csv');
|
||||
* console.log(col2);
|
||||
* //=>
|
||||
* // Column {
|
||||
* // name: "colName"
|
||||
* // mod: ":csv"
|
||||
* // }
|
||||
*
|
||||
* // creating a column from a configurator:
|
||||
* const col3 = new Column({
|
||||
* name: 'colName', // required
|
||||
* prop: 'propName', // optional
|
||||
* mod: '^', // optional
|
||||
* def: 123 // optional
|
||||
* });
|
||||
* console.log(col3);
|
||||
* //=>
|
||||
* // Column {
|
||||
* // name: "colName"
|
||||
* // prop: "propName"
|
||||
* // mod: "^"
|
||||
* // def: 123
|
||||
* // }
|
||||
*
|
||||
*/
|
||||
class Column extends InnerState {
|
||||
|
||||
constructor(col) {
|
||||
super();
|
||||
|
||||
if (typeof col === `string`) {
|
||||
const info = parseColumn(col);
|
||||
this.name = info.name;
|
||||
if (`mod` in info) {
|
||||
this.mod = info.mod;
|
||||
}
|
||||
if (`cnd` in info) {
|
||||
this.cnd = info.cnd;
|
||||
}
|
||||
} else {
|
||||
col = assert(col, [`name`, `prop`, `mod`, `cast`, `cnd`, `def`, `init`, `skip`]);
|
||||
if (`name` in col) {
|
||||
if (!npm.utils.isText(col.name)) {
|
||||
throw new TypeError(`Invalid 'name' value: ${npm.utils.toJson(col.name)}. A non-empty string was expected.`);
|
||||
}
|
||||
if (npm.utils.isNull(col.prop) && !isValidVariable(col.name)) {
|
||||
throw new TypeError(`Invalid 'name' syntax: ${npm.utils.toJson(col.name)}.`);
|
||||
}
|
||||
this.name = col.name; // column name + property name (if 'prop' isn't specified)
|
||||
|
||||
if (!npm.utils.isNull(col.prop)) {
|
||||
if (!npm.utils.isText(col.prop)) {
|
||||
throw new TypeError(`Invalid 'prop' value: ${npm.utils.toJson(col.prop)}. A non-empty string was expected.`);
|
||||
}
|
||||
if (!isValidVariable(col.prop)) {
|
||||
throw new TypeError(`Invalid 'prop' syntax: ${npm.utils.toJson(col.prop)}.`);
|
||||
}
|
||||
if (col.prop !== col.name) {
|
||||
// optional property name, if different from the column's name;
|
||||
this.prop = col.prop;
|
||||
}
|
||||
}
|
||||
if (!npm.utils.isNull(col.mod)) {
|
||||
if (typeof col.mod !== `string` || !isValidMod(col.mod)) {
|
||||
throw new TypeError(`Invalid 'mod' value: ${npm.utils.toJson(col.mod)}.`);
|
||||
}
|
||||
this.mod = col.mod; // optional format modifier;
|
||||
}
|
||||
if (!npm.utils.isNull(col.cast)) {
|
||||
this.cast = parseCast(col.cast); // optional SQL type casting
|
||||
}
|
||||
if (`cnd` in col) {
|
||||
this.cnd = !!col.cnd;
|
||||
}
|
||||
if (`def` in col) {
|
||||
this.def = col.def; // optional default
|
||||
}
|
||||
if (typeof col.init === `function`) {
|
||||
this.init = col.init; // optional value override (overrides 'def' also)
|
||||
}
|
||||
if (typeof col.skip === `function`) {
|
||||
this.skip = col.skip;
|
||||
}
|
||||
} else {
|
||||
throw new TypeError(`Invalid column details.`);
|
||||
}
|
||||
}
|
||||
|
||||
const variable = `\${` + (this.prop || this.name) + (this.mod || ``) + `}`;
|
||||
const castText = this.cast ? (`::` + this.cast) : ``;
|
||||
const escapedName = npm.formatting.as.name(this.name);
|
||||
|
||||
this.extendState({variable, castText, escapedName});
|
||||
Object.freeze(this);
|
||||
}
|
||||
|
||||
/**
|
||||
* @name helpers.Column#variable
|
||||
* @type string
|
||||
* @readonly
|
||||
* @description
|
||||
* Full-syntax formatting variable, ready for direct use in query templates.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet([
|
||||
* 'id',
|
||||
* 'coordinate:json',
|
||||
* {
|
||||
* name: 'places',
|
||||
* mod: ':csv',
|
||||
* cast: 'int[]'
|
||||
* }
|
||||
* ]);
|
||||
*
|
||||
* // cs.columns[0].variable = ${id}
|
||||
* // cs.columns[1].variable = ${coordinate:json}
|
||||
* // cs.columns[2].variable = ${places:csv}::int[]
|
||||
*/
|
||||
get variable() {
|
||||
return this._inner.variable;
|
||||
}
|
||||
|
||||
/**
|
||||
* @name helpers.Column#castText
|
||||
* @type string
|
||||
* @readonly
|
||||
* @description
|
||||
* Full-syntax sql type casting, if there is any, or else an empty string.
|
||||
*/
|
||||
get castText() {
|
||||
return this._inner.castText;
|
||||
}
|
||||
|
||||
/**
|
||||
* @name helpers.Column#escapedName
|
||||
* @type string
|
||||
* @readonly
|
||||
* @description
|
||||
* Escaped name of the column, ready to be injected into queries directly.
|
||||
*
|
||||
*/
|
||||
get escapedName() {
|
||||
return this._inner.escapedName;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
function parseCast(name) {
|
||||
if (typeof name === `string`) {
|
||||
const s = name.replace(/^[:\s]*|\s*$/g, ``);
|
||||
if (s) {
|
||||
return s;
|
||||
}
|
||||
}
|
||||
throw new TypeError(`Invalid 'cast' value: ${npm.utils.toJson(name)}.`);
|
||||
}
|
||||
|
||||
function parseColumn(name) {
|
||||
const m = name.match(npm.patterns.validColumn);
|
||||
if (m && m[0] === name) {
|
||||
const res = {};
|
||||
if (name[0] === `?`) {
|
||||
res.cnd = true;
|
||||
name = name.substr(1);
|
||||
}
|
||||
const mod = name.match(npm.patterns.hasValidModifier);
|
||||
if (mod) {
|
||||
res.name = name.substr(0, mod.index);
|
||||
res.mod = mod[0];
|
||||
} else {
|
||||
res.name = name;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
throw new TypeError(`Invalid column syntax: ${npm.utils.toJson(name)}.`);
|
||||
}
|
||||
|
||||
function isValidMod(mod) {
|
||||
return npm.patterns.validModifiers.indexOf(mod) !== -1;
|
||||
}
|
||||
|
||||
function isValidVariable(name) {
|
||||
const m = name.match(npm.patterns.validVariable);
|
||||
return !!m && m[0] === name;
|
||||
}
|
||||
|
||||
/**
|
||||
* @method helpers.Column#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the object.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
Column.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap0 = npm.utils.messageGap(level),
|
||||
gap1 = npm.utils.messageGap(level + 1),
|
||||
lines = [
|
||||
gap0 + `Column {`,
|
||||
gap1 + `name: ` + npm.utils.toJson(this.name)
|
||||
];
|
||||
if (`prop` in this) {
|
||||
lines.push(gap1 + `prop: ` + npm.utils.toJson(this.prop));
|
||||
}
|
||||
if (`mod` in this) {
|
||||
lines.push(gap1 + `mod: ` + npm.utils.toJson(this.mod));
|
||||
}
|
||||
if (`cast` in this) {
|
||||
lines.push(gap1 + `cast: ` + npm.utils.toJson(this.cast));
|
||||
}
|
||||
if (`cnd` in this) {
|
||||
lines.push(gap1 + `cnd: ` + npm.utils.toJson(this.cnd));
|
||||
}
|
||||
if (`def` in this) {
|
||||
lines.push(gap1 + `def: ` + npm.utils.toJson(this.def));
|
||||
}
|
||||
if (`init` in this) {
|
||||
lines.push(gap1 + `init: [Function]`);
|
||||
}
|
||||
if (`skip` in this) {
|
||||
lines.push(gap1 + `skip: [Function]`);
|
||||
}
|
||||
lines.push(gap0 + `}`);
|
||||
return lines.join(npm.os.EOL);
|
||||
};
|
||||
|
||||
npm.utils.addInspection(Column, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
/**
|
||||
* @typedef helpers.ColumnConfig
|
||||
* @description
|
||||
* A simple structure with column details, to be passed into the {@link helpers.Column Column} constructor for initialization.
|
||||
*
|
||||
* @property {string} name
|
||||
* Destination column name + source property name (if `prop` is skipped). The name must adhere to JavaScript syntax for variables,
|
||||
* unless `prop` is specified, in which case `name` represents only the column name, and therefore can be any non-empty string.
|
||||
*
|
||||
* @property {string} [prop]
|
||||
* Source property name, if different from the column's name. It must adhere to JavaScript syntax for variables.
|
||||
*
|
||||
* It is ignored when it is the same as `name`.
|
||||
*
|
||||
* @property {string} [mod]
|
||||
* Formatting modifier, as supported by method {@link formatting.format as.format}: `^`, `~`, `#`, `:csv`, `:list`, `:json`, `:alias`, `:name`, `:raw`, `:value`.
|
||||
*
|
||||
* @property {string} [cast]
|
||||
* Server-side type casting. Leading `::` is allowed, but not needed (automatically removed when specified).
|
||||
*
|
||||
* @property {boolean} [cnd]
|
||||
* Conditional column flag.
|
||||
*
|
||||
* Used by methods {@link helpers.update update} and {@link helpers.sets sets}, ignored by methods {@link helpers.insert insert} and
|
||||
* {@link helpers.values values}. It indicates that the column is reserved for a `WHERE` condition, not to be set or updated.
|
||||
*
|
||||
* It can be set from a string initialization, by adding `?` in front of the name.
|
||||
*
|
||||
* @property {*} [def]
|
||||
* Default value for the property, to be used only when the source object doesn't have the property.
|
||||
* It is ignored when property `init` is set.
|
||||
*
|
||||
* @property {helpers.initCB} [init]
|
||||
* Override callback for the value.
|
||||
*
|
||||
* @property {helpers.skipCB} [skip]
|
||||
* An override for skipping columns dynamically.
|
||||
*
|
||||
* Used by methods {@link helpers.update update} (for a single object) and {@link helpers.sets sets}, ignored by methods
|
||||
* {@link helpers.insert insert} and {@link helpers.values values}.
|
||||
*
|
||||
* It is also ignored when conditional flag `cnd` is set.
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* @callback helpers.initCB
|
||||
* @description
|
||||
* A callback function type used by parameter `init` within {@link helpers.ColumnConfig ColumnConfig}.
|
||||
*
|
||||
* It works as an override for the corresponding property value in the `source` object.
|
||||
*
|
||||
* The function is called with `this` set to the `source` object.
|
||||
*
|
||||
* @param {*} col
|
||||
* Column-to-property descriptor.
|
||||
*
|
||||
* @param {object} col.source
|
||||
* The source object, equals to `this` that's passed into the function.
|
||||
*
|
||||
* @param {string} col.name
|
||||
* Resolved name of the property within the `source` object, i.e. the value of `name` when `prop` is not used
|
||||
* for the column, or the value of `prop` when it is specified.
|
||||
*
|
||||
* @param {*} col.value
|
||||
*
|
||||
* Property value, set to one of the following:
|
||||
*
|
||||
* - Value of the property within the `source` object (`value` = `source[name]`), if the property exists
|
||||
* - If the property doesn't exist and `def` is set in the column, then `value` is set to the value of `def`
|
||||
* - If the property doesn't exist and `def` is not set in the column, then `value` is set to `undefined`
|
||||
*
|
||||
* @param {boolean} col.exists
|
||||
* Indicates whether the property exists in the `source` object (`exists = name in source`).
|
||||
*
|
||||
* @returns {*}
|
||||
* The new value to be used for the corresponding column.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @callback helpers.skipCB
|
||||
* @description
|
||||
* A callback function type used by parameter `skip` within {@link helpers.ColumnConfig ColumnConfig}.
|
||||
*
|
||||
* It is to dynamically determine when the property with specified `name` in the `source` object is to be skipped.
|
||||
*
|
||||
* The function is called with `this` set to the `source` object.
|
||||
*
|
||||
* @param {*} col
|
||||
* Column-to-property descriptor.
|
||||
*
|
||||
* @param {object} col.source
|
||||
* The source object, equals to `this` that's passed into the function.
|
||||
*
|
||||
* @param {string} col.name
|
||||
* Resolved name of the property within the `source` object, i.e. the value of `name` when `prop` is not used
|
||||
* for the column, or the value of `prop` when it is specified.
|
||||
*
|
||||
* @param {*} col.value
|
||||
*
|
||||
* Property value, set to one of the following:
|
||||
*
|
||||
* - Value of the property within the `source` object (`value` = `source[name]`), if the property exists
|
||||
* - If the property doesn't exist and `def` is set in the column, then `value` is set to the value of `def`
|
||||
* - If the property doesn't exist and `def` is not set in the column, then `value` is set to `undefined`
|
||||
*
|
||||
* @param {boolean} col.exists
|
||||
* Indicates whether the property exists in the `source` object (`exists = name in source`).
|
||||
*
|
||||
* @returns {boolean}
|
||||
* A truthy value that indicates whether the column is to be skipped.
|
||||
*
|
||||
*/
|
||||
|
||||
module.exports = {Column};
|
||||
73
ProjectSourceCode/node_modules/pg-promise/lib/helpers/index.js
generated
vendored
Normal file
73
ProjectSourceCode/node_modules/pg-promise/lib/helpers/index.js
generated
vendored
Normal file
@@ -0,0 +1,73 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {Column} = require(`./column`);
|
||||
const {ColumnSet} = require(`./column-set`);
|
||||
const {TableName} = require(`./table-name`);
|
||||
const method = require(`./methods`);
|
||||
const utils = require(`../utils`);
|
||||
|
||||
/**
|
||||
* @namespace helpers
|
||||
* @description
|
||||
* Namespace for query-formatting generators, available as {@link module:pg-promise~helpers pgp.helpers}, after initializing the library.
|
||||
*
|
||||
* It unifies the approach to generating multi-row `INSERT` / `UPDATE` queries with the single-row ones.
|
||||
*
|
||||
* See also: $[Performance Boost].
|
||||
*
|
||||
* @property {function} TableName
|
||||
* {@link helpers.TableName TableName} class constructor.
|
||||
*
|
||||
* @property {function} ColumnSet
|
||||
* {@link helpers.ColumnSet ColumnSet} class constructor.
|
||||
*
|
||||
* @property {function} Column
|
||||
* {@link helpers.Column Column} class constructor.
|
||||
*
|
||||
* @property {function} insert
|
||||
* {@link helpers.insert insert} static method.
|
||||
*
|
||||
* @property {function} update
|
||||
* {@link helpers.update update} static method.
|
||||
*
|
||||
* @property {function} values
|
||||
* {@link helpers.values values} static method.
|
||||
*
|
||||
* @property {function} sets
|
||||
* {@link helpers.sets sets} static method.
|
||||
*
|
||||
* @property {function} concat
|
||||
* {@link helpers.concat concat} static method.
|
||||
*/
|
||||
module.exports = config => {
|
||||
const capSQL = () => config.options && config.options.capSQL;
|
||||
const res = {
|
||||
insert(data, columns, table) {
|
||||
return method.insert(data, columns, table, capSQL());
|
||||
},
|
||||
update(data, columns, table, options) {
|
||||
return method.update(data, columns, table, options, capSQL());
|
||||
},
|
||||
concat(queries) {
|
||||
return method.concat(queries, capSQL());
|
||||
},
|
||||
values(data, columns) {
|
||||
return method.values(data, columns, capSQL());
|
||||
},
|
||||
sets(data, columns) {
|
||||
return method.sets(data, columns, capSQL());
|
||||
},
|
||||
TableName,
|
||||
ColumnSet,
|
||||
Column
|
||||
};
|
||||
utils.lock(res, true, config.options);
|
||||
return res;
|
||||
};
|
||||
103
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/concat.js
generated
vendored
Normal file
103
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/concat.js
generated
vendored
Normal file
@@ -0,0 +1,103 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {QueryFile} = require(`../../query-file`);
|
||||
|
||||
const npm = {
|
||||
formatting: require(`../../formatting`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.concat
|
||||
* @description
|
||||
* Formats and concatenates multiple queries into a single query string.
|
||||
*
|
||||
* Before joining the queries, the method does the following:
|
||||
* - Formats each query, if `values` are provided;
|
||||
* - Removes all leading and trailing spaces, tabs and semi-colons;
|
||||
* - Automatically skips all empty queries.
|
||||
*
|
||||
* @param {array<string|helpers.QueryFormat|QueryFile>} queries
|
||||
* Array of mixed-type elements:
|
||||
* - a simple query string, to be used as is
|
||||
* - a {@link helpers.QueryFormat QueryFormat}-like object = `{query, [values], [options]}`
|
||||
* - a {@link QueryFile} object
|
||||
*
|
||||
* @returns {string}
|
||||
* Concatenated string with all queries.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const pgp = require('pg-promise')();
|
||||
*
|
||||
* const qf1 = new pgp.QueryFile('./query1.sql', {minify: true});
|
||||
* const qf2 = new pgp.QueryFile('./query2.sql', {minify: true});
|
||||
*
|
||||
* const query = pgp.helpers.concat([
|
||||
* {query: 'INSERT INTO Users(name, age) VALUES($1, $2)', values: ['John', 23]}, // QueryFormat-like object
|
||||
* {query: qf1, values: [1, 'Name']}, // QueryFile with formatting parameters
|
||||
* 'SELECT count(*) FROM Users', // a simple-string query,
|
||||
* qf2 // direct QueryFile object
|
||||
* ]);
|
||||
*
|
||||
* // query = concatenated string with all the queries
|
||||
*/
|
||||
function concat(queries, capSQL) {
|
||||
if (!Array.isArray(queries)) {
|
||||
throw new TypeError(`Parameter 'queries' must be an array.`);
|
||||
}
|
||||
const fmOptions = {capSQL};
|
||||
const all = queries.map((q, index) => {
|
||||
if (typeof q === `string`) {
|
||||
// a simple query string without parameters:
|
||||
return clean(q);
|
||||
}
|
||||
if (q && typeof q === `object`) {
|
||||
if (q instanceof QueryFile) {
|
||||
// QueryFile object:
|
||||
return clean(q[npm.formatting.as.ctf.toPostgres]());
|
||||
}
|
||||
if (`query` in q) {
|
||||
// object {query, values, options}:
|
||||
let opt = q.options && typeof q.options === `object` ? q.options : {};
|
||||
opt = opt.capSQL === undefined ? Object.assign(opt, fmOptions) : opt;
|
||||
return clean(npm.formatting.as.format(q.query, q.values, opt));
|
||||
}
|
||||
}
|
||||
throw new Error(`Invalid query element at index ${index}.`);
|
||||
});
|
||||
|
||||
return all.filter(q => q).join(`;`);
|
||||
}
|
||||
|
||||
function clean(q) {
|
||||
// removes from the query all leading and trailing symbols ' ', '\t' and ';'
|
||||
return q.replace(/^[\s;]*|[\s;]*$/g, ``);
|
||||
}
|
||||
|
||||
module.exports = {concat};
|
||||
|
||||
/**
|
||||
* @typedef helpers.QueryFormat
|
||||
* @description
|
||||
* A simple structure of parameters to be passed into method {@link formatting.format as.format} exactly as they are,
|
||||
* used by {@link helpers.concat}.
|
||||
*
|
||||
* @property {string|value|object} query
|
||||
* A query string or a value/object that implements $[Custom Type Formatting], to be formatted according to `values`.
|
||||
*
|
||||
* @property {array|object|value} [values]
|
||||
* Query-formatting values.
|
||||
*
|
||||
* @property {object} [options]
|
||||
* Query-formatting options, as supported by method {@link formatting.format as.format}.
|
||||
*
|
||||
* @see
|
||||
* {@link formatting.format as.format}
|
||||
*/
|
||||
13
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/index.js
generated
vendored
Normal file
13
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/index.js
generated
vendored
Normal file
@@ -0,0 +1,13 @@
|
||||
const {concat} = require(`./concat`);
|
||||
const {insert} = require(`./insert`);
|
||||
const {update} = require(`./update`);
|
||||
const {values} = require(`./values`);
|
||||
const {sets} = require(`./sets`);
|
||||
|
||||
module.exports = {
|
||||
concat,
|
||||
insert,
|
||||
update,
|
||||
values,
|
||||
sets
|
||||
};
|
||||
148
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/insert.js
generated
vendored
Normal file
148
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/insert.js
generated
vendored
Normal file
@@ -0,0 +1,148 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {TableName} = require(`../table-name`);
|
||||
const {ColumnSet} = require(`../column-set`);
|
||||
|
||||
const npm = {
|
||||
formatting: require(`../../formatting`),
|
||||
utils: require(`../../utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.insert
|
||||
* @description
|
||||
* Generates an `INSERT` query for either one object or an array of objects.
|
||||
*
|
||||
* @param {object|object[]} data
|
||||
* An insert object with properties for insert values, or an array of such objects.
|
||||
*
|
||||
* When `data` is not a non-null object and not an array, it will throw {@link external:TypeError TypeError} = `Invalid parameter 'data' specified.`
|
||||
*
|
||||
* When `data` is an empty array, it will throw {@link external:TypeError TypeError} = `Cannot generate an INSERT from an empty array.`
|
||||
*
|
||||
* When `data` is an array that contains a non-object value, the method will throw {@link external:Error Error} =
|
||||
* `Invalid insert object at index N.`
|
||||
*
|
||||
* @param {array|helpers.Column|helpers.ColumnSet} [columns]
|
||||
* Set of columns to be inserted.
|
||||
*
|
||||
* It is optional when `data` is a single object, and required when `data` is an array of objects. If not specified for an array
|
||||
* of objects, the method will throw {@link external:TypeError TypeError} = `Parameter 'columns' is required when inserting multiple records.`
|
||||
*
|
||||
* When `columns` is not a {@link helpers.ColumnSet ColumnSet} object, a temporary {@link helpers.ColumnSet ColumnSet}
|
||||
* is created - from the value of `columns` (if it was specified), or from the value of `data` (if it is not an array).
|
||||
*
|
||||
* When the final {@link helpers.ColumnSet ColumnSet} is empty (no columns in it), the method will throw
|
||||
* {@link external:Error Error} = `Cannot generate an INSERT without any columns.`
|
||||
*
|
||||
* @param {helpers.TableName|string|{table,schema}} [table]
|
||||
* Destination table.
|
||||
*
|
||||
* It is normally a required parameter. But when `columns` is passed in as a {@link helpers.ColumnSet ColumnSet} object
|
||||
* with `table` set in it, that will be used when this parameter isn't specified. When neither is available, the method
|
||||
* will throw {@link external:Error Error} = `Table name is unknown.`
|
||||
*
|
||||
* @returns {string}
|
||||
* An `INSERT` query string.
|
||||
*
|
||||
* @see
|
||||
* {@link helpers.Column Column},
|
||||
* {@link helpers.ColumnSet ColumnSet},
|
||||
* {@link helpers.TableName TableName}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const pgp = require('pg-promise')({
|
||||
* capSQL: true // if you want all generated SQL capitalized
|
||||
* });
|
||||
*
|
||||
* const dataSingle = {val: 123, msg: 'hello'};
|
||||
* const dataMulti = [{val: 123, msg: 'hello'}, {val: 456, msg: 'world!'}];
|
||||
*
|
||||
* // Column details can be taken from the data object:
|
||||
*
|
||||
* pgp.helpers.insert(dataSingle, null, 'my-table');
|
||||
* //=> INSERT INTO "my-table"("val","msg") VALUES(123,'hello')
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Column details are required for a multi-row `INSERT`:
|
||||
*
|
||||
* pgp.helpers.insert(dataMulti, ['val', 'msg'], 'my-table');
|
||||
* //=> INSERT INTO "my-table"("val","msg") VALUES(123,'hello'),(456,'world!')
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Column details from a reusable ColumnSet (recommended for performance):
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['val', 'msg'], {table: 'my-table'});
|
||||
*
|
||||
* pgp.helpers.insert(dataMulti, cs);
|
||||
* //=> INSERT INTO "my-table"("val","msg") VALUES(123,'hello'),(456,'world!')
|
||||
*
|
||||
*/
|
||||
function insert(data, columns, table, capSQL) {
|
||||
|
||||
if (!data || typeof data !== `object`) {
|
||||
throw new TypeError(`Invalid parameter 'data' specified.`);
|
||||
}
|
||||
|
||||
const isArray = Array.isArray(data);
|
||||
|
||||
if (isArray && !data.length) {
|
||||
throw new TypeError(`Cannot generate an INSERT from an empty array.`);
|
||||
}
|
||||
|
||||
if (columns instanceof ColumnSet) {
|
||||
if (npm.utils.isNull(table)) {
|
||||
table = columns.table;
|
||||
}
|
||||
} else {
|
||||
if (isArray && npm.utils.isNull(columns)) {
|
||||
throw new TypeError(`Parameter 'columns' is required when inserting multiple records.`);
|
||||
}
|
||||
columns = new ColumnSet(columns || data);
|
||||
}
|
||||
|
||||
if (!columns.columns.length) {
|
||||
throw new Error(`Cannot generate an INSERT without any columns.`);
|
||||
}
|
||||
|
||||
if (!table) {
|
||||
throw new Error(`Table name is unknown.`);
|
||||
}
|
||||
|
||||
if (!(table instanceof TableName)) {
|
||||
table = new TableName(table);
|
||||
}
|
||||
|
||||
let query = capSQL ? sql.capCase : sql.lowCase;
|
||||
const fmOptions = {capSQL};
|
||||
|
||||
const format = npm.formatting.as.format;
|
||||
query = format(query, [table.name, columns.names], fmOptions);
|
||||
|
||||
if (isArray) {
|
||||
return query + data.map((d, index) => {
|
||||
if (!d || typeof d !== `object`) {
|
||||
throw new Error(`Invalid insert object at index ${index}.`);
|
||||
}
|
||||
return `(` + format(columns.variables, columns.prepare(d), fmOptions) + `)`;
|
||||
}).join();
|
||||
}
|
||||
return query + `(` + format(columns.variables, columns.prepare(data), fmOptions) + `)`;
|
||||
}
|
||||
|
||||
const sql = {
|
||||
lowCase: `insert into $1^($2^) values`,
|
||||
capCase: `INSERT INTO $1^($2^) VALUES`
|
||||
};
|
||||
|
||||
module.exports = {insert};
|
||||
80
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/sets.js
generated
vendored
Normal file
80
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/sets.js
generated
vendored
Normal file
@@ -0,0 +1,80 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {ColumnSet} = require(`../column-set`);
|
||||
|
||||
const npm = {
|
||||
format: require(`../../formatting`).as.format,
|
||||
utils: require(`../../utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.sets
|
||||
* @description
|
||||
* Generates a string of comma-separated value-set statements from a single object: `col1=val1, col2=val2, ...`,
|
||||
* to be used as part of a query.
|
||||
*
|
||||
* Since it is to be used as part of `UPDATE` queries, {@link helpers.Column Column} properties `cnd` and `skip` apply.
|
||||
*
|
||||
* @param {object} data
|
||||
* A simple, non-null and non-array source object.
|
||||
*
|
||||
* If it is anything else, the method will throw {@link external:TypeError TypeError} = `Invalid parameter 'data' specified.`
|
||||
*
|
||||
* @param {array|helpers.Column|helpers.ColumnSet} [columns]
|
||||
* Columns for which to set values.
|
||||
*
|
||||
* When not specified, properties of the `data` object are used.
|
||||
*
|
||||
* When no effective columns are found, an empty string is returned.
|
||||
*
|
||||
* @returns {string}
|
||||
* - comma-separated value-set statements for the `data` object
|
||||
* - an empty string, if no effective columns found
|
||||
*
|
||||
* @see
|
||||
* {@link helpers.Column Column},
|
||||
* {@link helpers.ColumnSet ColumnSet}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const pgp = require('pg-promise')();
|
||||
*
|
||||
* const data = {id: 1, val: 123, msg: 'hello'};
|
||||
*
|
||||
* // Properties can be pulled automatically from the object:
|
||||
*
|
||||
* pgp.helpers.sets(data);
|
||||
* //=> "id"=1,"val"=123,"msg"='hello'
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Column details from a reusable ColumnSet (recommended for performance);
|
||||
* // NOTE: Conditional columns (start with '?') are skipped:
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['?id','val', 'msg']);
|
||||
*
|
||||
* pgp.helpers.sets(data, cs);
|
||||
* //=> "val"=123,"msg"='hello'
|
||||
*
|
||||
*/
|
||||
function sets(data, columns, capSQL) {
|
||||
|
||||
if (!data || typeof data !== `object` || Array.isArray(data)) {
|
||||
throw new TypeError(`Invalid parameter 'data' specified.`);
|
||||
}
|
||||
|
||||
if (!(columns instanceof ColumnSet)) {
|
||||
columns = new ColumnSet(columns || data);
|
||||
}
|
||||
|
||||
return npm.format(columns.assign({source: data}), columns.prepare(data), {capSQL});
|
||||
}
|
||||
|
||||
module.exports = {sets};
|
||||
245
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/update.js
generated
vendored
Normal file
245
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/update.js
generated
vendored
Normal file
@@ -0,0 +1,245 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {assert} = require(`../../assert`);
|
||||
const {TableName} = require(`../table-name`);
|
||||
const {ColumnSet} = require(`../column-set`);
|
||||
|
||||
const npm = {
|
||||
formatting: require(`../../formatting`),
|
||||
utils: require(`../../utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.update
|
||||
* @description
|
||||
* Generates a simplified `UPDATE` query for either one object or an array of objects.
|
||||
*
|
||||
* The resulting query needs a `WHERE` clause to be appended to it, to specify the update logic.
|
||||
* This is to allow for update conditions of any complexity that are easy to add.
|
||||
*
|
||||
* @param {object|object[]} data
|
||||
* An update object with properties for update values, or an array of such objects.
|
||||
*
|
||||
* When `data` is not a non-null object and not an array, it will throw {@link external:TypeError TypeError} = `Invalid parameter 'data' specified.`
|
||||
*
|
||||
* When `data` is an empty array, it will throw {@link external:TypeError TypeError} = `Cannot generate an UPDATE from an empty array.`
|
||||
*
|
||||
* When `data` is an array that contains a non-object value, the method will throw {@link external:Error Error} =
|
||||
* `Invalid update object at index N.`
|
||||
*
|
||||
* @param {array|helpers.Column|helpers.ColumnSet} [columns]
|
||||
* Set of columns to be updated.
|
||||
*
|
||||
* It is optional when `data` is a single object, and required when `data` is an array of objects. If not specified for an array
|
||||
* of objects, the method will throw {@link external:TypeError TypeError} = `Parameter 'columns' is required when updating multiple records.`
|
||||
*
|
||||
* When `columns` is not a {@link helpers.ColumnSet ColumnSet} object, a temporary {@link helpers.ColumnSet ColumnSet}
|
||||
* is created - from the value of `columns` (if it was specified), or from the value of `data` (if it is not an array).
|
||||
*
|
||||
* When the final {@link helpers.ColumnSet ColumnSet} is empty (no columns in it), the method will throw
|
||||
* {@link external:Error Error} = `Cannot generate an UPDATE without any columns.`, unless option `emptyUpdate` was specified.
|
||||
*
|
||||
* @param {helpers.TableName|string|{table,schema}} [table]
|
||||
* Table to be updated.
|
||||
*
|
||||
* It is normally a required parameter. But when `columns` is passed in as a {@link helpers.ColumnSet ColumnSet} object
|
||||
* with `table` set in it, that will be used when this parameter isn't specified. When neither is available, the method
|
||||
* will throw {@link external:Error Error} = `Table name is unknown.`
|
||||
*
|
||||
* @param {{}} [options]
|
||||
* An object with formatting options for multi-row `UPDATE` queries.
|
||||
*
|
||||
* @param {string} [options.tableAlias=t]
|
||||
* Name of the SQL variable that represents the destination table.
|
||||
*
|
||||
* @param {string} [options.valueAlias=v]
|
||||
* Name of the SQL variable that represents the values.
|
||||
*
|
||||
* @param {*} [options.emptyUpdate]
|
||||
* This is a convenience option, to avoid throwing an error when generating a conditional update results in no columns.
|
||||
*
|
||||
* When present, regardless of the value, this option overrides the method's behavior when applying `skip` logic results in no columns,
|
||||
* i.e. when every column is being skipped.
|
||||
*
|
||||
* By default, in that situation the method throws {@link external:Error Error} = `Cannot generate an UPDATE without any columns.`
|
||||
* But when this option is present, the method will instead return whatever value the option was passed.
|
||||
*
|
||||
* @returns {*}
|
||||
* An `UPDATE` query string that needs a `WHERE` condition appended.
|
||||
*
|
||||
* If it results in an empty update, and option `emptyUpdate` was passed in, then the method returns the value
|
||||
* to which the option was set.
|
||||
*
|
||||
* @see
|
||||
* {@link helpers.Column Column},
|
||||
* {@link helpers.ColumnSet ColumnSet},
|
||||
* {@link helpers.TableName TableName}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const pgp = require('pg-promise')({
|
||||
* capSQL: true // if you want all generated SQL capitalized
|
||||
* });
|
||||
*
|
||||
* const dataSingle = {id: 1, val: 123, msg: 'hello'};
|
||||
* const dataMulti = [{id: 1, val: 123, msg: 'hello'}, {id: 2, val: 456, msg: 'world!'}];
|
||||
*
|
||||
* // Although column details can be taken from the data object, it is not
|
||||
* // a likely scenario for an update, unless updating the whole table:
|
||||
*
|
||||
* pgp.helpers.update(dataSingle, null, 'my-table');
|
||||
* //=> UPDATE "my-table" SET "id"=1,"val"=123,"msg"='hello'
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // A typical single-object update:
|
||||
*
|
||||
* // Dynamic conditions must be escaped/formatted properly:
|
||||
* const condition = pgp.as.format(' WHERE id = ${id}', dataSingle);
|
||||
*
|
||||
* pgp.helpers.update(dataSingle, ['val', 'msg'], 'my-table') + condition;
|
||||
* //=> UPDATE "my-table" SET "val"=123,"msg"='hello' WHERE id = 1
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Column details are required for a multi-row `UPDATE`;
|
||||
* // Adding '?' in front of a column name means it is only for a WHERE condition:
|
||||
*
|
||||
* pgp.helpers.update(dataMulti, ['?id', 'val', 'msg'], 'my-table') + ' WHERE v.id = t.id';
|
||||
* //=> UPDATE "my-table" AS t SET "val"=v."val","msg"=v."msg" FROM (VALUES(1,123,'hello'),(2,456,'world!'))
|
||||
* // AS v("id","val","msg") WHERE v.id = t.id
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Column details from a reusable ColumnSet (recommended for performance):
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['?id', 'val', 'msg'], {table: 'my-table'});
|
||||
*
|
||||
* pgp.helpers.update(dataMulti, cs) + ' WHERE v.id = t.id';
|
||||
* //=> UPDATE "my-table" AS t SET "val"=v."val","msg"=v."msg" FROM (VALUES(1,123,'hello'),(2,456,'world!'))
|
||||
* // AS v("id","val","msg") WHERE v.id = t.id
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Using parameter `options` to change the default alias names:
|
||||
*
|
||||
* pgp.helpers.update(dataMulti, cs, null, {tableAlias: 'X', valueAlias: 'Y'}) + ' WHERE Y.id = X.id';
|
||||
* //=> UPDATE "my-table" AS X SET "val"=Y."val","msg"=Y."msg" FROM (VALUES(1,123,'hello'),(2,456,'world!'))
|
||||
* // AS Y("id","val","msg") WHERE Y.id = X.id
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Handling an empty update
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['?id', '?name'], {table: 'tt'}); // no actual update-able columns
|
||||
* const result = pgp.helpers.update(dataMulti, cs, null, {emptyUpdate: 123});
|
||||
* if(result === 123) {
|
||||
* // We know the update is empty, i.e. no columns that can be updated;
|
||||
* // And it didn't throw because we specified `emptyUpdate` option.
|
||||
* }
|
||||
*/
|
||||
function update(data, columns, table, options, capSQL) {
|
||||
|
||||
if (!data || typeof data !== `object`) {
|
||||
throw new TypeError(`Invalid parameter 'data' specified.`);
|
||||
}
|
||||
|
||||
const isArray = Array.isArray(data);
|
||||
|
||||
if (isArray && !data.length) {
|
||||
throw new TypeError(`Cannot generate an UPDATE from an empty array.`);
|
||||
}
|
||||
|
||||
if (columns instanceof ColumnSet) {
|
||||
if (npm.utils.isNull(table)) {
|
||||
table = columns.table;
|
||||
}
|
||||
} else {
|
||||
if (isArray && npm.utils.isNull(columns)) {
|
||||
throw new TypeError(`Parameter 'columns' is required when updating multiple records.`);
|
||||
}
|
||||
columns = new ColumnSet(columns || data);
|
||||
}
|
||||
|
||||
options = assert(options, [`tableAlias`, `valueAlias`, `emptyUpdate`]);
|
||||
|
||||
const format = npm.formatting.as.format,
|
||||
useEmptyUpdate = `emptyUpdate` in options,
|
||||
fmOptions = {capSQL};
|
||||
|
||||
if (isArray) {
|
||||
const tableAlias = npm.formatting.as.alias(npm.utils.isNull(options.tableAlias) ? `t` : options.tableAlias);
|
||||
const valueAlias = npm.formatting.as.alias(npm.utils.isNull(options.valueAlias) ? `v` : options.valueAlias);
|
||||
|
||||
const q = capSQL ? sql.multi.capCase : sql.multi.lowCase;
|
||||
|
||||
const actualColumns = columns.columns.filter(c => !c.cnd);
|
||||
|
||||
if (checkColumns(actualColumns)) {
|
||||
return options.emptyUpdate;
|
||||
}
|
||||
|
||||
checkTable();
|
||||
|
||||
const targetCols = actualColumns.map(c => c.escapedName + `=` + valueAlias + `.` + c.escapedName).join();
|
||||
|
||||
const values = data.map((d, index) => {
|
||||
if (!d || typeof d !== `object`) {
|
||||
throw new Error(`Invalid update object at index ${index}.`);
|
||||
}
|
||||
return `(` + format(columns.variables, columns.prepare(d), fmOptions) + `)`;
|
||||
}).join();
|
||||
|
||||
return format(q, [table.name, tableAlias, targetCols, values, valueAlias, columns.names], fmOptions);
|
||||
}
|
||||
|
||||
const updates = columns.assign({source: data});
|
||||
|
||||
if (checkColumns(updates)) {
|
||||
return options.emptyUpdate;
|
||||
}
|
||||
|
||||
checkTable();
|
||||
|
||||
const query = capSQL ? sql.single.capCase : sql.single.lowCase;
|
||||
|
||||
return format(query, table.name) + format(updates, columns.prepare(data), fmOptions);
|
||||
|
||||
function checkTable() {
|
||||
if (table && !(table instanceof TableName)) {
|
||||
table = new TableName(table);
|
||||
}
|
||||
if (!table) {
|
||||
throw new Error(`Table name is unknown.`);
|
||||
}
|
||||
}
|
||||
|
||||
function checkColumns(cols) {
|
||||
if (!cols.length) {
|
||||
if (useEmptyUpdate) {
|
||||
return true;
|
||||
}
|
||||
throw new Error(`Cannot generate an UPDATE without any columns.`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const sql = {
|
||||
single: {
|
||||
lowCase: `update $1^ set `,
|
||||
capCase: `UPDATE $1^ SET `
|
||||
},
|
||||
multi: {
|
||||
lowCase: `update $1^ as $2^ set $3^ from (values$4^) as $5^($6^)`,
|
||||
capCase: `UPDATE $1^ AS $2^ SET $3^ FROM (VALUES$4^) AS $5^($6^)`
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = {update};
|
||||
115
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/values.js
generated
vendored
Normal file
115
ProjectSourceCode/node_modules/pg-promise/lib/helpers/methods/values.js
generated
vendored
Normal file
@@ -0,0 +1,115 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {ColumnSet} = require(`../column-set`);
|
||||
|
||||
const npm = {
|
||||
formatting: require(`../../formatting`),
|
||||
utils: require(`../../utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @method helpers.values
|
||||
* @description
|
||||
* Generates a string of comma-separated value groups from either one object or an array of objects,
|
||||
* to be used as part of a query:
|
||||
*
|
||||
* - from a single object: `(val_1, val_2, ...)`
|
||||
* - from an array of objects: `(val_11, val_12, ...), (val_21, val_22, ...)`
|
||||
*
|
||||
* @param {object|object[]} data
|
||||
* A source object with properties as values, or an array of such objects.
|
||||
*
|
||||
* If it is anything else, the method will throw {@link external:TypeError TypeError} = `Invalid parameter 'data' specified.`
|
||||
*
|
||||
* When `data` is an array that contains a non-object value, the method will throw {@link external:Error Error} =
|
||||
* `Invalid object at index N.`
|
||||
*
|
||||
* When `data` is an empty array, an empty string is returned.
|
||||
*
|
||||
* @param {array|helpers.Column|helpers.ColumnSet} [columns]
|
||||
* Columns for which to return values.
|
||||
*
|
||||
* It is optional when `data` is a single object, and required when `data` is an array of objects. If not specified for an array
|
||||
* of objects, the method will throw {@link external:TypeError TypeError} = `Parameter 'columns' is required when generating multi-row values.`
|
||||
*
|
||||
* When the final {@link helpers.ColumnSet ColumnSet} is empty (no columns in it), the method will throw
|
||||
* {@link external:Error Error} = `Cannot generate values without any columns.`
|
||||
*
|
||||
* @returns {string}
|
||||
* - comma-separated value groups, according to `data`
|
||||
* - an empty string, if `data` is an empty array
|
||||
*
|
||||
* @see
|
||||
* {@link helpers.Column Column},
|
||||
* {@link helpers.ColumnSet ColumnSet}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const pgp = require('pg-promise')();
|
||||
*
|
||||
* const dataSingle = {val: 123, msg: 'hello'};
|
||||
* const dataMulti = [{val: 123, msg: 'hello'}, {val: 456, msg: 'world!'}];
|
||||
*
|
||||
* // Properties can be pulled automatically from a single object:
|
||||
*
|
||||
* pgp.helpers.values(dataSingle);
|
||||
* //=> (123,'hello')
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Column details are required when using an array of objects:
|
||||
*
|
||||
* pgp.helpers.values(dataMulti, ['val', 'msg']);
|
||||
* //=> (123,'hello'),(456,'world!')
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Column details from a reusable ColumnSet (recommended for performance):
|
||||
*
|
||||
* const cs = new pgp.helpers.ColumnSet(['val', 'msg']);
|
||||
*
|
||||
* pgp.helpers.values(dataMulti, cs);
|
||||
* //=> (123,'hello'),(456,'world!')
|
||||
*
|
||||
*/
|
||||
function values(data, columns, capSQL) {
|
||||
|
||||
if (!data || typeof data !== `object`) {
|
||||
throw new TypeError(`Invalid parameter 'data' specified.`);
|
||||
}
|
||||
|
||||
const isArray = Array.isArray(data);
|
||||
|
||||
if (!(columns instanceof ColumnSet)) {
|
||||
if (isArray && npm.utils.isNull(columns)) {
|
||||
throw new TypeError(`Parameter 'columns' is required when generating multi-row values.`);
|
||||
}
|
||||
columns = new ColumnSet(columns || data);
|
||||
}
|
||||
|
||||
if (!columns.columns.length) {
|
||||
throw new Error(`Cannot generate values without any columns.`);
|
||||
}
|
||||
|
||||
const format = npm.formatting.as.format,
|
||||
fmOptions = {capSQL};
|
||||
|
||||
if (isArray) {
|
||||
return data.map((d, index) => {
|
||||
if (!d || typeof d !== `object`) {
|
||||
throw new Error(`Invalid object at index ${index}.`);
|
||||
}
|
||||
return `(` + format(columns.variables, columns.prepare(d), fmOptions) + `)`;
|
||||
}).join();
|
||||
}
|
||||
return `(` + format(columns.variables, columns.prepare(data), fmOptions) + `)`;
|
||||
}
|
||||
|
||||
module.exports = {values};
|
||||
128
ProjectSourceCode/node_modules/pg-promise/lib/helpers/table-name.js
generated
vendored
Normal file
128
ProjectSourceCode/node_modules/pg-promise/lib/helpers/table-name.js
generated
vendored
Normal file
@@ -0,0 +1,128 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {assert} = require(`../assert`);
|
||||
|
||||
const npm = {
|
||||
utils: require(`../utils`),
|
||||
format: require(`../formatting`).as // formatting namespace
|
||||
};
|
||||
|
||||
/**
|
||||
* @class helpers.TableName
|
||||
* @description
|
||||
* Represents a full table name that can be injected into queries directly.
|
||||
*
|
||||
* This is a read-only type that can be used wherever parameter `table` is supported.
|
||||
*
|
||||
* It supports $[Custom Type Formatting], which means you can use the type directly as a formatting
|
||||
* parameter, without specifying any escaping.
|
||||
*
|
||||
* Filter `:alias` is an alternative approach to splitting an SQL name into multiple ones.
|
||||
*
|
||||
* @param {string|object} table
|
||||
* Table name details, depending on the type:
|
||||
*
|
||||
* - table name, if `table` is a string
|
||||
* - object `{table, [schema]}`
|
||||
*
|
||||
* @property {string} name
|
||||
* Formatted/escaped full table name, combining `schema` + `table`.
|
||||
*
|
||||
* @property {string} table
|
||||
* Table name.
|
||||
*
|
||||
* @property {string} schema
|
||||
* Database schema name.
|
||||
*
|
||||
* It is `undefined` when no valid schema was specified.
|
||||
*
|
||||
* @returns {helpers.TableName}
|
||||
*
|
||||
* @see
|
||||
* {@link helpers.TableName#toPostgres toPostgres}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const table = new pgp.helpers.TableName({table: 'my-table', schema: 'my-schema'});
|
||||
* console.log(table);
|
||||
* //=> "my-schema"."my-table"
|
||||
*
|
||||
* // Formatting the type directly:
|
||||
* pgp.as.format('SELECT * FROM $1', table);
|
||||
* //=> SELECT * FROM "my-schema"."my-table"
|
||||
*
|
||||
*/
|
||||
class TableName {
|
||||
|
||||
constructor(table) {
|
||||
if (typeof table === `string`) {
|
||||
this.table = table;
|
||||
} else {
|
||||
const config = assert(table, [`table`, `schema`]);
|
||||
this.table = config.table;
|
||||
if (npm.utils.isText(config.schema)) {
|
||||
this.schema = config.schema;
|
||||
}
|
||||
}
|
||||
if (!npm.utils.isText(this.table)) {
|
||||
throw new TypeError(`Table name must be a non-empty text string.`);
|
||||
}
|
||||
this.name = npm.format.name(this.table);
|
||||
if (this.schema) {
|
||||
this.name = npm.format.name(this.schema) + `.` + this.name;
|
||||
}
|
||||
Object.freeze(this);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @method helpers.TableName#toPostgres
|
||||
* @description
|
||||
* $[Custom Type Formatting], based on $[Symbolic CTF], i.e. the actual method is available only via {@link external:Symbol Symbol}:
|
||||
*
|
||||
* ```js
|
||||
* const ctf = pgp.as.ctf; // Custom Type Formatting symbols namespace
|
||||
* const fullName = tn[ctf.toPostgres]; // tn = an object of type TableName
|
||||
* ```
|
||||
*
|
||||
* This is a raw formatting type (`rawType = true`), i.e. when used as a query-formatting parameter, type `TableName`
|
||||
* injects full table name as raw text.
|
||||
*
|
||||
* @param {helpers.TableName} [self]
|
||||
* Optional self-reference, for ES6 arrow functions.
|
||||
*
|
||||
* @returns {string}
|
||||
* Escaped full table name that includes optional schema name, if specified.
|
||||
*/
|
||||
TableName.prototype[npm.format.ctf.toPostgres] = function (self) {
|
||||
self = this instanceof TableName && this || self;
|
||||
return self.name;
|
||||
};
|
||||
|
||||
TableName.prototype[npm.format.ctf.rawType] = true; // use as pre-formatted
|
||||
|
||||
/**
|
||||
* @method helpers.TableName#toString
|
||||
* @description
|
||||
* Creates a well-formatted string that represents the object.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
TableName.prototype.toString = function () {
|
||||
return this.name;
|
||||
};
|
||||
|
||||
npm.utils.addInspection(TableName, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
module.exports = {TableName};
|
||||
27
ProjectSourceCode/node_modules/pg-promise/lib/index.js
generated
vendored
Normal file
27
ProjectSourceCode/node_modules/pg-promise/lib/index.js
generated
vendored
Normal file
@@ -0,0 +1,27 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
/* eslint no-var: off */
|
||||
var v = process.versions.node.split(`.`),
|
||||
highVer = +v[0];
|
||||
|
||||
// istanbul ignore next
|
||||
if (highVer < 12) {
|
||||
|
||||
// From pg-promise v10.15.0, the oldest supported Node.js is v12.0.0
|
||||
|
||||
// Node.js v8.0.0 was supported up to pg-promise v10.14.2
|
||||
// Node.js v7.6.0 was supported up to pg-promise v10.3.5
|
||||
// Node.js v4.5.0 was supported up to pg-promise v8.7.5
|
||||
// Node.js v0.10 was supported up to pg-promise v5.5.8
|
||||
|
||||
throw new Error(`Minimum Node.js version supported by pg-promise is 12.0.0`);
|
||||
}
|
||||
|
||||
module.exports = require(`./main`);
|
||||
39
ProjectSourceCode/node_modules/pg-promise/lib/inner-state.js
generated
vendored
Normal file
39
ProjectSourceCode/node_modules/pg-promise/lib/inner-state.js
generated
vendored
Normal file
@@ -0,0 +1,39 @@
|
||||
const {addReadProp} = require(`./utils`);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @class InnerState
|
||||
* @description
|
||||
* Implements support for private/inner state object inside the class,
|
||||
* which can be accessed by a derived class via hidden read-only property _inner.
|
||||
*/
|
||||
class InnerState {
|
||||
|
||||
constructor(initialState) {
|
||||
addReadProp(this, `_inner`, {}, true);
|
||||
if (initialState && typeof initialState === `object`) {
|
||||
this.extendState(initialState);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Extends or overrides inner state with the specified properties.
|
||||
*
|
||||
* Only own properties are used, i.e. inherited ones are skipped.
|
||||
*/
|
||||
extendState(state) {
|
||||
for (const a in state) {
|
||||
// istanbul ignore else
|
||||
if (Object.prototype.hasOwnProperty.call(state, a)) {
|
||||
this._inner[a] = state[a];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @member InnerState#_inner
|
||||
* Private/Inner object state.
|
||||
*/
|
||||
|
||||
module.exports = {InnerState};
|
||||
443
ProjectSourceCode/node_modules/pg-promise/lib/main.js
generated
vendored
Normal file
443
ProjectSourceCode/node_modules/pg-promise/lib/main.js
generated
vendored
Normal file
@@ -0,0 +1,443 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {PromiseAdapter} = require(`./promise-adapter`);
|
||||
const {DatabasePool} = require(`./database-pool`);
|
||||
const {PreparedStatement, ParameterizedQuery} = require(`./types`);
|
||||
const {QueryFile} = require(`./query-file`);
|
||||
const {queryResult} = require(`./query-result`);
|
||||
const {parsePromise} = require(`./promise-parser`);
|
||||
const {assert} = require(`./assert`);
|
||||
|
||||
const npm = {
|
||||
path: require(`path`),
|
||||
pg: require(`pg`),
|
||||
minify: require(`pg-minify`),
|
||||
formatting: require(`./formatting`),
|
||||
helpers: require(`./helpers`),
|
||||
errors: require(`./errors`),
|
||||
utils: require(`./utils`),
|
||||
pubUtils: require(`./utils/public`),
|
||||
mode: require(`./tx-mode`),
|
||||
package: require(`../package.json`),
|
||||
text: require(`./text`)
|
||||
};
|
||||
|
||||
let originalClientConnect;
|
||||
|
||||
/**
|
||||
* @author Vitaly Tomilov
|
||||
* @module pg-promise
|
||||
*
|
||||
* @description
|
||||
* ## pg-promise v10.15
|
||||
* All documentation here is for the latest official release only.
|
||||
*
|
||||
* ### Initialization Options
|
||||
*
|
||||
* Below is the complete list of _Initialization Options_ for the library that can be passed in during
|
||||
* the library's initialization:
|
||||
*
|
||||
* ```js
|
||||
* const initOptions = {/* options as documented below */};
|
||||
*
|
||||
* const pgp = require('pg-promise')(initOptions);
|
||||
* ```
|
||||
*
|
||||
* @param {{}} [options]
|
||||
* Library Initialization Options.
|
||||
*
|
||||
* @param {boolean} [options.pgFormatting=false]
|
||||
* Redirects all query formatting to the $[pg] driver.
|
||||
*
|
||||
* By default (`false`), the library uses its own advanced query-formatting engine.
|
||||
* If you set this option to a truthy value, query formatting will be done entirely by the
|
||||
* $[pg] driver, which means you won't be able to use any of the feature-rich query formatting
|
||||
* that this library implements, restricting yourself to the very basic `$1, $2,...` syntax.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {boolean} [options.pgNative=false]
|
||||
* Use $[Native Bindings]. Library $[pg-native] must be included and installed independently, or else there will
|
||||
* be an error thrown: {@link external:Error Error} = `Failed to initialize Native Bindings.`
|
||||
*
|
||||
* This is a static option (can only be set prior to initialization).
|
||||
*
|
||||
* @param {object|function} [options.promiseLib=Promise]
|
||||
* Overrides the default (ES6 Promise) promise library for its internal use.
|
||||
*
|
||||
* Example below sets to use $[Bluebird] - the best and recommended promise library. It is the fastest one,
|
||||
* and supports $[Long Stack Traces], essential for debugging promises.
|
||||
*
|
||||
* ```js
|
||||
* const Promise = require('bluebird');
|
||||
* const initOptions = {
|
||||
* promiseLib: Promise
|
||||
* };
|
||||
* const pgp = require('pg-promise')(initOptions);
|
||||
* ```
|
||||
*
|
||||
* All existing promise libraries are supported. The ones with recognizable signature are used automatically,
|
||||
* while the rest can be configured via the $[Promise Adapter].
|
||||
*
|
||||
* This is a static option (can only be set prior to initialization).
|
||||
*
|
||||
* @param {boolean} [options.noLocking=false]
|
||||
* Prevents protocol locking.
|
||||
*
|
||||
* By default, the library locks much of its protocol to read-only access, as a fool-proof mechanism.
|
||||
* Specifically for the {@link event:extend extend} event this serves as a protection against overriding existing
|
||||
* properties or trying to set them at the wrong time.
|
||||
*
|
||||
* If this provision gets in the way of using a mock-up framework for your tests, you can force
|
||||
* the library to deactivate most of the locks by setting `noLocking` = `true` within the options.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization). However, changing it after the library's
|
||||
* initialization will not affect {@link Database} objects that have already been created.
|
||||
*
|
||||
* @param {boolean} [options.capSQL=false]
|
||||
* Capitalizes any SQL generated by the library.
|
||||
*
|
||||
* By default, all internal SQL within the library is generated using the low case.
|
||||
* If, however, you want all SQL to be capitalized instead, set `capSQL` = `true`.
|
||||
*
|
||||
* It is purely a cosmetic feature.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {string|Array<string>|null|undefined|function} [options.schema]
|
||||
* Forces change of the default database schema(s) for every fresh connection, i.e.
|
||||
* the library will execute `SET search_path TO schema_1, schema_2, ...` in the background
|
||||
* whenever a fresh physical connection is allocated.
|
||||
*
|
||||
* Normally, one changes the default schema(s) by $[changing the database or the role], but sometimes you
|
||||
* may want to switch the default schema(s) without persisting the change, and then use this option.
|
||||
*
|
||||
* It can be a string, an array of strings, or a callback function that takes `dc` (database context)
|
||||
* as the only parameter (and as `this`), and returns schema(s) according to the database context. A callback function
|
||||
* can also return nothing (`undefined` or `null`), if no schema change needed for the specified database context.
|
||||
*
|
||||
* The order of schema names matters, so if a table name exists in more than one schema, its default access resolves
|
||||
* to the table from the first such schema on the list.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {boolean} [options.noWarnings=false]
|
||||
* Disables all diagnostic warnings in the library (it is ill-advised).
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {function} [options.connect]
|
||||
* Global event {@link event:connect connect} handler.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {function} [options.disconnect]
|
||||
* Global event {@link event:disconnect disconnect} handler.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {function} [options.query]
|
||||
* Global event {@link event:query query} handler.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {function} [options.receive]
|
||||
* Global event {@link event:receive receive} handler.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {function} [options.task]
|
||||
* Global event {@link event:task task} handler.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {function} [options.transact]
|
||||
* Global event {@link event:transact transact} handler.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {function} [options.error]
|
||||
* Global event {@link event:error error} handler.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @param {function} [options.extend]
|
||||
* Global event {@link event:extend extend} handler.
|
||||
*
|
||||
* This option is dynamic (can be set before or after initialization).
|
||||
*
|
||||
* @see
|
||||
* {@link module:pg-promise~end end},
|
||||
* {@link module:pg-promise~as as},
|
||||
* {@link module:pg-promise~errors errors},
|
||||
* {@link module:pg-promise~helpers helpers},
|
||||
* {@link module:pg-promise~minify minify},
|
||||
* {@link module:pg-promise~ParameterizedQuery ParameterizedQuery},
|
||||
* {@link module:pg-promise~PreparedStatement PreparedStatement},
|
||||
* {@link module:pg-promise~pg pg},
|
||||
* {@link module:pg-promise~QueryFile QueryFile},
|
||||
* {@link module:pg-promise~queryResult queryResult},
|
||||
* {@link module:pg-promise~spex spex},
|
||||
* {@link module:pg-promise~txMode txMode},
|
||||
* {@link module:pg-promise~utils utils}
|
||||
*
|
||||
*/
|
||||
function $main(options) {
|
||||
|
||||
options = assert(options, [`pgFormatting`, `pgNative`, `promiseLib`, `noLocking`, `capSQL`, `noWarnings`,
|
||||
`connect`, `disconnect`, `query`, `receive`, `task`, `transact`, `error`, `extend`, `schema`]);
|
||||
|
||||
let pg = npm.pg;
|
||||
const p = parsePromise(options.promiseLib);
|
||||
|
||||
const config = {
|
||||
version: npm.package.version,
|
||||
promiseLib: p.promiseLib,
|
||||
promise: p.promise
|
||||
};
|
||||
|
||||
npm.utils.addReadProp(config, `$npm`, {}, true);
|
||||
|
||||
// Locking properties that cannot be changed later:
|
||||
npm.utils.addReadProp(options, `promiseLib`, options.promiseLib);
|
||||
npm.utils.addReadProp(options, `pgNative`, !!options.pgNative);
|
||||
|
||||
config.options = options;
|
||||
|
||||
// istanbul ignore next:
|
||||
// we do not cover code specific to Native Bindings
|
||||
if (options.pgNative) {
|
||||
pg = npm.pg.native;
|
||||
if (npm.utils.isNull(pg)) {
|
||||
throw new Error(npm.text.nativeError);
|
||||
}
|
||||
} else {
|
||||
if (!originalClientConnect) {
|
||||
originalClientConnect = pg.Client.prototype.connect;
|
||||
pg.Client.prototype.connect = function () {
|
||||
const handler = msg => {
|
||||
if (msg.parameterName === `server_version`) {
|
||||
this.serverVersion = msg.parameterValue;
|
||||
this.connection.removeListener(`parameterStatus`, handler);
|
||||
}
|
||||
};
|
||||
this.connection.on(`parameterStatus`, handler);
|
||||
return originalClientConnect.call(this, ...arguments);
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
const Database = require(`./database`)(config);
|
||||
|
||||
const inst = (cn, dc) => {
|
||||
if (npm.utils.isText(cn) || (cn && typeof cn === `object`)) {
|
||||
return new Database(cn, dc, config);
|
||||
}
|
||||
throw new TypeError(`Invalid connection details: ` + npm.utils.toJson(cn));
|
||||
};
|
||||
|
||||
npm.utils.addReadProperties(inst, rootNameSpace);
|
||||
|
||||
/**
|
||||
* @member {external:PG} pg
|
||||
* @description
|
||||
* Instance of the $[pg] library that's being used, depending on initialization option `pgNative`:
|
||||
* - regular `pg` module instance, without option `pgNative`, or equal to `false` (default)
|
||||
* - `pg` module instance with $[Native Bindings], if option `pgNative` was set.
|
||||
*
|
||||
* Available as `pgp.pg`, after initializing the library.
|
||||
*/
|
||||
inst.pg = pg; // keep it modifiable, so the protocol can be mocked
|
||||
|
||||
/**
|
||||
* @member {function} end
|
||||
* @readonly
|
||||
* @description
|
||||
* Shuts down all connection pools created in the process, so it can terminate without delay.
|
||||
* It is available as `pgp.end`, after initializing the library.
|
||||
*
|
||||
* All {@link Database} objects created previously can no longer be used, and their query methods will be rejecting
|
||||
* with {@link external:Error Error} = `Connection pool of the database object has been destroyed.`
|
||||
*
|
||||
* And if you want to shut down only a specific connection pool, you do so via the {@link Database}
|
||||
* object that owns the pool: `db.$pool.end()` (see {@link Database#$pool Database.$pool}).
|
||||
*
|
||||
* For more details see $[Library de-initialization].
|
||||
*/
|
||||
npm.utils.addReadProp(inst, `end`, () => {
|
||||
DatabasePool.shutDown();
|
||||
});
|
||||
|
||||
/**
|
||||
* @member {helpers} helpers
|
||||
* @readonly
|
||||
* @description
|
||||
* Namespace for {@link helpers all query-formatting helper functions}.
|
||||
*
|
||||
* Available as `pgp.helpers`, after initializing the library.
|
||||
*
|
||||
* @see {@link helpers}.
|
||||
*/
|
||||
npm.utils.addReadProp(inst, `helpers`, npm.helpers(config));
|
||||
|
||||
/**
|
||||
* @member {external:spex} spex
|
||||
* @readonly
|
||||
* @description
|
||||
* Initialized instance of the $[spex] module, used by the library within tasks and transactions.
|
||||
*
|
||||
* Available as `pgp.spex`, after initializing the library.
|
||||
*
|
||||
* @see
|
||||
* {@link Task#batch},
|
||||
* {@link Task#page},
|
||||
* {@link Task#sequence}
|
||||
*/
|
||||
npm.utils.addReadProp(inst, `spex`, config.$npm.spex);
|
||||
|
||||
config.pgp = inst;
|
||||
npm.utils.lock(config, true, options);
|
||||
|
||||
return inst;
|
||||
}
|
||||
|
||||
const rootNameSpace = {
|
||||
|
||||
/**
|
||||
* @member {formatting} as
|
||||
* @readonly
|
||||
* @description
|
||||
* Namespace for {@link formatting all query-formatting functions}.
|
||||
*
|
||||
* Available as `pgp.as`, before and after initializing the library.
|
||||
*
|
||||
* @see {@link formatting}.
|
||||
*/
|
||||
as: npm.formatting.as,
|
||||
|
||||
/**
|
||||
* @member {external:pg-minify} minify
|
||||
* @readonly
|
||||
* @description
|
||||
* Instance of the $[pg-minify] library used internally to minify SQL scripts.
|
||||
*
|
||||
* Available as `pgp.minify`, before and after initializing the library.
|
||||
*/
|
||||
minify: npm.minify,
|
||||
|
||||
/**
|
||||
* @member {queryResult} queryResult
|
||||
* @readonly
|
||||
* @description
|
||||
* Query Result Mask enumerator.
|
||||
*
|
||||
* Available as `pgp.queryResult`, before and after initializing the library.
|
||||
*/
|
||||
queryResult,
|
||||
|
||||
/**
|
||||
* @member {PromiseAdapter} PromiseAdapter
|
||||
* @readonly
|
||||
* @description
|
||||
* {@link PromiseAdapter} class.
|
||||
*
|
||||
* Available as `pgp.PromiseAdapter`, before and after initializing the library.
|
||||
*/
|
||||
PromiseAdapter,
|
||||
|
||||
/**
|
||||
* @member {ParameterizedQuery} ParameterizedQuery
|
||||
* @readonly
|
||||
* @description
|
||||
* {@link ParameterizedQuery} class.
|
||||
*
|
||||
* Available as `pgp.ParameterizedQuery`, before and after initializing the library.
|
||||
*/
|
||||
ParameterizedQuery,
|
||||
|
||||
/**
|
||||
* @member {PreparedStatement} PreparedStatement
|
||||
* @readonly
|
||||
* @description
|
||||
* {@link PreparedStatement} class.
|
||||
*
|
||||
* Available as `pgp.PreparedStatement`, before and after initializing the library.
|
||||
*/
|
||||
PreparedStatement,
|
||||
|
||||
/**
|
||||
* @member {QueryFile} QueryFile
|
||||
* @readonly
|
||||
* @description
|
||||
* {@link QueryFile} class.
|
||||
*
|
||||
* Available as `pgp.QueryFile`, before and after initializing the library.
|
||||
*/
|
||||
QueryFile,
|
||||
|
||||
/**
|
||||
* @member {errors} errors
|
||||
* @readonly
|
||||
* @description
|
||||
* {@link errors} - namespace for all error types.
|
||||
*
|
||||
* Available as `pgp.errors`, before and after initializing the library.
|
||||
*/
|
||||
errors: npm.errors,
|
||||
|
||||
/**
|
||||
* @member {utils} utils
|
||||
* @readonly
|
||||
* @description
|
||||
* {@link utils} - namespace for utility functions.
|
||||
*
|
||||
* Available as `pgp.utils`, before and after initializing the library.
|
||||
*/
|
||||
utils: npm.pubUtils,
|
||||
|
||||
/**
|
||||
* @member {txMode} txMode
|
||||
* @readonly
|
||||
* @description
|
||||
* {@link txMode Transaction Mode} namespace.
|
||||
*
|
||||
* Available as `pgp.txMode`, before and after initializing the library.
|
||||
*/
|
||||
txMode: npm.mode
|
||||
};
|
||||
|
||||
npm.utils.addReadProperties($main, rootNameSpace);
|
||||
|
||||
module.exports = $main;
|
||||
|
||||
/**
|
||||
* @external Promise
|
||||
* @see https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/Promise
|
||||
*/
|
||||
|
||||
/**
|
||||
* @external PG
|
||||
* @see https://node-postgres.com
|
||||
*/
|
||||
|
||||
/**
|
||||
* @external Client
|
||||
* @see https://node-postgres.com/api/client
|
||||
*/
|
||||
|
||||
/**
|
||||
* @external pg-minify
|
||||
* @see https://github.com/vitaly-t/pg-minify
|
||||
*/
|
||||
|
||||
/**
|
||||
* @external spex
|
||||
* @see https://github.com/vitaly-t/spex
|
||||
*/
|
||||
43
ProjectSourceCode/node_modules/pg-promise/lib/patterns.js
generated
vendored
Normal file
43
ProjectSourceCode/node_modules/pg-promise/lib/patterns.js
generated
vendored
Normal file
@@ -0,0 +1,43 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
/*
|
||||
The most important regular expressions and data as used by the library,
|
||||
isolated here to help with possible edge cases during integration.
|
||||
*/
|
||||
|
||||
module.exports = {
|
||||
// Searches for all Named Parameters, supporting any of the following syntax:
|
||||
// ${propName}, $(propName), $[propName], $/propName/, $<propName>
|
||||
// Nested property names are also supported: ${propName.abc}
|
||||
namedParameters: /\$(?:({)|(\()|(<)|(\[)|(\/))\s*[a-zA-Z0-9$_.]+(\^|~|#|:raw|:alias|:name|:json|:csv|:list|:value)?\s*(?:(?=\2)(?=\3)(?=\4)(?=\5)}|(?=\1)(?=\3)(?=\4)(?=\5)\)|(?=\1)(?=\2)(?=\4)(?=\5)>|(?=\1)(?=\2)(?=\3)(?=\5)]|(?=\1)(?=\2)(?=\3)(?=\4)\/)/g,
|
||||
|
||||
// Searches for all variables $1, $2, ...$100000, and while it will find greater than $100000
|
||||
// variables, the formatting engine is expected to throw an error for those.
|
||||
multipleValues: /\$([1-9][0-9]{0,16}(?![0-9])(\^|~|#|:raw|:alias|:name|:json|:csv|:list|:value)?)/g,
|
||||
|
||||
// Searches for all occurrences of variable $1
|
||||
singleValue: /\$1(?![0-9])(\^|~|#|:raw|:alias|:name|:json|:csv|:list|:value)?/g,
|
||||
|
||||
// Matches a valid column name for the Column type parser, according to the following rules:
|
||||
// - can contain: any combination of a-z, A-Z, 0-9, $ or _
|
||||
// - can contain ? at the start
|
||||
// - can contain one of the supported filters/modifiers
|
||||
validColumn: /\??[a-zA-Z0-9$_]+(\^|~|#|:raw|:alias|:name|:json|:csv|:list|:value)?/,
|
||||
|
||||
// Matches a valid open-name JavaScript variable, according to the following rules:
|
||||
// - can contain: any combination of a-z, A-Z, 0-9, $ or _
|
||||
validVariable: /[a-zA-Z0-9$_]+/,
|
||||
|
||||
// Matches a valid modifier in a column/property:
|
||||
hasValidModifier: /\^|~|#|:raw|:alias|:name|:json|:csv|:list|:value/,
|
||||
|
||||
// List of all supported formatting modifiers:
|
||||
validModifiers: [`^`, `~`, `#`, `:raw`, `:alias`, `:name`, `:json`, `:csv`, `:list`, `:value`]
|
||||
};
|
||||
86
ProjectSourceCode/node_modules/pg-promise/lib/promise-adapter.js
generated
vendored
Normal file
86
ProjectSourceCode/node_modules/pg-promise/lib/promise-adapter.js
generated
vendored
Normal file
@@ -0,0 +1,86 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {assert} = require(`./assert`);
|
||||
|
||||
/**
|
||||
* @class PromiseAdapter
|
||||
* @summary Adapter for the primary promise operations.
|
||||
* @description
|
||||
* Provides compatibility with promise libraries that cannot be recognized automatically,
|
||||
* via functions that implement the primary operations with promises:
|
||||
*
|
||||
* - construct a new promise with a callback function
|
||||
* - resolve a promise with some result data
|
||||
* - reject a promise with a reason
|
||||
* - resolve an array of promises
|
||||
*
|
||||
* The type is available from the library's root: `pgp.PromiseAdapter`.
|
||||
*
|
||||
* @param {object} api
|
||||
* Promise API configuration object.
|
||||
*
|
||||
* Passing in anything other than an object will throw {@link external:TypeError TypeError} = `Adapter requires an api configuration object.`
|
||||
*
|
||||
* @param {function} api.create
|
||||
* A function that takes a callback parameter and returns a new promise object.
|
||||
* The callback parameter is expected to be `function(resolve, reject)`.
|
||||
*
|
||||
* Passing in anything other than a function will throw {@link external:TypeError TypeError} = `Function 'create' must be specified.`
|
||||
*
|
||||
* @param {function} api.resolve
|
||||
* A function that takes an optional data parameter and resolves a promise with it.
|
||||
*
|
||||
* Passing in anything other than a function will throw {@link external:TypeError TypeError} = `Function 'resolve' must be specified.`
|
||||
*
|
||||
* @param {function} api.reject
|
||||
* A function that takes an optional error parameter and rejects a promise with it.
|
||||
*
|
||||
* Passing in anything other than a function will throw {@link external:TypeError TypeError} = `Function 'reject' must be specified.`
|
||||
*
|
||||
* @param {function} api.all
|
||||
* A function that resolves an array of promises.
|
||||
*
|
||||
* Passing in anything other than a function will throw {@link external:TypeError TypeError} = `Function 'all' must be specified.`
|
||||
*
|
||||
* @returns {PromiseAdapter}
|
||||
*/
|
||||
class PromiseAdapter {
|
||||
constructor(api) {
|
||||
|
||||
if (!api || typeof api !== `object`) {
|
||||
throw new TypeError(`Adapter requires an api configuration object.`);
|
||||
}
|
||||
|
||||
api = assert(api, [`create`, `resolve`, `reject`, `all`]);
|
||||
|
||||
this.create = api.create;
|
||||
this.resolve = api.resolve;
|
||||
this.reject = api.reject;
|
||||
this.all = api.all;
|
||||
|
||||
if (typeof this.create !== `function`) {
|
||||
throw new TypeError(`Function 'create' must be specified.`);
|
||||
}
|
||||
|
||||
if (typeof this.resolve !== `function`) {
|
||||
throw new TypeError(`Function 'resolve' must be specified.`);
|
||||
}
|
||||
|
||||
if (typeof this.reject !== `function`) {
|
||||
throw new TypeError(`Function 'reject' must be specified.`);
|
||||
}
|
||||
|
||||
if (typeof this.all !== `function`) {
|
||||
throw new TypeError(`Function 'all' must be specified.`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {PromiseAdapter};
|
||||
56
ProjectSourceCode/node_modules/pg-promise/lib/promise-parser.js
generated
vendored
Normal file
56
ProjectSourceCode/node_modules/pg-promise/lib/promise-parser.js
generated
vendored
Normal file
@@ -0,0 +1,56 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {PromiseAdapter} = require(`./promise-adapter`);
|
||||
|
||||
//////////////////////////////////////////
|
||||
// Parses and validates a promise library;
|
||||
function parse(pl) {
|
||||
|
||||
let promise;
|
||||
if (pl instanceof PromiseAdapter) {
|
||||
promise = function (func) {
|
||||
return pl.create(func);
|
||||
};
|
||||
promise.resolve = pl.resolve;
|
||||
promise.reject = pl.reject;
|
||||
promise.all = pl.all;
|
||||
return promise;
|
||||
}
|
||||
const t = typeof pl;
|
||||
if (t === `function` || t === `object`) {
|
||||
const Root = typeof pl.Promise === `function` ? pl.Promise : pl;
|
||||
promise = function (func) {
|
||||
return new Root(func);
|
||||
};
|
||||
promise.resolve = Root.resolve;
|
||||
promise.reject = Root.reject;
|
||||
promise.all = Root.all;
|
||||
if (typeof promise.resolve === `function` &&
|
||||
typeof promise.reject === `function` &&
|
||||
typeof promise.all === `function`) {
|
||||
return promise;
|
||||
}
|
||||
}
|
||||
|
||||
throw new TypeError(`Invalid promise library specified.`);
|
||||
}
|
||||
|
||||
function parsePromise(promiseLib) {
|
||||
const result = {promiseLib};
|
||||
if (promiseLib) {
|
||||
result.promise = parse(promiseLib);
|
||||
} else {
|
||||
result.promise = parse(Promise);
|
||||
result.promiseLib = Promise;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
module.exports = {parsePromise};
|
||||
398
ProjectSourceCode/node_modules/pg-promise/lib/query-file.js
generated
vendored
Normal file
398
ProjectSourceCode/node_modules/pg-promise/lib/query-file.js
generated
vendored
Normal file
@@ -0,0 +1,398 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {InnerState} = require(`./inner-state`);
|
||||
const {QueryFileError} = require(`./errors`);
|
||||
const {assert} = require(`./assert`);
|
||||
const {ColorConsole} = require(`./utils/color`);
|
||||
|
||||
const npm = {
|
||||
fs: require(`fs`),
|
||||
os: require(`os`),
|
||||
path: require(`path`),
|
||||
minify: require(`pg-minify`),
|
||||
utils: require(`./utils`),
|
||||
formatting: require(`./formatting`)
|
||||
};
|
||||
|
||||
const file$query = Symbol(`QueryFile.query`);
|
||||
|
||||
/**
|
||||
* @class QueryFile
|
||||
* @description
|
||||
*
|
||||
* Represents an external SQL file. The type is available from the library's root: `pgp.QueryFile`.
|
||||
*
|
||||
* Reads a file with SQL and prepares it for execution, also parses and minifies it, if required.
|
||||
* The SQL can be of any complexity, with both single and multi-line comments.
|
||||
*
|
||||
* The type can be used in place of the `query` parameter, with any query method directly, plus as `text` in {@link PreparedStatement}
|
||||
* and {@link ParameterizedQuery}.
|
||||
*
|
||||
* It never throws any error, leaving it for query methods to reject with {@link errors.QueryFileError QueryFileError}.
|
||||
*
|
||||
* **IMPORTANT:** You should only create a single reusable object per file, in order to avoid repeated file reads,
|
||||
* as the IO is a very expensive resource. If you do not follow it, you will be seeing the following warning:
|
||||
* `Creating a duplicate QueryFile object for the same file`, which signals a bad-use pattern.
|
||||
*
|
||||
* @param {string} file
|
||||
* Path to the SQL file with the query, either absolute or relative to the application's entry point file.
|
||||
*
|
||||
* If there is any problem reading the file, it will be reported when executing the query.
|
||||
*
|
||||
* @param {QueryFile.Options} [options]
|
||||
* Set of configuration options, as documented by {@link QueryFile.Options}.
|
||||
*
|
||||
* @returns {QueryFile}
|
||||
*
|
||||
* @see
|
||||
* {@link errors.QueryFileError QueryFileError},
|
||||
* {@link QueryFile#toPostgres toPostgres}
|
||||
*
|
||||
* @example
|
||||
* // File sql.js
|
||||
*
|
||||
* // Proper way to organize an sql provider:
|
||||
* //
|
||||
* // - have all sql files for Users in ./sql/users
|
||||
* // - have all sql files for Products in ./sql/products
|
||||
* // - have your sql provider module as ./sql/index.js
|
||||
*
|
||||
* const {QueryFile} = require('pg-promise');
|
||||
* const {join: joinPath} = require('path');
|
||||
*
|
||||
* // Helper for linking to external query files:
|
||||
* function sql(file) {
|
||||
* const fullPath = joinPath(__dirname, file); // generating full path;
|
||||
* return new QueryFile(fullPath, {minify: true});
|
||||
* }
|
||||
*
|
||||
* module.exports = {
|
||||
* // external queries for Users:
|
||||
* users: {
|
||||
* add: sql('users/create.sql'),
|
||||
* search: sql('users/search.sql'),
|
||||
* report: sql('users/report.sql'),
|
||||
* },
|
||||
* // external queries for Products:
|
||||
* products: {
|
||||
* add: sql('products/add.sql'),
|
||||
* quote: sql('products/quote.sql'),
|
||||
* search: sql('products/search.sql'),
|
||||
* }
|
||||
* };
|
||||
*
|
||||
* @example
|
||||
* // Testing our SQL provider
|
||||
*
|
||||
* const db = require('./db'); // our database module;
|
||||
* const {users: sql} = require('./sql'); // sql for users;
|
||||
*
|
||||
* module.exports = {
|
||||
* addUser: (name, age) => db.none(sql.add, [name, age]),
|
||||
* findUser: name => db.any(sql.search, name)
|
||||
* };
|
||||
*
|
||||
*/
|
||||
class QueryFile extends InnerState {
|
||||
|
||||
constructor(file, options) {
|
||||
|
||||
let filePath = file;
|
||||
|
||||
options = assert(options, {
|
||||
debug: npm.utils.isDev(),
|
||||
minify: (options && options.compress && options.minify === undefined) ? true : undefined,
|
||||
compress: undefined,
|
||||
params: undefined,
|
||||
noWarnings: undefined
|
||||
});
|
||||
|
||||
if (npm.utils.isText(filePath) && !npm.path.isAbsolute(filePath)) {
|
||||
filePath = npm.path.join(npm.utils.startDir, filePath);
|
||||
}
|
||||
|
||||
const {usedPath} = QueryFile.instance;
|
||||
|
||||
// istanbul ignore next:
|
||||
if (!options.noWarnings) {
|
||||
if (filePath in usedPath) {
|
||||
usedPath[filePath]++;
|
||||
ColorConsole.warn(`WARNING: Creating a duplicate QueryFile object for the same file - \n ${filePath}\n${npm.utils.getLocalStack(2, 3)}\n`);
|
||||
} else {
|
||||
usedPath[filePath] = 0;
|
||||
}
|
||||
}
|
||||
|
||||
const _inner = {
|
||||
file,
|
||||
filePath,
|
||||
options,
|
||||
sql: undefined,
|
||||
error: undefined,
|
||||
ready: undefined,
|
||||
modTime: undefined
|
||||
};
|
||||
|
||||
super(_inner);
|
||||
|
||||
this.prepare();
|
||||
}
|
||||
|
||||
/**
|
||||
* Global instance of the file-path repository.
|
||||
*
|
||||
* @return {{usedPath: {}}}
|
||||
*/
|
||||
static get instance() {
|
||||
const s = Symbol.for(`pgPromiseQueryFile`);
|
||||
let scope = global[s];
|
||||
if (!scope) {
|
||||
scope = {
|
||||
usedPath: {} // used-path look-up dictionary
|
||||
};
|
||||
global[s] = scope;
|
||||
}
|
||||
return scope;
|
||||
}
|
||||
|
||||
/**
|
||||
* @name QueryFile#Symbol(QueryFile.$query)
|
||||
* @type {string}
|
||||
* @default undefined
|
||||
* @readonly
|
||||
* @private
|
||||
* @summary Prepared query string.
|
||||
* @description
|
||||
* When property {@link QueryFile#error error} is set, the query is `undefined`.
|
||||
*
|
||||
* **IMPORTANT:** This property is for internal use by the library only, never use this
|
||||
* property directly from your code.
|
||||
*/
|
||||
get [file$query]() {
|
||||
return this._inner.sql;
|
||||
}
|
||||
|
||||
/**
|
||||
* @name QueryFile#error
|
||||
* @type {errors.QueryFileError}
|
||||
* @default undefined
|
||||
* @readonly
|
||||
* @description
|
||||
* When in an error state, it is set to a {@link errors.QueryFileError QueryFileError} object. Otherwise, it is `undefined`.
|
||||
*/
|
||||
get error() {
|
||||
return this._inner.error;
|
||||
}
|
||||
|
||||
/**
|
||||
* @name QueryFile#file
|
||||
* @type {string}
|
||||
* @readonly
|
||||
* @description
|
||||
* File name that was passed into the constructor.
|
||||
*
|
||||
* This property is primarily for internal use by the library.
|
||||
*/
|
||||
get file() {
|
||||
return this._inner.file;
|
||||
}
|
||||
|
||||
/**
|
||||
* @name QueryFile#options
|
||||
* @type {QueryFile.Options}
|
||||
* @readonly
|
||||
* @description
|
||||
* Set of options, as configured during the object's construction.
|
||||
*
|
||||
* This property is primarily for internal use by the library.
|
||||
*/
|
||||
get options() {
|
||||
return this._inner.options;
|
||||
}
|
||||
|
||||
/**
|
||||
* @summary Prepares the query for execution.
|
||||
* @description
|
||||
* If the query hasn't been prepared yet, it will read the file and process the content according
|
||||
* to the parameters passed into the constructor.
|
||||
*
|
||||
* This method is primarily for internal use by the library.
|
||||
*
|
||||
* @param {boolean} [throwErrors=false]
|
||||
* Throw any error encountered.
|
||||
*/
|
||||
prepare(throwErrors) {
|
||||
const i = this._inner, options = i.options;
|
||||
let lastMod;
|
||||
if (options.debug && i.ready) {
|
||||
try {
|
||||
lastMod = npm.fs.statSync(i.filePath).mtime.getTime();
|
||||
// istanbul ignore if;
|
||||
if (lastMod === i.modTime) {
|
||||
return;
|
||||
}
|
||||
i.ready = false;
|
||||
} catch (e) {
|
||||
i.sql = undefined;
|
||||
i.ready = false;
|
||||
i.error = e;
|
||||
if (throwErrors) {
|
||||
throw i.error;
|
||||
}
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (i.ready) {
|
||||
return;
|
||||
}
|
||||
try {
|
||||
i.sql = npm.fs.readFileSync(i.filePath, `utf8`);
|
||||
i.modTime = lastMod || npm.fs.statSync(i.filePath).mtime.getTime();
|
||||
if (options.minify && options.minify !== `after`) {
|
||||
i.sql = npm.minify(i.sql, {compress: options.compress});
|
||||
}
|
||||
if (options.params !== undefined) {
|
||||
i.sql = npm.formatting.as.format(i.sql, options.params, {partial: true});
|
||||
}
|
||||
if (options.minify && options.minify === `after`) {
|
||||
i.sql = npm.minify(i.sql, {compress: options.compress});
|
||||
}
|
||||
i.ready = true;
|
||||
i.error = undefined;
|
||||
} catch (e) {
|
||||
i.sql = undefined;
|
||||
i.error = new QueryFileError(e, this);
|
||||
if (throwErrors) {
|
||||
throw i.error;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Hiding the query as a symbol within the type,
|
||||
// to make it even more difficult to misuse it:
|
||||
QueryFile.$query = file$query;
|
||||
|
||||
/**
|
||||
* @method QueryFile#toPostgres
|
||||
* @description
|
||||
* $[Custom Type Formatting], based on $[Symbolic CTF], i.e. the actual method is available only via {@link external:Symbol Symbol}:
|
||||
*
|
||||
* ```js
|
||||
* const ctf = pgp.as.ctf; // Custom Type Formatting symbols namespace
|
||||
* const query = qf[ctf.toPostgres](); // qf = an object of type QueryFile
|
||||
* ```
|
||||
*
|
||||
* This is a raw formatting type (`rawType = true`), i.e. when used as a query-formatting parameter, type `QueryFile` injects SQL as raw text.
|
||||
*
|
||||
* If you need to support type `QueryFile` outside of query methods, this is the only safe way to get the most current SQL.
|
||||
* And you would want to use this method dynamically, as it reloads the SQL automatically, if option `debug` is set.
|
||||
* See {@link QueryFile.Options Options}.
|
||||
*
|
||||
* @param {QueryFile} [self]
|
||||
* Optional self-reference, for ES6 arrow functions.
|
||||
*
|
||||
* @returns {string}
|
||||
* SQL string from the file, according to the {@link QueryFile.Options options} specified.
|
||||
*
|
||||
*/
|
||||
QueryFile.prototype[npm.formatting.as.ctf.toPostgres] = function (self) {
|
||||
self = this instanceof QueryFile && this || self;
|
||||
self.prepare(true);
|
||||
return self[QueryFile.$query];
|
||||
};
|
||||
|
||||
QueryFile.prototype[npm.formatting.as.ctf.rawType] = true; // use as pre-formatted
|
||||
|
||||
/**
|
||||
* @method QueryFile#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the object's current state.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
QueryFile.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap = npm.utils.messageGap(level + 1);
|
||||
const lines = [
|
||||
`QueryFile {`
|
||||
];
|
||||
this.prepare();
|
||||
lines.push(gap + `file: "` + this.file + `"`);
|
||||
lines.push(gap + `options: ` + npm.utils.toJson(this.options));
|
||||
if (this.error) {
|
||||
lines.push(gap + `error: ` + this.error.toString(level + 1));
|
||||
} else {
|
||||
lines.push(gap + `query: "` + this[QueryFile.$query] + `"`);
|
||||
}
|
||||
lines.push(npm.utils.messageGap(level) + `}`);
|
||||
return lines.join(npm.os.EOL);
|
||||
};
|
||||
|
||||
npm.utils.addInspection(QueryFile, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
module.exports = {QueryFile};
|
||||
|
||||
/**
|
||||
* @typedef QueryFile.Options
|
||||
* @description
|
||||
* A set of configuration options as passed into the {@link QueryFile} constructor.
|
||||
*
|
||||
* @property {boolean} debug
|
||||
* When in debug mode, the query file is checked for its last modification time on every query request,
|
||||
* so if it changes, the file is read afresh.
|
||||
*
|
||||
* The default for this property is `true` when `NODE_ENV` = `development`,
|
||||
* or `false` otherwise.
|
||||
*
|
||||
* @property {boolean|string} minify=false
|
||||
* Parses and minifies the SQL using $[pg-minify]:
|
||||
* - `false` - do not use $[pg-minify]
|
||||
* - `true` - use $[pg-minify] to parse and minify SQL
|
||||
* - `'after'` - use $[pg-minify] after applying static formatting parameters
|
||||
* (option `params`), as opposed to before it (default)
|
||||
*
|
||||
* If option `compress` is set, then the default for `minify` is `true`.
|
||||
*
|
||||
* Failure to parse SQL will result in $[SQLParsingError].
|
||||
*
|
||||
* @property {boolean} compress=false
|
||||
* Sets option `compress` as supported by $[pg-minify], to uglify the SQL:
|
||||
* - `false` - no compression to be applied, keep minimum spaces for easier read
|
||||
* - `true` - remove all unnecessary spaces from SQL
|
||||
*
|
||||
* This option has no meaning, if `minify` is explicitly set to `false`. However, if `minify` is not
|
||||
* specified and `compress` is specified as `true`, then `minify` defaults to `true`.
|
||||
*
|
||||
* @property {array|object|value} params
|
||||
*
|
||||
* Static formatting parameters to be applied to the SQL, using the same method {@link formatting.format as.format},
|
||||
* but with option `partial` = `true`.
|
||||
*
|
||||
* Most of the time query formatting is fully dynamic, and applied just before executing the query.
|
||||
* In some cases though you may need to pre-format SQL with static values. Examples of it can be a
|
||||
* schema name, or a configurable table name.
|
||||
*
|
||||
* This option makes two-step SQL formatting easy: you can pre-format the SQL initially, and then
|
||||
* apply the second-step dynamic formatting when executing the query.
|
||||
*
|
||||
* @property {boolean} noWarnings=false
|
||||
* Suppresses all warnings produced by the class. It is not recommended for general use, only in specific tests
|
||||
* that may require it.
|
||||
*
|
||||
*/
|
||||
39
ProjectSourceCode/node_modules/pg-promise/lib/query-result.js
generated
vendored
Normal file
39
ProjectSourceCode/node_modules/pg-promise/lib/query-result.js
generated
vendored
Normal file
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @enum {number}
|
||||
* @alias queryResult
|
||||
* @readonly
|
||||
* @description
|
||||
* **Query Result Mask**
|
||||
*
|
||||
* Binary mask that represents the number of rows expected from a query method,
|
||||
* used by generic {@link Database#query query} method, plus {@link Database#func func}.
|
||||
*
|
||||
* The mask is always the last optional parameter, which defaults to `queryResult.any`.
|
||||
*
|
||||
* Any combination of flags is supported, except for `one + many`.
|
||||
*
|
||||
* The type is available from the library's root: `pgp.queryResult`.
|
||||
*
|
||||
* @see {@link Database#query Database.query}, {@link Database#func Database.func}
|
||||
*/
|
||||
const queryResult = {
|
||||
/** Single row is expected, to be resolved as a single row-object. */
|
||||
one: 1,
|
||||
/** One or more rows expected, to be resolved as an array, with at least 1 row-object. */
|
||||
many: 2,
|
||||
/** Expecting no rows, to be resolved with `null`. */
|
||||
none: 4,
|
||||
/** `many|none` - any result is expected, to be resolved with an array of rows-objects. */
|
||||
any: 6
|
||||
};
|
||||
|
||||
module.exports = {queryResult};
|
||||
279
ProjectSourceCode/node_modules/pg-promise/lib/query.js
generated
vendored
Normal file
279
ProjectSourceCode/node_modules/pg-promise/lib/query.js
generated
vendored
Normal file
@@ -0,0 +1,279 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {Events} = require(`./events`);
|
||||
const {QueryFile} = require(`./query-file`);
|
||||
const {ServerFormatting, PreparedStatement, ParameterizedQuery} = require(`./types`);
|
||||
const {SpecialQuery} = require(`./special-query`);
|
||||
const {queryResult} = require(`./query-result`);
|
||||
|
||||
const npm = {
|
||||
util: require(`util`),
|
||||
utils: require(`./utils`),
|
||||
formatting: require(`./formatting`),
|
||||
errors: require(`./errors`),
|
||||
stream: require(`./stream`),
|
||||
text: require(`./text`)
|
||||
};
|
||||
|
||||
const QueryResultError = npm.errors.QueryResultError,
|
||||
InternalError = npm.utils.InternalError,
|
||||
qrec = npm.errors.queryResultErrorCode;
|
||||
|
||||
const badMask = queryResult.one | queryResult.many; // unsupported combination bit-mask;
|
||||
|
||||
//////////////////////////////
|
||||
// Generic query method;
|
||||
function $query(ctx, query, values, qrm, config) {
|
||||
|
||||
const special = qrm instanceof SpecialQuery && qrm;
|
||||
const $p = config.promise;
|
||||
|
||||
if (special && special.isStream) {
|
||||
return npm.stream.call(this, ctx, query, values, config);
|
||||
}
|
||||
|
||||
const opt = ctx.options,
|
||||
capSQL = opt.capSQL;
|
||||
|
||||
let error, entityType,
|
||||
pgFormatting = opt.pgFormatting,
|
||||
params = pgFormatting ? values : undefined;
|
||||
|
||||
if (typeof query === `function`) {
|
||||
try {
|
||||
query = npm.formatting.resolveFunc(query, values);
|
||||
} catch (e) {
|
||||
error = e;
|
||||
params = values;
|
||||
query = npm.util.inspect(query);
|
||||
}
|
||||
}
|
||||
|
||||
if (!error && !query) {
|
||||
error = new TypeError(npm.text.invalidQuery);
|
||||
}
|
||||
|
||||
if (!error && typeof query === `object`) {
|
||||
if (query instanceof QueryFile) {
|
||||
query.prepare();
|
||||
if (query.error) {
|
||||
error = query.error;
|
||||
query = query.file;
|
||||
} else {
|
||||
query = query[QueryFile.$query];
|
||||
}
|
||||
} else {
|
||||
if (`entity` in query) {
|
||||
entityType = query.type;
|
||||
query = query.entity; // query is a function name;
|
||||
} else {
|
||||
if (query instanceof ServerFormatting) {
|
||||
pgFormatting = true;
|
||||
} else {
|
||||
if (`name` in query) {
|
||||
query = new PreparedStatement(query);
|
||||
pgFormatting = true;
|
||||
} else {
|
||||
if (`text` in query) {
|
||||
query = new ParameterizedQuery(query);
|
||||
pgFormatting = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (query instanceof ServerFormatting && !npm.utils.isNull(values)) {
|
||||
query.values = values;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!error) {
|
||||
if (!pgFormatting && !npm.utils.isText(query)) {
|
||||
const errTxt = entityType ? (entityType === `func` ? npm.text.invalidFunction : npm.text.invalidProc) : npm.text.invalidQuery;
|
||||
error = new TypeError(errTxt);
|
||||
}
|
||||
if (query instanceof ServerFormatting) {
|
||||
const qp = query.parse();
|
||||
if (qp instanceof Error) {
|
||||
error = qp;
|
||||
} else {
|
||||
query = qp;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!error && !special) {
|
||||
if (npm.utils.isNull(qrm)) {
|
||||
qrm = queryResult.any; // default query result;
|
||||
} else {
|
||||
if (qrm !== parseInt(qrm) || (qrm & badMask) === badMask || qrm < 1 || qrm > 6) {
|
||||
error = new TypeError(npm.text.invalidMask);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!error && (!pgFormatting || entityType)) {
|
||||
try {
|
||||
// use 'pg-promise' implementation of values formatting;
|
||||
if (entityType) {
|
||||
params = undefined;
|
||||
query = npm.formatting.formatEntity(query, values, {capSQL, type: entityType});
|
||||
} else {
|
||||
query = npm.formatting.formatQuery(query, values);
|
||||
}
|
||||
} catch (e) {
|
||||
if (entityType) {
|
||||
let prefix = entityType === `func` ? `select * from` : `call`;
|
||||
if (capSQL) {
|
||||
prefix = prefix.toUpperCase();
|
||||
}
|
||||
query = prefix + ` ` + query + `(...)`;
|
||||
} else {
|
||||
params = values;
|
||||
}
|
||||
error = e instanceof Error ? e : new npm.utils.InternalError(e);
|
||||
}
|
||||
}
|
||||
|
||||
return $p((resolve, reject) => {
|
||||
|
||||
if (notifyReject()) {
|
||||
return;
|
||||
}
|
||||
error = Events.query(opt, getContext());
|
||||
if (notifyReject()) {
|
||||
return;
|
||||
}
|
||||
try {
|
||||
const start = Date.now();
|
||||
ctx.db.client.query(query, params, (err, result) => {
|
||||
let data, multiResult, lastResult = result;
|
||||
if (err) {
|
||||
// istanbul ignore if (auto-testing connectivity issues is too problematic)
|
||||
if (npm.utils.isConnectivityError(err)) {
|
||||
ctx.db.client.$connectionError = err;
|
||||
}
|
||||
err.query = err.query || query;
|
||||
err.params = err.params || params;
|
||||
error = err;
|
||||
} else {
|
||||
multiResult = Array.isArray(result);
|
||||
if (multiResult) {
|
||||
lastResult = result[result.length - 1];
|
||||
for (let i = 0; i < result.length; i++) {
|
||||
const r = result[i];
|
||||
makeIterable(r);
|
||||
error = Events.receive(opt, r.rows, r, getContext());
|
||||
if (error) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
makeIterable(result);
|
||||
result.duration = Date.now() - start;
|
||||
error = Events.receive(opt, result.rows, result, getContext());
|
||||
}
|
||||
}
|
||||
if (!error) {
|
||||
data = lastResult;
|
||||
if (special) {
|
||||
if (special.isMultiResult) {
|
||||
data = multiResult ? result : [result]; // method .multiResult() is called
|
||||
}
|
||||
// else, method .result() is called
|
||||
} else {
|
||||
data = data.rows;
|
||||
const len = data.length;
|
||||
if (len) {
|
||||
if (len > 1 && qrm & queryResult.one) {
|
||||
// one row was expected, but returned multiple;
|
||||
error = new QueryResultError(qrec.multiple, lastResult, query, params);
|
||||
} else {
|
||||
if (!(qrm & (queryResult.one | queryResult.many))) {
|
||||
// no data should have been returned;
|
||||
error = new QueryResultError(qrec.notEmpty, lastResult, query, params);
|
||||
} else {
|
||||
if (!(qrm & queryResult.many)) {
|
||||
data = data[0];
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// no data returned;
|
||||
if (qrm & queryResult.none) {
|
||||
if (qrm & queryResult.one) {
|
||||
data = null;
|
||||
} else {
|
||||
data = qrm & queryResult.many ? data : null;
|
||||
}
|
||||
} else {
|
||||
error = new QueryResultError(qrec.noData, lastResult, query, params);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!notifyReject()) {
|
||||
resolve(data);
|
||||
}
|
||||
});
|
||||
} catch (e) {
|
||||
// this can only happen as a result of an internal failure within node-postgres,
|
||||
// like during a sudden loss of communications, which is impossible to reproduce
|
||||
// automatically, so removing it from the test coverage:
|
||||
// istanbul ignore next
|
||||
error = e;
|
||||
}
|
||||
|
||||
function getContext() {
|
||||
let client;
|
||||
if (ctx.db) {
|
||||
client = ctx.db.client;
|
||||
} else {
|
||||
error = new Error(npm.text.looseQuery);
|
||||
}
|
||||
return {
|
||||
client, query, params,
|
||||
dc: ctx.dc,
|
||||
ctx: ctx.ctx
|
||||
};
|
||||
}
|
||||
|
||||
notifyReject();
|
||||
|
||||
function notifyReject() {
|
||||
const context = getContext();
|
||||
if (error) {
|
||||
if (error instanceof InternalError) {
|
||||
error = error.error;
|
||||
}
|
||||
Events.error(opt, error, context);
|
||||
reject(error);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// Extends Result to provide iterable for the rows;
|
||||
//
|
||||
// To be removed once the following PR is merged amd released:
|
||||
// https://github.com/brianc/node-postgres/pull/2861
|
||||
function makeIterable(r) {
|
||||
r[Symbol.iterator] = function () {
|
||||
return this.rows.values();
|
||||
};
|
||||
}
|
||||
|
||||
module.exports = config => {
|
||||
return function (ctx, query, values, qrm) {
|
||||
return $query.call(this, ctx, query, values, qrm, config);
|
||||
};
|
||||
};
|
||||
30
ProjectSourceCode/node_modules/pg-promise/lib/special-query.js
generated
vendored
Normal file
30
ProjectSourceCode/node_modules/pg-promise/lib/special-query.js
generated
vendored
Normal file
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const specialQueryType = {
|
||||
result: 0,
|
||||
multiResult: 1,
|
||||
stream: 2
|
||||
};
|
||||
|
||||
class SpecialQuery {
|
||||
constructor(type) {
|
||||
this.isResult = type === specialQueryType.result; // type used implicitly
|
||||
this.isStream = type === specialQueryType.stream;
|
||||
this.isMultiResult = type === specialQueryType.multiResult;
|
||||
}
|
||||
}
|
||||
|
||||
const cache = {
|
||||
resultQuery: new SpecialQuery(specialQueryType.result),
|
||||
multiResultQuery: new SpecialQuery(specialQueryType.multiResult),
|
||||
streamQuery: new SpecialQuery(specialQueryType.stream)
|
||||
};
|
||||
|
||||
module.exports = Object.assign({SpecialQuery}, cache);
|
||||
127
ProjectSourceCode/node_modules/pg-promise/lib/stream.js
generated
vendored
Normal file
127
ProjectSourceCode/node_modules/pg-promise/lib/stream.js
generated
vendored
Normal file
@@ -0,0 +1,127 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {Events} = require(`./events`);
|
||||
|
||||
const npm = {
|
||||
utils: require(`./utils`),
|
||||
text: require(`./text`)
|
||||
};
|
||||
|
||||
////////////////////////////////////////////
|
||||
// Streams query data into any destination,
|
||||
// with the help of pg-query-stream library.
|
||||
function $stream(ctx, qs, initCB, config) {
|
||||
|
||||
const $p = config.promise;
|
||||
|
||||
// istanbul ignore next:
|
||||
// we do not provide code coverage for the Native Bindings specifics
|
||||
if (ctx.options.pgNative) {
|
||||
return $p.reject(new Error(npm.text.nativeStreaming));
|
||||
}
|
||||
// Stream class was renamed again, see the following issue:
|
||||
// https://github.com/brianc/node-postgres/issues/2412
|
||||
if (!qs || !qs.constructor || qs.constructor.name !== `QueryStream`) {
|
||||
// invalid or missing stream object;
|
||||
return $p.reject(new TypeError(npm.text.invalidStream));
|
||||
}
|
||||
if (qs._reading || qs._closed) {
|
||||
// stream object is in the wrong state;
|
||||
return $p.reject(new Error(npm.text.invalidStreamState));
|
||||
}
|
||||
if (typeof initCB !== `function`) {
|
||||
// parameter `initCB` must be passed as the initialization callback;
|
||||
return $p.reject(new TypeError(npm.text.invalidStreamCB));
|
||||
}
|
||||
|
||||
let error = Events.query(ctx.options, getContext());
|
||||
|
||||
if (error) {
|
||||
error = getError(error);
|
||||
Events.error(ctx.options, error, getContext());
|
||||
return $p.reject(error);
|
||||
}
|
||||
|
||||
const stream = ctx.db.client.query(qs);
|
||||
|
||||
stream.on(`data`, onData);
|
||||
stream.on(`error`, onError);
|
||||
stream.on(`end`, onEnd);
|
||||
|
||||
try {
|
||||
initCB.call(this, stream); // the stream must be initialized during the call;
|
||||
} catch (e) {
|
||||
release();
|
||||
error = getError(e);
|
||||
Events.error(ctx.options, error, getContext());
|
||||
return $p.reject(error);
|
||||
}
|
||||
|
||||
const start = Date.now();
|
||||
let resolve, reject, nRows = 0;
|
||||
|
||||
function onData(data) {
|
||||
nRows++;
|
||||
error = Events.receive(ctx.options, [data], undefined, getContext());
|
||||
if (error) {
|
||||
onError(error);
|
||||
}
|
||||
}
|
||||
|
||||
function onError(e) {
|
||||
release();
|
||||
stream.destroy();
|
||||
e = getError(e);
|
||||
Events.error(ctx.options, e, getContext());
|
||||
reject(e);
|
||||
}
|
||||
|
||||
function onEnd() {
|
||||
release();
|
||||
resolve({
|
||||
processed: nRows, // total number of rows processed;
|
||||
duration: Date.now() - start // duration, in milliseconds;
|
||||
});
|
||||
}
|
||||
|
||||
function release() {
|
||||
stream.removeListener(`data`, onData);
|
||||
stream.removeListener(`error`, onError);
|
||||
stream.removeListener(`end`, onEnd);
|
||||
}
|
||||
|
||||
function getError(e) {
|
||||
return e instanceof npm.utils.InternalError ? e.error : e;
|
||||
}
|
||||
|
||||
function getContext() {
|
||||
let client;
|
||||
if (ctx.db) {
|
||||
client = ctx.db.client;
|
||||
} else {
|
||||
error = new Error(npm.text.looseQuery);
|
||||
}
|
||||
return {
|
||||
client,
|
||||
dc: ctx.dc,
|
||||
query: qs.cursor.text,
|
||||
params: qs.cursor.values,
|
||||
ctx: ctx.ctx
|
||||
};
|
||||
}
|
||||
|
||||
return $p((res, rej) => {
|
||||
resolve = res;
|
||||
reject = rej;
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
module.exports = $stream;
|
||||
416
ProjectSourceCode/node_modules/pg-promise/lib/task.js
generated
vendored
Normal file
416
ProjectSourceCode/node_modules/pg-promise/lib/task.js
generated
vendored
Normal file
@@ -0,0 +1,416 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {Events} = require(`./events`);
|
||||
|
||||
const npm = {
|
||||
spex: require(`spex`),
|
||||
utils: require(`./utils`),
|
||||
mode: require(`./tx-mode`),
|
||||
query: require(`./query`),
|
||||
text: require(`./text`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @interface Task
|
||||
* @description
|
||||
* Extends {@link Database} for an automatic connection session, with methods for executing multiple database queries.
|
||||
*
|
||||
* The type isn't available directly, it can only be created via methods {@link Database#task Database.task}, {@link Database#tx Database.tx},
|
||||
* or their derivations.
|
||||
*
|
||||
* When executing more than one request at a time, one should allocate and release the connection only once,
|
||||
* while executing all the required queries within the same connection session. More importantly, a transaction
|
||||
* can only work within a single connection.
|
||||
*
|
||||
* This is an interface for tasks/transactions to implement a connection session, during which you can
|
||||
* execute multiple queries against the same connection that's released automatically when the task/transaction is finished.
|
||||
*
|
||||
* Each task/transaction manages the connection automatically. When executed on the root {@link Database} object, the connection
|
||||
* is allocated from the pool, and once the method's callback has finished, the connection is released back to the pool.
|
||||
* However, when invoked inside another task or transaction, the method reuses the parent connection.
|
||||
*
|
||||
* @see
|
||||
* {@link Task#ctx ctx},
|
||||
* {@link Task#batch batch},
|
||||
* {@link Task#sequence sequence},
|
||||
* {@link Task#page page}
|
||||
*
|
||||
* @example
|
||||
* db.task(t => {
|
||||
* // t = task protocol context;
|
||||
* // t.ctx = Task Context;
|
||||
* return t.one('select * from users where id=$1', 123)
|
||||
* .then(user => {
|
||||
* return t.any('select * from events where login=$1', user.name);
|
||||
* });
|
||||
* })
|
||||
* .then(events => {
|
||||
* // success;
|
||||
* })
|
||||
* .catch(error => {
|
||||
* // error;
|
||||
* });
|
||||
*
|
||||
*/
|
||||
function Task(ctx, tag, isTX, config) {
|
||||
|
||||
const $p = config.promise;
|
||||
|
||||
/**
|
||||
* @member {TaskContext} Task#ctx
|
||||
* @readonly
|
||||
* @description
|
||||
* Task/Transaction Context object - contains individual properties for each task/transaction.
|
||||
*
|
||||
* @see event {@link event:query query}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* db.task(t => {
|
||||
* return t.ctx; // task context object
|
||||
* })
|
||||
* .then(ctx => {
|
||||
* console.log('Task Duration:', ctx.duration);
|
||||
* });
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* db.tx(t => {
|
||||
* return t.ctx; // transaction context object
|
||||
* })
|
||||
* .then(ctx => {
|
||||
* console.log('Transaction Duration:', ctx.duration);
|
||||
* });
|
||||
*/
|
||||
this.ctx = ctx.ctx = {}; // task context object;
|
||||
|
||||
npm.utils.addReadProp(this.ctx, `isTX`, isTX);
|
||||
|
||||
if (`context` in ctx) {
|
||||
npm.utils.addReadProp(this.ctx, `context`, ctx.context);
|
||||
}
|
||||
|
||||
npm.utils.addReadProp(this.ctx, `connected`, !ctx.db);
|
||||
npm.utils.addReadProp(this.ctx, `tag`, tag);
|
||||
npm.utils.addReadProp(this.ctx, `dc`, ctx.dc);
|
||||
npm.utils.addReadProp(this.ctx, `level`, ctx.level);
|
||||
npm.utils.addReadProp(this.ctx, `inTransaction`, ctx.inTransaction);
|
||||
|
||||
if (isTX) {
|
||||
npm.utils.addReadProp(this.ctx, `txLevel`, ctx.txLevel);
|
||||
}
|
||||
|
||||
npm.utils.addReadProp(this.ctx, `parent`, ctx.parentCtx);
|
||||
|
||||
// generic query method;
|
||||
this.query = function (query, values, qrm) {
|
||||
if (!ctx.db) {
|
||||
return $p.reject(new Error(npm.text.looseQuery));
|
||||
}
|
||||
return config.$npm.query.call(this, ctx, query, values, qrm);
|
||||
};
|
||||
|
||||
/**
|
||||
* @method Task#batch
|
||||
* @description
|
||||
* Settles a predefined array of mixed values by redirecting to method $[spex.batch].
|
||||
*
|
||||
* For complete method documentation see $[spex.batch].
|
||||
*
|
||||
* @param {array} values
|
||||
* @param {Object} [options]
|
||||
* Optional Parameters.
|
||||
* @param {function} [options.cb]
|
||||
*
|
||||
* @returns {external:Promise}
|
||||
*/
|
||||
this.batch = function (values, options) {
|
||||
return config.$npm.spex.batch.call(this, values, options);
|
||||
};
|
||||
|
||||
/**
|
||||
* @method Task#page
|
||||
* @description
|
||||
* Resolves a dynamic sequence of arrays/pages with mixed values, by redirecting to method $[spex.page].
|
||||
*
|
||||
* For complete method documentation see $[spex.page].
|
||||
*
|
||||
* @param {function} source
|
||||
* @param {Object} [options]
|
||||
* Optional Parameters.
|
||||
* @param {function} [options.dest]
|
||||
* @param {number} [options.limit=0]
|
||||
*
|
||||
* @returns {external:Promise}
|
||||
*/
|
||||
this.page = function (source, options) {
|
||||
return config.$npm.spex.page.call(this, source, options);
|
||||
};
|
||||
|
||||
/**
|
||||
* @method Task#sequence
|
||||
* @description
|
||||
* Resolves a dynamic sequence of mixed values by redirecting to method $[spex.sequence].
|
||||
*
|
||||
* For complete method documentation see $[spex.sequence].
|
||||
*
|
||||
* @param {function} source
|
||||
* @param {Object} [options]
|
||||
* Optional Parameters.
|
||||
* @param {function} [options.dest]
|
||||
* @param {number} [options.limit=0]
|
||||
* @param {boolean} [options.track=false]
|
||||
*
|
||||
* @returns {external:Promise}
|
||||
*/
|
||||
this.sequence = function (source, options) {
|
||||
return config.$npm.spex.sequence.call(this, source, options);
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @method Task.callback
|
||||
* Callback invocation helper.
|
||||
*
|
||||
* @param ctx
|
||||
* @param obj
|
||||
* @param cb
|
||||
* @param config
|
||||
* @returns {Promise.<TResult>}
|
||||
*/
|
||||
const callback = (ctx, obj, cb, config) => {
|
||||
|
||||
const $p = config.promise;
|
||||
let result;
|
||||
|
||||
try {
|
||||
if (cb.constructor.name === `GeneratorFunction`) {
|
||||
// v9.0 dropped all support for ES6 generator functions;
|
||||
// Clients should use the new ES7 async/await syntax.
|
||||
throw new TypeError(`ES6 generator functions are no longer supported!`);
|
||||
}
|
||||
result = cb.call(obj, obj); // invoking the callback function;
|
||||
} catch (err) {
|
||||
Events.error(ctx.options, err, {
|
||||
client: ctx.db && ctx.db.client, // the error can be due to loss of connectivity
|
||||
dc: ctx.dc,
|
||||
ctx: ctx.ctx
|
||||
});
|
||||
return $p.reject(err); // reject with the error;
|
||||
}
|
||||
if (result && typeof result.then === `function`) {
|
||||
return result; // result is a valid promise object;
|
||||
}
|
||||
return $p.resolve(result);
|
||||
};
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @method Task.execute
|
||||
* Executes a task.
|
||||
*
|
||||
* @param ctx
|
||||
* @param obj
|
||||
* @param isTX
|
||||
* @param config
|
||||
* @returns {Promise.<TResult>}
|
||||
*/
|
||||
const execute = (ctx, obj, isTX, config) => {
|
||||
|
||||
const $p = config.promise;
|
||||
|
||||
// updates the task context and notifies the client;
|
||||
function update(start, success, result) {
|
||||
const c = ctx.ctx;
|
||||
if (start) {
|
||||
npm.utils.addReadProp(c, `start`, new Date());
|
||||
} else {
|
||||
c.finish = new Date();
|
||||
c.success = success;
|
||||
c.result = result;
|
||||
c.duration = c.finish - c.start;
|
||||
npm.utils.lock(c, true);
|
||||
}
|
||||
(isTX ? Events.transact : Events.task)(ctx.options, {
|
||||
client: ctx.db && ctx.db.client, // loss of connectivity is possible at this point
|
||||
dc: ctx.dc,
|
||||
ctx: c
|
||||
});
|
||||
}
|
||||
|
||||
let cbData, cbReason, success,
|
||||
spName; // Save-Point Name;
|
||||
|
||||
const capSQL = ctx.options.capSQL; // capitalize sql;
|
||||
|
||||
update(true);
|
||||
|
||||
if (isTX) {
|
||||
// executing a transaction;
|
||||
spName = `sp_${ctx.txLevel}_${ctx.nextTxCount}`;
|
||||
return begin()
|
||||
.then(() => callback(ctx, obj, ctx.cb, config)
|
||||
.then(data => {
|
||||
cbData = data; // save callback data;
|
||||
success = true;
|
||||
return commit();
|
||||
}, err => {
|
||||
cbReason = err; // save callback failure reason;
|
||||
return rollback();
|
||||
})
|
||||
.then(() => {
|
||||
if (success) {
|
||||
update(false, true, cbData);
|
||||
return cbData;
|
||||
}
|
||||
update(false, false, cbReason);
|
||||
return $p.reject(cbReason);
|
||||
},
|
||||
err => {
|
||||
// either COMMIT or ROLLBACK has failed, which is impossible
|
||||
// to replicate in a test environment, so skipping from the test;
|
||||
// istanbul ignore next:
|
||||
update(false, false, err);
|
||||
// istanbul ignore next:
|
||||
return $p.reject(err);
|
||||
}),
|
||||
err => {
|
||||
// BEGIN has failed, which is impossible to replicate in a test
|
||||
// environment, so skipping the whole block from the test;
|
||||
// istanbul ignore next:
|
||||
update(false, false, err);
|
||||
// istanbul ignore next:
|
||||
return $p.reject(err);
|
||||
});
|
||||
}
|
||||
|
||||
function begin() {
|
||||
if (!ctx.txLevel && ctx.mode instanceof npm.mode.TransactionMode) {
|
||||
return exec(ctx.mode.begin(capSQL), `savepoint`);
|
||||
}
|
||||
return exec(`begin`, `savepoint`);
|
||||
}
|
||||
|
||||
function commit() {
|
||||
return exec(`commit`, `release savepoint`);
|
||||
}
|
||||
|
||||
function rollback() {
|
||||
return exec(`rollback`, `rollback to savepoint`);
|
||||
}
|
||||
|
||||
function exec(top, nested) {
|
||||
if (ctx.txLevel) {
|
||||
return obj.none((capSQL ? nested.toUpperCase() : nested) + ` ` + spName);
|
||||
}
|
||||
return obj.none(capSQL ? top.toUpperCase() : top);
|
||||
}
|
||||
|
||||
// executing a task;
|
||||
return callback(ctx, obj, ctx.cb, config)
|
||||
.then(data => {
|
||||
update(false, true, data);
|
||||
return data;
|
||||
})
|
||||
.catch(error => {
|
||||
update(false, false, error);
|
||||
return $p.reject(error);
|
||||
});
|
||||
};
|
||||
|
||||
module.exports = config => {
|
||||
const npmLocal = config.$npm;
|
||||
|
||||
// istanbul ignore next:
|
||||
// we keep 'npm.query' initialization here, even though it is always
|
||||
// pre-initialized by the 'database' module, for integrity purpose.
|
||||
npmLocal.query = npmLocal.query || npm.query(config);
|
||||
npmLocal.spex = npmLocal.spex || npm.spex(config.promiseLib);
|
||||
|
||||
return {
|
||||
Task, execute, callback
|
||||
};
|
||||
};
|
||||
|
||||
/**
|
||||
* @typedef TaskContext
|
||||
* @description
|
||||
* Task/Transaction Context used via property {@link Task#ctx ctx} inside tasks (methods {@link Database#task Database.task} and {@link Database#taskIf Database.taskIf})
|
||||
* and transactions (methods {@link Database#tx Database.tx} and {@link Database#txIf Database.txIf}).
|
||||
*
|
||||
* Properties `context`, `connected`, `parent`, `level`, `dc`, `isTX`, `tag`, `start`, `useCount` and `serverVersion` are set just before the operation has started,
|
||||
* while properties `finish`, `duration`, `success` and `result` are set immediately after the operation has finished.
|
||||
*
|
||||
* @property {*} context
|
||||
* If the operation was invoked with a calling context - `task.call(context,...)` or `tx.call(context,...)`,
|
||||
* this property is set with the context that was passed in. Otherwise, the property doesn't exist.
|
||||
*
|
||||
* @property {*} dc
|
||||
* _Database Context_ that was passed into the {@link Database} object during construction.
|
||||
*
|
||||
* @property {boolean} isTX
|
||||
* Indicates whether this operation is a transaction (as opposed to a regular task).
|
||||
*
|
||||
* @property {number} duration
|
||||
* Number of milliseconds consumed by the operation.
|
||||
*
|
||||
* Set after the operation has finished, it is simply a shortcut for `finish - start`.
|
||||
*
|
||||
* @property {number} level
|
||||
* Task nesting level, starting from 0, counting both regular tasks and transactions.
|
||||
*
|
||||
* @property {number} txLevel
|
||||
* Transaction nesting level, starting from 0. Transactions on level 0 use `BEGIN/COMMIT/ROLLBACK`,
|
||||
* while transactions on nested levels use the corresponding `SAVEPOINT` commands.
|
||||
*
|
||||
* This property exists only within the context of a transaction (`isTX = true`).
|
||||
*
|
||||
* @property {boolean} inTransaction
|
||||
* Available in both tasks and transactions, it simplifies checking when there is a transaction
|
||||
* going on either on this level or above.
|
||||
*
|
||||
* For example, when you want to check for a containing transaction while inside a task, and
|
||||
* only start a transaction when there is none yet.
|
||||
*
|
||||
* @property {TaskContext} parent
|
||||
* Parent task/transaction context, or `null` when it is top-level.
|
||||
*
|
||||
* @property {boolean} connected
|
||||
* Indicates when the task/transaction acquired the connection on its own (`connected = true`), and will release it once
|
||||
* the operation has finished. When the value is `false`, the operation is reusing an existing connection.
|
||||
*
|
||||
* @property {*} tag
|
||||
* Tag value as it was passed into the task. See methods {@link Database#task task} and {@link Database#tx tx}.
|
||||
*
|
||||
* @property {Date} start
|
||||
* Date/Time of when this operation started the execution.
|
||||
*
|
||||
* @property {number} useCount
|
||||
* Number of times the connection has been previously used, starting with 0 for a freshly
|
||||
* allocated physical connection.
|
||||
*
|
||||
* @property {string} serverVersion
|
||||
* Version of the PostgreSQL server to which we are connected.
|
||||
* Not available with $[Native Bindings].
|
||||
*
|
||||
* @property {Date} finish
|
||||
* Once the operation has finished, this property is set to the Data/Time of when it happened.
|
||||
*
|
||||
* @property {boolean} success
|
||||
* Once the operation has finished, this property indicates whether it was successful.
|
||||
*
|
||||
* @property {*} result
|
||||
* Once the operation has finished, this property contains the result, depending on property `success`:
|
||||
* - data resolved by the operation, if `success = true`
|
||||
* - error / rejection reason, if `success = false`
|
||||
*
|
||||
*/
|
||||
40
ProjectSourceCode/node_modules/pg-promise/lib/text.js
generated
vendored
Normal file
40
ProjectSourceCode/node_modules/pg-promise/lib/text.js
generated
vendored
Normal file
@@ -0,0 +1,40 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
/* All error messages used in the module */
|
||||
|
||||
const streamVersion = require(`../package.json`)
|
||||
.devDependencies[`pg-query-stream`];
|
||||
|
||||
module.exports = {
|
||||
nativeError: `Failed to initialize Native Bindings.`,
|
||||
|
||||
/* Database errors */
|
||||
queryDisconnected: `Cannot execute a query on a disconnected client.`,
|
||||
invalidQuery: `Invalid query format.`,
|
||||
invalidFunction: `Invalid function name.`,
|
||||
invalidProc: `Invalid procedure name.`,
|
||||
invalidMask: `Invalid Query Result Mask specified.`,
|
||||
looseQuery: `Querying against a released or lost connection.`,
|
||||
|
||||
/* result errors */
|
||||
notEmpty: `No return data was expected.`,
|
||||
noData: `No data returned from the query.`,
|
||||
multiple: `Multiple rows were not expected.`,
|
||||
|
||||
/* streaming support */
|
||||
nativeStreaming: `Streaming doesn't work with Native Bindings.`,
|
||||
invalidStream: `Invalid or missing stream object: pg-query-stream >= v${streamVersion} was expected`,
|
||||
invalidStreamState: `Invalid stream state.`,
|
||||
invalidStreamCB: `Invalid or missing stream initialization callback.`,
|
||||
|
||||
/* connection errors */
|
||||
poolDestroyed: `Connection pool of the database object has been destroyed.`,
|
||||
clientEnd: `Abnormal client.end() call, due to invalid code or failed server connection.`
|
||||
};
|
||||
190
ProjectSourceCode/node_modules/pg-promise/lib/tx-mode.js
generated
vendored
Normal file
190
ProjectSourceCode/node_modules/pg-promise/lib/tx-mode.js
generated
vendored
Normal file
@@ -0,0 +1,190 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {InnerState} = require(`./inner-state`);
|
||||
const {addInspection} = require(`./utils`);
|
||||
const {assert} = require(`./assert`);
|
||||
|
||||
/**
|
||||
* @enum {number}
|
||||
* @alias txMode.isolationLevel
|
||||
* @readonly
|
||||
* @summary Transaction Isolation Level.
|
||||
* @description
|
||||
* The type is available from the {@link txMode} namespace.
|
||||
*
|
||||
* @see $[Transaction Isolation]
|
||||
*/
|
||||
const isolationLevel = {
|
||||
/** Isolation level not specified. */
|
||||
none: 0,
|
||||
|
||||
/** ISOLATION LEVEL SERIALIZABLE */
|
||||
serializable: 1,
|
||||
|
||||
/** ISOLATION LEVEL REPEATABLE READ */
|
||||
repeatableRead: 2,
|
||||
|
||||
/** ISOLATION LEVEL READ COMMITTED */
|
||||
readCommitted: 3
|
||||
|
||||
// From the official documentation: http://www.postgresql.org/docs/9.5/static/sql-set-transaction.html
|
||||
// The SQL standard defines one additional level, READ UNCOMMITTED. In PostgreSQL READ UNCOMMITTED is treated as READ COMMITTED.
|
||||
// => skipping `READ UNCOMMITTED`.
|
||||
};
|
||||
|
||||
/**
|
||||
* @class txMode.TransactionMode
|
||||
* @description
|
||||
* Constructs a complete transaction-opening `BEGIN` command, from these options:
|
||||
* - isolation level
|
||||
* - access mode
|
||||
* - deferrable mode
|
||||
*
|
||||
* The type is available from the {@link txMode} namespace.
|
||||
*
|
||||
* @param {} [options]
|
||||
* Transaction Mode options.
|
||||
*
|
||||
* @param {txMode.isolationLevel} [options.tiLevel]
|
||||
* Transaction Isolation Level.
|
||||
*
|
||||
* @param {boolean} [options.readOnly]
|
||||
* Sets transaction access mode based on the read-only flag:
|
||||
* - `undefined` - access mode not specified (default)
|
||||
* - `true` - access mode is set to `READ ONLY`
|
||||
* - `false` - access mode is set to `READ WRITE`
|
||||
*
|
||||
* @param {boolean} [options.deferrable]
|
||||
* Sets transaction deferrable mode based on the boolean value:
|
||||
* - `undefined` - deferrable mode not specified (default)
|
||||
* - `true` - mode is set to `DEFERRABLE`
|
||||
* - `false` - mode is set to `NOT DEFERRABLE`
|
||||
*
|
||||
* It is used only when `tiLevel`=`isolationLevel.serializable`
|
||||
* and `readOnly`=`true`, or else it is ignored.
|
||||
*
|
||||
* @returns {txMode.TransactionMode}
|
||||
*
|
||||
* @see $[BEGIN], {@link txMode.isolationLevel}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const {TransactionMode, isolationLevel} = pgp.txMode;
|
||||
*
|
||||
* // Create a reusable transaction mode (serializable + read-only + deferrable):
|
||||
* const mode = new TransactionMode({
|
||||
* tiLevel: isolationLevel.serializable,
|
||||
* readOnly: true,
|
||||
* deferrable: true
|
||||
* });
|
||||
*
|
||||
* db.tx({mode}, t => {
|
||||
* return t.any('SELECT * FROM table');
|
||||
* })
|
||||
* .then(data => {
|
||||
* // success;
|
||||
* })
|
||||
* .catch(error => {
|
||||
* // error
|
||||
* });
|
||||
*
|
||||
* // Instead of the default BEGIN, such transaction will start with:
|
||||
*
|
||||
* // BEGIN ISOLATION LEVEL SERIALIZABLE READ ONLY DEFERRABLE
|
||||
*
|
||||
*/
|
||||
class TransactionMode extends InnerState {
|
||||
|
||||
constructor(options) {
|
||||
options = assert(options, [`tiLevel`, `deferrable`, `readOnly`]);
|
||||
const {readOnly, deferrable} = options;
|
||||
let {tiLevel} = options;
|
||||
let level, accessMode, deferrableMode, begin = `begin`;
|
||||
tiLevel = (tiLevel > 0) ? parseInt(tiLevel) : 0;
|
||||
|
||||
if (tiLevel > 0 && tiLevel < 4) {
|
||||
const values = [`serializable`, `repeatable read`, `read committed`];
|
||||
level = `isolation level ` + values[tiLevel - 1];
|
||||
}
|
||||
if (readOnly) {
|
||||
accessMode = `read only`;
|
||||
} else {
|
||||
if (readOnly !== undefined) {
|
||||
accessMode = `read write`;
|
||||
}
|
||||
}
|
||||
// From the official documentation: http://www.postgresql.org/docs/9.5/static/sql-set-transaction.html
|
||||
// The DEFERRABLE transaction property has no effect unless the transaction is also SERIALIZABLE and READ ONLY
|
||||
if (tiLevel === isolationLevel.serializable && readOnly) {
|
||||
if (deferrable) {
|
||||
deferrableMode = `deferrable`;
|
||||
} else {
|
||||
if (deferrable !== undefined) {
|
||||
deferrableMode = `not deferrable`;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (level) {
|
||||
begin += ` ` + level;
|
||||
}
|
||||
if (accessMode) {
|
||||
begin += ` ` + accessMode;
|
||||
}
|
||||
if (deferrableMode) {
|
||||
begin += ` ` + deferrableMode;
|
||||
}
|
||||
|
||||
super({begin, capBegin: begin.toUpperCase()});
|
||||
}
|
||||
|
||||
/**
|
||||
* @method txMode.TransactionMode#begin
|
||||
* @description
|
||||
* Returns a complete BEGIN statement, according to all the parameters passed into the class.
|
||||
*
|
||||
* This method is primarily for internal use by the library.
|
||||
*
|
||||
* @param {boolean} [cap=false]
|
||||
* Indicates whether the returned SQL must be capitalized.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
begin(cap) {
|
||||
return cap ? this._inner.capBegin : this._inner.begin;
|
||||
}
|
||||
}
|
||||
|
||||
addInspection(TransactionMode, function () {
|
||||
return this.begin(true);
|
||||
});
|
||||
|
||||
/**
|
||||
* @namespace txMode
|
||||
* @description
|
||||
* Transaction Mode namespace, available as `pgp.txMode`, before and after initializing the library.
|
||||
*
|
||||
* Extends the default `BEGIN` with Transaction Mode parameters:
|
||||
* - isolation level
|
||||
* - access mode
|
||||
* - deferrable mode
|
||||
*
|
||||
* @property {function} TransactionMode
|
||||
* {@link txMode.TransactionMode TransactionMode} class constructor.
|
||||
*
|
||||
* @property {txMode.isolationLevel} isolationLevel
|
||||
* Transaction Isolation Level enumerator
|
||||
*
|
||||
* @see $[BEGIN]
|
||||
*/
|
||||
module.exports = {
|
||||
isolationLevel,
|
||||
TransactionMode
|
||||
};
|
||||
|
||||
18
ProjectSourceCode/node_modules/pg-promise/lib/types/index.js
generated
vendored
Normal file
18
ProjectSourceCode/node_modules/pg-promise/lib/types/index.js
generated
vendored
Normal file
@@ -0,0 +1,18 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {ServerFormatting} = require(`./server-formatting`);
|
||||
const {PreparedStatement} = require(`./prepared-statement`);
|
||||
const {ParameterizedQuery} = require(`./parameterized-query`);
|
||||
|
||||
module.exports = {
|
||||
ServerFormatting,
|
||||
PreparedStatement,
|
||||
ParameterizedQuery
|
||||
};
|
||||
250
ProjectSourceCode/node_modules/pg-promise/lib/types/parameterized-query.js
generated
vendored
Normal file
250
ProjectSourceCode/node_modules/pg-promise/lib/types/parameterized-query.js
generated
vendored
Normal file
@@ -0,0 +1,250 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {ServerFormatting} = require(`./server-formatting`);
|
||||
const {ParameterizedQueryError} = require(`../errors`);
|
||||
const {QueryFile} = require(`../query-file`);
|
||||
const {assert} = require(`../assert`);
|
||||
|
||||
const npm = {
|
||||
EOL: require(`os`).EOL,
|
||||
utils: require(`../utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @class ParameterizedQuery
|
||||
* @description
|
||||
* Constructs a new {@link ParameterizedQuery} object. All properties can also be set after the object's construction.
|
||||
*
|
||||
* This type extends the basic `{text, values}` object, i.e. when the basic object is used with a query method,
|
||||
* a new {@link ParameterizedQuery} object is created in its place.
|
||||
*
|
||||
* The type can be used in place of the `query` parameter, with any query method directly.
|
||||
*
|
||||
* The type is available from the library's root: `pgp.ParameterizedQuery`.
|
||||
*
|
||||
* @param {string|QueryFile|Object} [options]
|
||||
* Object configuration options / properties.
|
||||
*
|
||||
* @param {string|QueryFile} [options.text] - See property {@link ParameterizedQuery#text text}.
|
||||
* @param {array} [options.values] - See property {@link ParameterizedQuery#values values}.
|
||||
* @param {boolean} [options.binary] - See property {@link ParameterizedQuery#binary binary}.
|
||||
* @param {string} [options.rowMode] - See property {@link ParameterizedQuery#rowMode rowMode}.
|
||||
*
|
||||
* @returns {ParameterizedQuery}
|
||||
*
|
||||
* @see
|
||||
* {@link errors.ParameterizedQueryError ParameterizedQueryError}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const {ParameterizedQuery: PQ} = require('pg-promise');
|
||||
*
|
||||
* // Creating a complete Parameterized Query with parameters:
|
||||
* const findUser = new PQ({text: 'SELECT * FROM Users WHERE id = $1', values: [123]});
|
||||
*
|
||||
* db.one(findUser)
|
||||
* .then(user => {
|
||||
* // user found;
|
||||
* })
|
||||
* .catch(error => {
|
||||
* // error;
|
||||
* });
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const {ParameterizedQuery: PQ} = require('pg-promise');
|
||||
*
|
||||
* // Creating a reusable Parameterized Query without values:
|
||||
* const addUser = new PQ('INSERT INTO Users(name, age) VALUES($1, $2)');
|
||||
*
|
||||
* // setting values explicitly:
|
||||
* addUser.values = ['John', 30];
|
||||
*
|
||||
* db.none(addUser)
|
||||
* .then(() => {
|
||||
* // user added;
|
||||
* })
|
||||
* .catch(error=> {
|
||||
* // error;
|
||||
* });
|
||||
*
|
||||
* // setting values implicitly, by passing them into the query method:
|
||||
* db.none(addUser, ['Mike', 25])
|
||||
* .then(() => {
|
||||
* // user added;
|
||||
* })
|
||||
* .catch(error=> {
|
||||
* // error;
|
||||
* });
|
||||
*/
|
||||
class ParameterizedQuery extends ServerFormatting {
|
||||
constructor(options) {
|
||||
if (typeof options === `string` || options instanceof QueryFile) {
|
||||
options = {
|
||||
text: options
|
||||
};
|
||||
} else {
|
||||
options = assert(options, [`text`, `values`, `binary`, `rowMode`]);
|
||||
}
|
||||
super(options);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @method ParameterizedQuery#parse
|
||||
* @description
|
||||
* Parses the current object and returns a simple `{text, values}`, if successful,
|
||||
* or else it returns a {@link errors.ParameterizedQueryError ParameterizedQueryError} object.
|
||||
*
|
||||
* This method is primarily for internal use by the library.
|
||||
*
|
||||
* @returns {{text, values}|errors.ParameterizedQueryError}
|
||||
*/
|
||||
ParameterizedQuery.prototype.parse = function () {
|
||||
|
||||
const _i = this._inner, options = _i.options;
|
||||
const qf = options.text instanceof QueryFile ? options.text : null;
|
||||
|
||||
if (!_i.changed && !qf) {
|
||||
return _i.target;
|
||||
}
|
||||
|
||||
const errors = [], values = _i.target.values;
|
||||
_i.target = {
|
||||
text: options.text
|
||||
};
|
||||
_i.changed = true;
|
||||
_i.currentError = undefined;
|
||||
|
||||
if (qf) {
|
||||
qf.prepare();
|
||||
if (qf.error) {
|
||||
errors.push(qf.error);
|
||||
} else {
|
||||
_i.target.text = qf[QueryFile.$query];
|
||||
}
|
||||
}
|
||||
|
||||
if (!npm.utils.isText(_i.target.text)) {
|
||||
errors.push(`Property 'text' must be a non-empty text string.`);
|
||||
}
|
||||
|
||||
if (!npm.utils.isNull(values)) {
|
||||
_i.target.values = values;
|
||||
}
|
||||
|
||||
if (options.binary !== undefined) {
|
||||
_i.target.binary = !!options.binary;
|
||||
}
|
||||
|
||||
if (options.rowMode !== undefined) {
|
||||
_i.target.rowMode = options.rowMode;
|
||||
}
|
||||
|
||||
if (errors.length) {
|
||||
return _i.currentError = new ParameterizedQueryError(errors[0], _i.target);
|
||||
}
|
||||
|
||||
_i.changed = false;
|
||||
|
||||
return _i.target;
|
||||
};
|
||||
|
||||
/**
|
||||
* @method ParameterizedQuery#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the object's current state.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
ParameterizedQuery.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap = npm.utils.messageGap(level + 1);
|
||||
const pq = this.parse();
|
||||
const lines = [
|
||||
`ParameterizedQuery {`
|
||||
];
|
||||
if (npm.utils.isText(pq.text)) {
|
||||
lines.push(gap + `text: "` + pq.text + `"`);
|
||||
}
|
||||
if (this.values !== undefined) {
|
||||
lines.push(gap + `values: ` + npm.utils.toJson(this.values));
|
||||
}
|
||||
if (this.binary !== undefined) {
|
||||
lines.push(gap + `binary: ` + npm.utils.toJson(this.binary));
|
||||
}
|
||||
if (this.rowMode !== undefined) {
|
||||
lines.push(gap + `rowMode: ` + npm.utils.toJson(this.rowMode));
|
||||
}
|
||||
if (this.error !== undefined) {
|
||||
lines.push(gap + `error: ` + this.error.toString(level + 1));
|
||||
}
|
||||
lines.push(npm.utils.messageGap(level) + `}`);
|
||||
return lines.join(npm.EOL);
|
||||
};
|
||||
|
||||
module.exports = {ParameterizedQuery};
|
||||
|
||||
/**
|
||||
* @name ParameterizedQuery#text
|
||||
* @type {string|QueryFile}
|
||||
* @description
|
||||
* A non-empty query string or a {@link QueryFile} object.
|
||||
*
|
||||
* Only the basic variables (`$1`, `$2`, etc) can be used in the query, because _Parameterized Queries_
|
||||
* are formatted on the server side.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @name ParameterizedQuery#values
|
||||
* @type {array}
|
||||
* @description
|
||||
* Query formatting parameters, depending on the type:
|
||||
*
|
||||
* - `null` / `undefined` means the query has no formatting parameters
|
||||
* - `Array` - it is an array of formatting parameters
|
||||
* - None of the above, means it is a single formatting value, which
|
||||
* is then automatically wrapped into an array
|
||||
*/
|
||||
|
||||
/**
|
||||
* @name ParameterizedQuery#binary
|
||||
* @type {boolean}
|
||||
* @default undefined
|
||||
* @description
|
||||
* Activates binary result mode. The default is the text mode.
|
||||
*
|
||||
* @see {@link http://www.postgresql.org/docs/devel/static/protocol-flow.html#PROTOCOL-FLOW-EXT-QUERY Extended Query}
|
||||
*/
|
||||
|
||||
/**
|
||||
* @name ParameterizedQuery#rowMode
|
||||
* @type {string}
|
||||
* @default undefined
|
||||
* @description
|
||||
* Changes the way data arrives to the client, with only one value supported by $[pg]:
|
||||
* - `array` will make all data rows arrive as arrays of values. By default, rows arrive as objects.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @name ParameterizedQuery#error
|
||||
* @type {errors.ParameterizedQueryError}
|
||||
* @default undefined
|
||||
* @readonly
|
||||
* @description
|
||||
* When in an error state, it is set to a {@link errors.ParameterizedQueryError ParameterizedQueryError} object. Otherwise, it is `undefined`.
|
||||
*
|
||||
* This property is primarily for internal use by the library.
|
||||
*/
|
||||
300
ProjectSourceCode/node_modules/pg-promise/lib/types/prepared-statement.js
generated
vendored
Normal file
300
ProjectSourceCode/node_modules/pg-promise/lib/types/prepared-statement.js
generated
vendored
Normal file
@@ -0,0 +1,300 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {ServerFormatting} = require(`./server-formatting`);
|
||||
const {PreparedStatementError} = require(`../errors`);
|
||||
const {QueryFile} = require(`../query-file`);
|
||||
const {assert} = require(`../assert`);
|
||||
|
||||
const npm = {
|
||||
EOL: require(`os`).EOL,
|
||||
utils: require(`../utils`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @class PreparedStatement
|
||||
* @description
|
||||
* Constructs a new $[Prepared Statement] object. All properties can also be set after the object's construction.
|
||||
*
|
||||
* This type extends the basic `{name, text, values}` object, i.e. when the basic object is used
|
||||
* with a query method, a new {@link PreparedStatement} object is created in its place.
|
||||
*
|
||||
* The type can be used in place of the `query` parameter, with any query method directly.
|
||||
*
|
||||
* The type is available from the library's root: `pgp.PreparedStatement`.
|
||||
*
|
||||
* @param {Object} [options]
|
||||
* Object configuration options / properties.
|
||||
*
|
||||
* @param {string} [options.name] - See property {@link PreparedStatement#name name}.
|
||||
* @param {string|QueryFile} [options.text] - See property {@link PreparedStatement#text text}.
|
||||
* @param {array} [options.values] - See property {@link PreparedStatement#values values}.
|
||||
* @param {boolean} [options.binary] - See property {@link PreparedStatement#binary binary}.
|
||||
* @param {string} [options.rowMode] - See property {@link PreparedStatement#rowMode rowMode}.
|
||||
* @param {number} [options.rows] - See property {@link PreparedStatement#rows rows}.
|
||||
*
|
||||
* @returns {PreparedStatement}
|
||||
*
|
||||
* @see
|
||||
* {@link errors.PreparedStatementError PreparedStatementError},
|
||||
* {@link http://www.postgresql.org/docs/9.6/static/sql-prepare.html PostgreSQL Prepared Statements}
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const {PreparedStatement: PS} = require('pg-promise');
|
||||
*
|
||||
* // Creating a complete Prepared Statement with parameters:
|
||||
* const findUser = new PS({name: 'find-user', text: 'SELECT * FROM Users WHERE id = $1', values: [123]});
|
||||
*
|
||||
* db.one(findUser)
|
||||
* .then(user => {
|
||||
* // user found;
|
||||
* })
|
||||
* .catch(error => {
|
||||
* // error;
|
||||
* });
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const {PreparedStatement: PS} = require('pg-promise');
|
||||
*
|
||||
* // Creating a reusable Prepared Statement without values:
|
||||
* const addUser = new PS({name: 'add-user', text: 'INSERT INTO Users(name, age) VALUES($1, $2)'});
|
||||
*
|
||||
* // setting values explicitly:
|
||||
* addUser.values = ['John', 30];
|
||||
*
|
||||
* db.none(addUser)
|
||||
* .then(() => {
|
||||
* // user added;
|
||||
* })
|
||||
* .catch(error => {
|
||||
* // error;
|
||||
* });
|
||||
*
|
||||
* // setting values implicitly, by passing them into the query method:
|
||||
* db.none(addUser, ['Mike', 25])
|
||||
* .then(() => {
|
||||
* // user added;
|
||||
* })
|
||||
* .catch(error => {
|
||||
* // error;
|
||||
* });
|
||||
*/
|
||||
class PreparedStatement extends ServerFormatting {
|
||||
constructor(options) {
|
||||
options = assert(options, [`name`, `text`, `values`, `binary`, `rowMode`, `rows`]);
|
||||
super(options);
|
||||
}
|
||||
|
||||
/**
|
||||
* @name PreparedStatement#name
|
||||
* @type {string}
|
||||
* @description
|
||||
* An arbitrary name given to this particular prepared statement. It must be unique within a single session and is
|
||||
* subsequently used to execute or deallocate a previously prepared statement.
|
||||
*/
|
||||
get name() {
|
||||
return this._inner.options.name;
|
||||
}
|
||||
|
||||
set name(value) {
|
||||
const _i = this._inner;
|
||||
if (value !== _i.options.name) {
|
||||
_i.options.name = value;
|
||||
_i.changed = true;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @name PreparedStatement#rows
|
||||
* @type {number}
|
||||
* @description
|
||||
* Number of rows to return at a time from a Prepared Statement's portal.
|
||||
* The default is 0, which means that all rows must be returned at once.
|
||||
*/
|
||||
get rows() {
|
||||
return this._inner.options.rows;
|
||||
}
|
||||
|
||||
set rows(value) {
|
||||
const _i = this._inner;
|
||||
if (value !== _i.options.rows) {
|
||||
_i.options.rows = value;
|
||||
_i.changed = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @method PreparedStatement#parse
|
||||
* @description
|
||||
* Parses the current object and returns a simple `{name, text, values}`, if successful,
|
||||
* or else it returns a {@link errors.PreparedStatementError PreparedStatementError} object.
|
||||
*
|
||||
* This method is primarily for internal use by the library.
|
||||
*
|
||||
* @returns {{name, text, values}|errors.PreparedStatementError}
|
||||
*/
|
||||
PreparedStatement.prototype.parse = function () {
|
||||
|
||||
const _i = this._inner, options = _i.options;
|
||||
|
||||
const qf = options.text instanceof QueryFile ? options.text : null;
|
||||
|
||||
if (!_i.changed && !qf) {
|
||||
return _i.target;
|
||||
}
|
||||
|
||||
const errors = [], values = _i.target.values;
|
||||
_i.target = {
|
||||
name: options.name,
|
||||
text: options.text
|
||||
};
|
||||
_i.changed = true;
|
||||
_i.currentError = undefined;
|
||||
|
||||
if (!npm.utils.isText(_i.target.name)) {
|
||||
errors.push(`Property 'name' must be a non-empty text string.`);
|
||||
}
|
||||
|
||||
if (qf) {
|
||||
qf.prepare();
|
||||
if (qf.error) {
|
||||
errors.push(qf.error);
|
||||
} else {
|
||||
_i.target.text = qf[QueryFile.$query];
|
||||
}
|
||||
}
|
||||
if (!npm.utils.isText(_i.target.text)) {
|
||||
errors.push(`Property 'text' must be a non-empty text string.`);
|
||||
}
|
||||
|
||||
if (!npm.utils.isNull(values)) {
|
||||
_i.target.values = values;
|
||||
}
|
||||
|
||||
if (options.binary !== undefined) {
|
||||
_i.target.binary = !!options.binary;
|
||||
}
|
||||
|
||||
if (options.rowMode !== undefined) {
|
||||
_i.target.rowMode = options.rowMode;
|
||||
}
|
||||
|
||||
if (options.rows !== undefined) {
|
||||
_i.target.rows = options.rows;
|
||||
}
|
||||
|
||||
if (errors.length) {
|
||||
return _i.currentError = new PreparedStatementError(errors[0], _i.target);
|
||||
}
|
||||
|
||||
_i.changed = false;
|
||||
|
||||
return _i.target;
|
||||
};
|
||||
|
||||
/**
|
||||
* @method PreparedStatement#toString
|
||||
* @description
|
||||
* Creates a well-formatted multi-line string that represents the object's current state.
|
||||
*
|
||||
* It is called automatically when writing the object into the console.
|
||||
*
|
||||
* @param {number} [level=0]
|
||||
* Nested output level, to provide visual offset.
|
||||
*
|
||||
* @returns {string}
|
||||
*/
|
||||
PreparedStatement.prototype.toString = function (level) {
|
||||
level = level > 0 ? parseInt(level) : 0;
|
||||
const gap = npm.utils.messageGap(level + 1);
|
||||
const ps = this.parse();
|
||||
const lines = [
|
||||
`PreparedStatement {`,
|
||||
gap + `name: ` + npm.utils.toJson(this.name)
|
||||
];
|
||||
if (npm.utils.isText(ps.text)) {
|
||||
lines.push(gap + `text: "` + ps.text + `"`);
|
||||
}
|
||||
if (this.values !== undefined) {
|
||||
lines.push(gap + `values: ` + npm.utils.toJson(this.values));
|
||||
}
|
||||
if (this.binary !== undefined) {
|
||||
lines.push(gap + `binary: ` + npm.utils.toJson(this.binary));
|
||||
}
|
||||
if (this.rowMode !== undefined) {
|
||||
lines.push(gap + `rowMode: ` + npm.utils.toJson(this.rowMode));
|
||||
}
|
||||
if (this.rows !== undefined) {
|
||||
lines.push(gap + `rows: ` + npm.utils.toJson(this.rows));
|
||||
}
|
||||
if (this.error) {
|
||||
lines.push(gap + `error: ` + this.error.toString(level + 1));
|
||||
}
|
||||
lines.push(npm.utils.messageGap(level) + `}`);
|
||||
return lines.join(npm.EOL);
|
||||
};
|
||||
|
||||
module.exports = {PreparedStatement};
|
||||
|
||||
/**
|
||||
* @name PreparedStatement#text
|
||||
* @type {string|QueryFile}
|
||||
* @description
|
||||
* A non-empty query string or a {@link QueryFile} object.
|
||||
*
|
||||
* Only the basic variables (`$1`, `$2`, etc) can be used in the query, because $[Prepared Statements]
|
||||
* are formatted on the server side.
|
||||
*
|
||||
* Changing this property for the same {@link PreparedStatement#name name} will have no effect, because queries
|
||||
* for Prepared Statements are cached by the server, with {@link PreparedStatement#name name} being the cache key.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @name PreparedStatement#values
|
||||
* @type {array}
|
||||
* @description
|
||||
* Query formatting parameters, depending on the type:
|
||||
*
|
||||
* - `null` / `undefined` means the query has no formatting parameters
|
||||
* - `Array` - it is an array of formatting parameters
|
||||
* - None of the above, means it is a single formatting value, which
|
||||
* is then automatically wrapped into an array
|
||||
*/
|
||||
|
||||
/**
|
||||
* @name PreparedStatement#binary
|
||||
* @type {boolean}
|
||||
* @default undefined
|
||||
* @description
|
||||
* Activates binary result mode. The default is the text mode.
|
||||
*
|
||||
* @see {@link http://www.postgresql.org/docs/devel/static/protocol-flow.html#PROTOCOL-FLOW-EXT-QUERY Extended Query}
|
||||
*/
|
||||
|
||||
/**
|
||||
* @name PreparedStatement#rowMode
|
||||
* @type {string}
|
||||
* @default undefined
|
||||
* @description
|
||||
* Changes the way data arrives to the client, with only one value supported by $[pg]:
|
||||
* - `array` will make all data rows arrive as arrays of values. By default, rows arrive as objects.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @name PreparedStatement#error
|
||||
* @type {errors.PreparedStatementError}
|
||||
* @default undefined
|
||||
* @description
|
||||
* When in an error state, it is set to a {@link errors.PreparedStatementError PreparedStatementError} object. Otherwise, it is `undefined`.
|
||||
*
|
||||
* This property is primarily for internal use by the library.
|
||||
*/
|
||||
97
ProjectSourceCode/node_modules/pg-promise/lib/types/server-formatting.js
generated
vendored
Normal file
97
ProjectSourceCode/node_modules/pg-promise/lib/types/server-formatting.js
generated
vendored
Normal file
@@ -0,0 +1,97 @@
|
||||
const {InnerState} = require(`../inner-state`);
|
||||
const {addInspection} = require(`../utils`);
|
||||
const utils = require(`../utils`);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @class ServerFormatting
|
||||
*/
|
||||
class ServerFormatting extends InnerState {
|
||||
|
||||
constructor(options) {
|
||||
const _inner = {
|
||||
options,
|
||||
changed: true,
|
||||
currentError: undefined,
|
||||
target: {}
|
||||
};
|
||||
super(_inner);
|
||||
setValues.call(this, options.values);
|
||||
}
|
||||
|
||||
get error() {
|
||||
return this._inner.currentError;
|
||||
}
|
||||
|
||||
get text() {
|
||||
return this._inner.options.text;
|
||||
}
|
||||
|
||||
set text(value) {
|
||||
const _i = this._inner;
|
||||
if (value !== _i.options.text) {
|
||||
_i.options.text = value;
|
||||
_i.changed = true;
|
||||
}
|
||||
}
|
||||
|
||||
get binary() {
|
||||
return this._inner.options.binary;
|
||||
}
|
||||
|
||||
set binary(value) {
|
||||
const _i = this._inner;
|
||||
if (value !== _i.options.binary) {
|
||||
_i.options.binary = value;
|
||||
_i.changed = true;
|
||||
}
|
||||
}
|
||||
|
||||
get rowMode() {
|
||||
return this._inner.options.rowMode;
|
||||
}
|
||||
|
||||
set rowMode(value) {
|
||||
const _i = this._inner;
|
||||
if (value !== _i.options.rowMode) {
|
||||
_i.options.rowMode = value;
|
||||
_i.changed = true;
|
||||
}
|
||||
}
|
||||
|
||||
get values() {
|
||||
return this._inner.target.values;
|
||||
}
|
||||
|
||||
set values(values) {
|
||||
setValues.call(this, values);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @member ServerFormatting#parse
|
||||
*/
|
||||
|
||||
function setValues(v) {
|
||||
const target = this._inner.target;
|
||||
if (Array.isArray(v)) {
|
||||
if (v.length) {
|
||||
target.values = v;
|
||||
} else {
|
||||
delete target.values;
|
||||
}
|
||||
} else {
|
||||
if (utils.isNull(v)) {
|
||||
delete target.values;
|
||||
} else {
|
||||
target.values = [v];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
addInspection(ServerFormatting, function () {
|
||||
return this.toString();
|
||||
});
|
||||
|
||||
module.exports = {ServerFormatting};
|
||||
13
ProjectSourceCode/node_modules/pg-promise/lib/utils/README.md
generated
vendored
Normal file
13
ProjectSourceCode/node_modules/pg-promise/lib/utils/README.md
generated
vendored
Normal file
@@ -0,0 +1,13 @@
|
||||
### `utils` namespace
|
||||
|
||||
This folder contains everything that's available via the [utils] namespace, before and after initialization:
|
||||
|
||||
```js
|
||||
const pgpLib = require('pg-promise');
|
||||
const pgp = pgpLib(/*initialization options*/);
|
||||
|
||||
pgpLib.utils; // `utils` namespace
|
||||
pgp.utils; // `utils` namespace
|
||||
```
|
||||
|
||||
[utils]:http://vitaly-t.github.io/pg-promise/utils.html
|
||||
68
ProjectSourceCode/node_modules/pg-promise/lib/utils/color.js
generated
vendored
Normal file
68
ProjectSourceCode/node_modules/pg-promise/lib/utils/color.js
generated
vendored
Normal file
@@ -0,0 +1,68 @@
|
||||
const util = require(`util`);
|
||||
|
||||
class ColorConsole {
|
||||
|
||||
static log() {
|
||||
ColorConsole.writeNormal([...arguments], 39); // white
|
||||
}
|
||||
|
||||
static info() {
|
||||
ColorConsole.writeNormal([...arguments], 36); // cyan
|
||||
}
|
||||
|
||||
static success() {
|
||||
ColorConsole.writeNormal([...arguments], 32); // green
|
||||
}
|
||||
|
||||
static warn() {
|
||||
ColorConsole.writeNormal([...arguments], 33); // yellow
|
||||
}
|
||||
|
||||
static error() {
|
||||
ColorConsole.writeError([...arguments], 31); // red
|
||||
}
|
||||
|
||||
static writeNormal(params, color) {
|
||||
// istanbul ignore else
|
||||
if (process.stdout.isTTY) {
|
||||
console.log.apply(null, ColorConsole.formatColor(params, color)); // eslint-disable-line no-console
|
||||
} else {
|
||||
console.log.apply(null, params); // eslint-disable-line no-console
|
||||
}
|
||||
}
|
||||
|
||||
static writeError(params, color) {
|
||||
// istanbul ignore else
|
||||
if (process.stderr.isTTY) {
|
||||
console.error.apply(null, ColorConsole.formatColor(params, color)); // eslint-disable-line no-console
|
||||
} else {
|
||||
console.error.apply(null, params); // eslint-disable-line no-console
|
||||
}
|
||||
}
|
||||
|
||||
static formatColor(args, color) {
|
||||
return args.map(a => `\x1b[${color}m${util.format(a)}\x1b[0m`);
|
||||
}
|
||||
}
|
||||
|
||||
ColorConsole.log.bright = function () {
|
||||
ColorConsole.writeNormal([...arguments], 97); // light white
|
||||
};
|
||||
|
||||
ColorConsole.info.bright = function () {
|
||||
ColorConsole.writeNormal([...arguments], 93); // light cyan
|
||||
};
|
||||
|
||||
ColorConsole.success.bright = function () {
|
||||
ColorConsole.writeNormal([...arguments], 92); // light green
|
||||
};
|
||||
|
||||
ColorConsole.warn.bright = function () {
|
||||
ColorConsole.writeNormal([...arguments], 93); // light yellow
|
||||
};
|
||||
|
||||
ColorConsole.error.bright = function () {
|
||||
ColorConsole.writeError([...arguments], 91); // light red
|
||||
};
|
||||
|
||||
module.exports = {ColorConsole};
|
||||
235
ProjectSourceCode/node_modules/pg-promise/lib/utils/index.js
generated
vendored
Normal file
235
ProjectSourceCode/node_modules/pg-promise/lib/utils/index.js
generated
vendored
Normal file
@@ -0,0 +1,235 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const npm = {
|
||||
path: require(`path`),
|
||||
util: require(`util`),
|
||||
patterns: require(`../patterns`),
|
||||
os: require(`os`)
|
||||
};
|
||||
|
||||
////////////////////////////////////////////
|
||||
// Simpler check for null/undefined;
|
||||
function isNull(value) {
|
||||
return value === null || value === undefined;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////
|
||||
// Verifies parameter for being a non-empty text string;
|
||||
function isText(txt) {
|
||||
return txt && typeof txt === `string` && /\S/.test(txt);
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////
|
||||
// Approximates the environment as being for development.
|
||||
//
|
||||
// Proper configuration is having NODE_ENV = 'development', but this
|
||||
// method only checks for 'dev' being present, and regardless of the case.
|
||||
function isDev() {
|
||||
const env = global.process.env.NODE_ENV || ``;
|
||||
return env.toLowerCase().indexOf(`dev`) !== -1;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////
|
||||
// Locks all properties in an object to read-only,
|
||||
// or freezes the entire object for any changes.
|
||||
function lock(obj, freeze, options) {
|
||||
if (options && options.noLocking) {
|
||||
return;
|
||||
}
|
||||
if (freeze) {
|
||||
Object.freeze(obj); // freeze the entire object, permanently;
|
||||
} else {
|
||||
const desc = {
|
||||
writable: false,
|
||||
configurable: false,
|
||||
enumerable: true
|
||||
};
|
||||
for (const p in obj) {
|
||||
Object.defineProperty(obj, p, desc);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////
|
||||
// Adds properties from source to the target,
|
||||
// making them read-only and enumerable.
|
||||
function addReadProperties(target, source) {
|
||||
for (const p in source) {
|
||||
addReadProp(target, p, source[p]);
|
||||
}
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////
|
||||
// Adds a read-only, non-deletable enumerable property.
|
||||
function addReadProp(obj, name, value, hidden) {
|
||||
Object.defineProperty(obj, name, {
|
||||
value,
|
||||
configurable: false,
|
||||
enumerable: !hidden,
|
||||
writable: false
|
||||
});
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////
|
||||
// Converts a connection string or object into its safe copy:
|
||||
// if password is present, it is masked with symbol '#'.
|
||||
function getSafeConnection(cn) {
|
||||
const maskPassword = cs => cs.replace(/:(?![/])([^@]+)/, (_, m) => `:` + new Array(m.length + 1).join(`#`));
|
||||
if (typeof cn === `object`) {
|
||||
const copy = Object.assign({}, cn);
|
||||
if (typeof copy.password === `string`) {
|
||||
copy.password = copy.password.replace(/./g, `#`);
|
||||
}
|
||||
if (typeof copy.connectionString === `string`) {
|
||||
copy.connectionString = maskPassword(copy.connectionString);
|
||||
}
|
||||
return copy;
|
||||
}
|
||||
return maskPassword(cn);
|
||||
}
|
||||
|
||||
///////////////////////////////////////////
|
||||
// Returns a space gap for console output;
|
||||
function messageGap(level) {
|
||||
return ` `.repeat(level * 4);
|
||||
}
|
||||
|
||||
/////////////////////////////////////////
|
||||
// Provides platform-neutral inheritance;
|
||||
function inherits(child, parent) {
|
||||
child.prototype.__proto__ = parent.prototype;
|
||||
}
|
||||
|
||||
// istanbul ignore next
|
||||
function getLocalStack(startIdx, maxLines) {
|
||||
// from the call stack, we take up to maximum lines,
|
||||
// starting with specified line index:
|
||||
startIdx = startIdx || 0;
|
||||
const endIdx = maxLines > 0 ? startIdx + maxLines : undefined;
|
||||
return new Error().stack
|
||||
.split(`\n`)
|
||||
.filter(line => line.match(/\(.+\)/))
|
||||
.slice(startIdx, endIdx)
|
||||
.join(`\n`);
|
||||
}
|
||||
|
||||
//////////////////////////////
|
||||
// Internal error container;
|
||||
function InternalError(error) {
|
||||
this.error = error;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////
|
||||
// Parses a property name, and gets its name from the object,
|
||||
// if the property exists. Returns object {valid, has, target, value}:
|
||||
// - valid - true/false, whether the syntax is valid
|
||||
// - has - a flag that property exists; set when 'valid' = true
|
||||
// - target - the target object that contains the property; set when 'has' = true
|
||||
// - value - the value; set when 'has' = true
|
||||
function getIfHas(obj, prop) {
|
||||
const result = {valid: true};
|
||||
if (prop.indexOf(`.`) === -1) {
|
||||
result.has = prop in obj;
|
||||
result.target = obj;
|
||||
if (result.has) {
|
||||
result.value = obj[prop];
|
||||
}
|
||||
} else {
|
||||
const names = prop.split(`.`);
|
||||
let missing, target;
|
||||
for (let i = 0; i < names.length; i++) {
|
||||
const n = names[i];
|
||||
if (!n) {
|
||||
result.valid = false;
|
||||
return result;
|
||||
}
|
||||
if (!missing && hasProperty(obj, n)) {
|
||||
target = obj;
|
||||
obj = obj[n];
|
||||
} else {
|
||||
missing = true;
|
||||
}
|
||||
}
|
||||
result.has = !missing;
|
||||
if (result.has) {
|
||||
result.target = target;
|
||||
result.value = obj;
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// Checks if the property exists in the object or value or its prototype;
|
||||
function hasProperty(value, prop) {
|
||||
return (value && typeof value === `object` && prop in value) ||
|
||||
value !== null && value !== undefined && value[prop] !== undefined;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////
|
||||
// Adds prototype inspection
|
||||
function addInspection(type, cb) {
|
||||
type.prototype[npm.util.inspect.custom] = cb;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Identifies a general connectivity error, after which no more queries can be executed.
|
||||
// This is for detecting when to skip executing ROLLBACK for a failed transaction.
|
||||
function isConnectivityError(err) {
|
||||
const code = err && typeof err.code === `string` && err.code;
|
||||
const cls = code && code.substr(0, 2); // Error Class
|
||||
// istanbul ignore next (we cannot test-cover all error cases):
|
||||
return code === `ECONNRESET` || (cls === `08` && code !== `08P01`) || (cls === `57` && code !== `57014`);
|
||||
// Code 'ECONNRESET' - Connectivity issue handled by the driver.
|
||||
// Class 08 - Connection Exception (except for 08P01, for protocol violation).
|
||||
// Class 57 - Operator Intervention (except for 57014, for cancelled queries).
|
||||
//
|
||||
// ERROR CODES: https://www.postgresql.org/docs/9.6/static/errcodes-appendix.html
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////
|
||||
// Does JSON.stringify, with support for BigInt (irreversible)
|
||||
function toJson(data) {
|
||||
if (data !== undefined) {
|
||||
return JSON.stringify(data, (_, v) => typeof v === `bigint` ? `${v}#bigint` : v)
|
||||
.replace(/"(-?\d+)#bigint"/g, (_, a) => a);
|
||||
}
|
||||
}
|
||||
|
||||
const platform = npm.os.platform();
|
||||
|
||||
const exp = {
|
||||
toJson,
|
||||
getIfHas,
|
||||
addInspection,
|
||||
InternalError,
|
||||
getLocalStack,
|
||||
lock,
|
||||
isText,
|
||||
isNull,
|
||||
isDev,
|
||||
platform: {
|
||||
isWindows: platform === `win32`,
|
||||
isMac: platform === `darwin`
|
||||
},
|
||||
addReadProp,
|
||||
addReadProperties,
|
||||
getSafeConnection,
|
||||
messageGap,
|
||||
inherits,
|
||||
isConnectivityError
|
||||
};
|
||||
|
||||
const mainFile = process.argv[1];
|
||||
|
||||
// istanbul ignore next
|
||||
exp.startDir = mainFile ? npm.path.dirname(mainFile) : process.cwd();
|
||||
|
||||
module.exports = exp;
|
||||
312
ProjectSourceCode/node_modules/pg-promise/lib/utils/public.js
generated
vendored
Normal file
312
ProjectSourceCode/node_modules/pg-promise/lib/utils/public.js
generated
vendored
Normal file
@@ -0,0 +1,312 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
const {assert} = require(`../assert`);
|
||||
|
||||
const npm = {
|
||||
fs: require(`fs`),
|
||||
path: require(`path`),
|
||||
utils: require(`./`),
|
||||
package: require(`../../package.json`)
|
||||
};
|
||||
|
||||
/**
|
||||
* @method utils.camelize
|
||||
* @description
|
||||
* Camelizes a text string.
|
||||
*
|
||||
* Case-changing characters include:
|
||||
* - _hyphen_
|
||||
* - _underscore_
|
||||
* - _period_
|
||||
* - _space_
|
||||
*
|
||||
* @param {string} text
|
||||
* Input text string.
|
||||
*
|
||||
* @returns {string}
|
||||
* Camelized text string.
|
||||
*
|
||||
* @see
|
||||
* {@link utils.camelizeVar camelizeVar}
|
||||
*
|
||||
*/
|
||||
function camelize(text) {
|
||||
text = text.replace(/[-_\s.]+(.)?/g, (_, c) => c ? c.toUpperCase() : ``);
|
||||
return text.substr(0, 1).toLowerCase() + text.substr(1);
|
||||
}
|
||||
|
||||
/**
|
||||
* @method utils.camelizeVar
|
||||
* @description
|
||||
* Camelizes a text string, while making it compliant with JavaScript variable names:
|
||||
* - contains symbols `a-z`, `A-Z`, `0-9`, `_` and `$`
|
||||
* - cannot have leading digits
|
||||
*
|
||||
* First, it removes all symbols that do not meet the above criteria, except for _hyphen_, _period_ and _space_,
|
||||
* and then it forwards into {@link utils.camelize camelize}.
|
||||
*
|
||||
* @param {string} text
|
||||
* Input text string.
|
||||
*
|
||||
* If it doesn't contain any symbols to make up a valid variable name, the result will be an empty string.
|
||||
*
|
||||
* @returns {string}
|
||||
* Camelized text string that can be used as an open property name.
|
||||
*
|
||||
* @see
|
||||
* {@link utils.camelize camelize}
|
||||
*
|
||||
*/
|
||||
function camelizeVar(text) {
|
||||
text = text.replace(/[^a-zA-Z0-9$_\-\s.]/g, ``).replace(/^[0-9_\-\s.]+/, ``);
|
||||
return camelize(text);
|
||||
}
|
||||
|
||||
function _enumSql(dir, options, cb, namePath) {
|
||||
const tree = {};
|
||||
npm.fs.readdirSync(dir).forEach(file => {
|
||||
let stat;
|
||||
const fullPath = npm.path.join(dir, file);
|
||||
try {
|
||||
stat = npm.fs.statSync(fullPath);
|
||||
} catch (e) {
|
||||
// while it is very easy to test manually, it is very difficult to test for
|
||||
// access-denied errors automatically; therefore excluding from the coverage:
|
||||
// istanbul ignore next
|
||||
if (options.ignoreErrors) {
|
||||
return; // on to the next file/folder;
|
||||
}
|
||||
// istanbul ignore next
|
||||
throw e;
|
||||
}
|
||||
if (stat.isDirectory()) {
|
||||
if (options.recursive) {
|
||||
const dirName = camelizeVar(file);
|
||||
const np = namePath ? (namePath + `.` + dirName) : dirName;
|
||||
const t = _enumSql(fullPath, options, cb, np);
|
||||
if (Object.keys(t).length) {
|
||||
if (!dirName.length || dirName in tree) {
|
||||
if (!options.ignoreErrors) {
|
||||
throw new Error(`Empty or duplicate camelized folder name: ` + fullPath);
|
||||
}
|
||||
}
|
||||
tree[dirName] = t;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (npm.path.extname(file).toLowerCase() === `.sql`) {
|
||||
const name = camelizeVar(file.replace(/\.[^/.]+$/, ``));
|
||||
if (!name.length || name in tree) {
|
||||
if (!options.ignoreErrors) {
|
||||
throw new Error(`Empty or duplicate camelized file name: ` + fullPath);
|
||||
}
|
||||
}
|
||||
tree[name] = fullPath;
|
||||
if (cb) {
|
||||
const result = cb(fullPath, name, namePath ? (namePath + `.` + name) : name);
|
||||
if (result !== undefined) {
|
||||
tree[name] = result;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
return tree;
|
||||
}
|
||||
|
||||
/**
|
||||
* @method utils.enumSql
|
||||
* @description
|
||||
* Synchronously enumerates all SQL files (within a given directory) into a camelized SQL tree.
|
||||
*
|
||||
* All property names within the tree are camelized via {@link utils.camelizeVar camelizeVar},
|
||||
* so they can be used in the code directly, as open property names.
|
||||
*
|
||||
* @param {string} dir
|
||||
* Directory path where SQL files are located, either absolute or relative to the current directory.
|
||||
*
|
||||
* SQL files are identified by using `.sql` extension (case-insensitive).
|
||||
*
|
||||
* @param {{}} [options]
|
||||
* Search options.
|
||||
*
|
||||
* @param {boolean} [options.recursive=false]
|
||||
* Include sub-directories into the search.
|
||||
*
|
||||
* Sub-directories without SQL files will be skipped from the result.
|
||||
*
|
||||
* @param {boolean} [options.ignoreErrors=false]
|
||||
* Ignore the following types of errors:
|
||||
* - access errors, when there is no read access to a file or folder
|
||||
* - empty or duplicate camelized property names
|
||||
*
|
||||
* This flag does not affect errors related to invalid input parameters, or if you pass in a
|
||||
* non-existing directory.
|
||||
*
|
||||
* @param {function} [cb]
|
||||
* A callback function that takes three arguments:
|
||||
* - `file` - SQL file path, relative or absolute, according to how you specified the search directory
|
||||
* - `name` - name of the property that represents the SQL file
|
||||
* - `path` - property resolution path (full property name)
|
||||
*
|
||||
* If the function returns anything other than `undefined`, it overrides the corresponding property value in the tree.
|
||||
*
|
||||
* @returns {object}
|
||||
* Camelized SQL tree object, with each value being an SQL file path (unless changed via the callback).
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // simple SQL tree generation for further processing:
|
||||
* const tree = pgp.utils.enumSql('../sql', {recursive: true});
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // generating an SQL tree for dynamic use of names:
|
||||
* const sql = pgp.utils.enumSql(__dirname, {recursive: true}, file => {
|
||||
* return new pgp.QueryFile(file, {minify: true});
|
||||
* });
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* const {join: joinPath} = require('path');
|
||||
*
|
||||
* // replacing each relative path in the tree with a full one:
|
||||
* const tree = pgp.utils.enumSql('../sql', {recursive: true}, file => {
|
||||
* return joinPath(__dirname, file);
|
||||
* });
|
||||
*
|
||||
*/
|
||||
function enumSql(dir, options, cb) {
|
||||
if (!npm.utils.isText(dir)) {
|
||||
throw new TypeError(`Parameter 'dir' must be a non-empty text string.`);
|
||||
}
|
||||
options = assert(options, [`recursive`, `ignoreErrors`]);
|
||||
cb = (typeof cb === `function`) ? cb : null;
|
||||
return _enumSql(dir, options, cb, ``);
|
||||
}
|
||||
|
||||
/**
|
||||
* @method utils.taskArgs
|
||||
* @description
|
||||
* Normalizes/prepares arguments for tasks and transactions.
|
||||
*
|
||||
* Its main purpose is to simplify adding custom methods {@link Database#task task}, {@link Database#taskIf taskIf},
|
||||
* {@link Database#tx tx} and {@link Database#txIf txIf} within event {@link event:extend extend}, as the those methods use fairly
|
||||
* complex logic for parsing inputs.
|
||||
*
|
||||
* @param args {Object}
|
||||
* Array-like object of `arguments` that was passed into the method. It is expected that the `arguments`
|
||||
* are always made of two parameters - `(options, cb)`, same as all the default task/transaction methods.
|
||||
*
|
||||
* And if your custom method needs additional parameters, they should be passed in as extra properties within `options`.
|
||||
*
|
||||
* @returns {Array}
|
||||
* Array of arguments that can be passed into a task or transaction.
|
||||
*
|
||||
* It is extended with properties `options` and `cb` to access the corresponding array elements `[0]` and `[1]` by name.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* // Registering a custom transaction method that assigns a default Transaction Mode:
|
||||
*
|
||||
* const initOptions = {
|
||||
* extend: obj => {
|
||||
* obj.myTx = function(options, cb) {
|
||||
* const args = pgp.utils.taskArgs(arguments); // prepare arguments
|
||||
*
|
||||
* if (!('mode' in args.options)) {
|
||||
* // if no 'mode' was specified, set default for transaction mode:
|
||||
* args.options.mode = myTxModeObject; // of type pgp.txMode.TransactionMode
|
||||
* }
|
||||
*
|
||||
* return obj.tx.apply(this, args);
|
||||
* // or explicitly, if needed:
|
||||
* // return obj.tx.call(this, args.options, args.cb);
|
||||
* }
|
||||
* }
|
||||
* };
|
||||
*
|
||||
*/
|
||||
function taskArgs(args) {
|
||||
|
||||
if (!args || typeof args.length !== `number`) {
|
||||
throw new TypeError(`Parameter 'args' must be an array-like object of arguments.`);
|
||||
}
|
||||
|
||||
let options = args[0], cb;
|
||||
if (typeof options === `function`) {
|
||||
cb = options;
|
||||
options = {};
|
||||
if (cb.name) {
|
||||
options.tag = cb.name;
|
||||
}
|
||||
} else {
|
||||
if (typeof args[1] === `function`) {
|
||||
cb = args[1];
|
||||
}
|
||||
if (typeof options === `string` || typeof options === `number`) {
|
||||
options = {tag: options};
|
||||
} else {
|
||||
options = (typeof options === `object` && options) || {};
|
||||
if (!(`tag` in options) && cb && cb.name) {
|
||||
options.tag = cb.name;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const res = [options, cb];
|
||||
|
||||
Object.defineProperty(res, `options`, {
|
||||
get: function () {
|
||||
return this[0];
|
||||
},
|
||||
set: function (newValue) {
|
||||
this[0] = newValue;
|
||||
},
|
||||
enumerable: true
|
||||
});
|
||||
|
||||
Object.defineProperty(res, `cb`, {
|
||||
get: function () {
|
||||
return this[1];
|
||||
},
|
||||
set: function (newValue) {
|
||||
this[1] = newValue;
|
||||
},
|
||||
enumerable: true
|
||||
});
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* @namespace utils
|
||||
*
|
||||
* @description
|
||||
* Namespace for general-purpose static functions, available as `pgp.utils`, before and after initializing the library.
|
||||
*
|
||||
* @property {function} camelize
|
||||
* {@link utils.camelize camelize} - camelizes a text string
|
||||
*
|
||||
* @property {function} camelizeVar
|
||||
* {@link utils.camelizeVar camelizeVar} - camelizes a text string as a variable
|
||||
*
|
||||
* @property {function} enumSql
|
||||
* {@link utils.enumSql enumSql} - enumerates SQL files in a directory
|
||||
*
|
||||
* @property {function} taskArgs
|
||||
* {@link utils.taskArgs taskArgs} - prepares arguments for tasks and transactions
|
||||
*/
|
||||
module.exports = {
|
||||
camelize,
|
||||
camelizeVar,
|
||||
enumSql,
|
||||
taskArgs
|
||||
};
|
||||
62
ProjectSourceCode/node_modules/pg-promise/package.json
generated
vendored
Normal file
62
ProjectSourceCode/node_modules/pg-promise/package.json
generated
vendored
Normal file
@@ -0,0 +1,62 @@
|
||||
{
|
||||
"name": "pg-promise",
|
||||
"version": "10.15.4",
|
||||
"description": "PostgreSQL interface for Node.js",
|
||||
"main": "lib/index.js",
|
||||
"typings": "typescript/pg-promise.d.ts",
|
||||
"scripts": {
|
||||
"spelling": "cspell --config=.cspell.json \"**/*.{md,ts,js}\" --no-progress",
|
||||
"coverage": "istanbul cover ./node_modules/jasmine-node/bin/jasmine-node test",
|
||||
"doc": "jsdoc -c ./jsdoc/jsdoc.js ./jsdoc/README.md -t ./jsdoc/templates/custom",
|
||||
"lint": "eslint ./lib ./test/*.js ./test/db --fix",
|
||||
"test": "jasmine-node --captureExceptions test",
|
||||
"test:native": "jasmine-node test --config PG_NATIVE true",
|
||||
"tslint": "tslint ./typescript/*.ts"
|
||||
},
|
||||
"files": [
|
||||
"lib",
|
||||
"typescript"
|
||||
],
|
||||
"homepage": "https://github.com/vitaly-t/pg-promise",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/vitaly-t/pg-promise.git"
|
||||
},
|
||||
"bugs": {
|
||||
"url": "https://github.com/vitaly-t/pg-promise/issues",
|
||||
"email": "vitaly.tomilov@gmail.com"
|
||||
},
|
||||
"keywords": [
|
||||
"pg",
|
||||
"promise",
|
||||
"postgres"
|
||||
],
|
||||
"author": {
|
||||
"name": "Vitaly Tomilov",
|
||||
"email": "vitaly.tomilov@gmail.com"
|
||||
},
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=12.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"assert-options": "0.8.0",
|
||||
"pg": "8.8.0",
|
||||
"pg-minify": "1.6.2",
|
||||
"spex": "3.2.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/node": "18.11.9",
|
||||
"bluebird": "3.7.2",
|
||||
"coveralls": "3.1.1",
|
||||
"cspell": "6.15.0",
|
||||
"eslint": "8.28.0",
|
||||
"istanbul": "0.4.5",
|
||||
"jasmine-node": "3.0.0",
|
||||
"jsdoc": "3.6.11",
|
||||
"JSONStream": "1.3.5",
|
||||
"pg-query-stream": "4.2.4",
|
||||
"tslint": "6.1.3",
|
||||
"typescript": "4.9.3"
|
||||
}
|
||||
}
|
||||
63
ProjectSourceCode/node_modules/pg-promise/typescript/README.md
generated
vendored
Normal file
63
ProjectSourceCode/node_modules/pg-promise/typescript/README.md
generated
vendored
Normal file
@@ -0,0 +1,63 @@
|
||||
## TypeScript for pg-promise
|
||||
|
||||
Complete TypeScript declarations for [pg-promise].
|
||||
|
||||
### Inclusion
|
||||
|
||||
Typescript should be able to pick up the definitions without any manual configuration.
|
||||
|
||||
### Simple Usage
|
||||
|
||||
```ts
|
||||
import pgPromise from 'pg-promise';
|
||||
|
||||
const pgp = pgPromise({/* Initialization Options */});
|
||||
|
||||
const db = pgp('postgres://username:password@host:port/database');
|
||||
|
||||
const {value} = await db.one('SELECT 123 as value');
|
||||
```
|
||||
|
||||
#### With Extensions
|
||||
|
||||
The library supports dynamic protocol extensions, via event [extend], which requires
|
||||
explicit extension interface to be declared and parameterized, as shown below.
|
||||
|
||||
```ts
|
||||
import * as pgPromise from 'pg-promise';
|
||||
|
||||
// your protocol extensions:
|
||||
interface IExtensions {
|
||||
findUser(userId: number): Promise<any>;
|
||||
}
|
||||
|
||||
// pg-promise initialization options:
|
||||
const options: pgPromise.IInitOptions<IExtensions> = {
|
||||
extend(obj) {
|
||||
obj.findUser = userId => {
|
||||
return obj.one('SELECT * FROM Users WHERE id = $1', [userId]);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// initializing the library:
|
||||
const pgp = pgPromise(options);
|
||||
|
||||
// database object:
|
||||
const db = pgp('postgres://username:password@host:port/database');
|
||||
|
||||
// protocol is extended on each level:
|
||||
const user = await db.findUser(123);
|
||||
|
||||
// ...including inside tasks and transactions:
|
||||
await db.task(async t => {
|
||||
const user = await t.findUser(123);
|
||||
// ...etc
|
||||
});
|
||||
```
|
||||
|
||||
For a comprehensive example, check out [pg-promise-demo].
|
||||
|
||||
[pg-promise-demo]:https://github.com/vitaly-t/pg-promise-demo
|
||||
[extend]:http://vitaly-t.github.io/pg-promise/global.html#event:extend
|
||||
[pg-promise]:https://github.com/vitaly-t/pg-promise
|
||||
699
ProjectSourceCode/node_modules/pg-promise/typescript/pg-promise.d.ts
generated
vendored
Normal file
699
ProjectSourceCode/node_modules/pg-promise/typescript/pg-promise.d.ts
generated
vendored
Normal file
@@ -0,0 +1,699 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
/////////////////////////////////////////
|
||||
// Requires pg-promise v10.14.0 or later.
|
||||
/////////////////////////////////////////
|
||||
|
||||
// We use ES6 as static promise here, because generic promises are still not supported.
|
||||
// Follow the links below:
|
||||
// http://stackoverflow.com/questions/36593087/using-a-custom-promise-as-a-generic-type
|
||||
// https://github.com/Microsoft/TypeScript/issues/1213
|
||||
type XPromise<T> = Promise<T>;
|
||||
|
||||
import * as pg from './pg-subset';
|
||||
import * as pgMinify from 'pg-minify';
|
||||
import * as spexLib from 'spex';
|
||||
|
||||
// internal namespace for "txMode" property:
|
||||
declare namespace _txMode {
|
||||
// Transaction Isolation Level;
|
||||
// API: http://vitaly-t.github.io/pg-promise/txMode.html#.isolationLevel
|
||||
enum isolationLevel {
|
||||
none = 0,
|
||||
serializable = 1,
|
||||
repeatableRead = 2,
|
||||
readCommitted = 3
|
||||
}
|
||||
|
||||
// TransactionMode class;
|
||||
// API: http://vitaly-t.github.io/pg-promise/txMode.TransactionMode.html
|
||||
class TransactionMode {
|
||||
constructor(options?: { tiLevel?: isolationLevel, readOnly?: boolean, deferrable?: boolean })
|
||||
|
||||
begin(cap?: boolean): string
|
||||
}
|
||||
}
|
||||
|
||||
// Main protocol of the library;
|
||||
// API: http://vitaly-t.github.io/pg-promise/module-pg-promise.html
|
||||
declare namespace pgPromise {
|
||||
|
||||
interface IQueryFileOptions {
|
||||
debug?: boolean
|
||||
minify?: boolean | 'after'
|
||||
compress?: boolean
|
||||
params?: any
|
||||
noWarnings?: boolean
|
||||
}
|
||||
|
||||
interface IFormattingOptions {
|
||||
capSQL?: boolean
|
||||
partial?: boolean
|
||||
def?: any
|
||||
}
|
||||
|
||||
interface ILostContext<C extends pg.IClient = pg.IClient> {
|
||||
cn: string
|
||||
dc: any
|
||||
start: Date
|
||||
client: C
|
||||
}
|
||||
|
||||
interface IConnectionOptions<C extends pg.IClient = pg.IClient> {
|
||||
direct?: boolean
|
||||
|
||||
onLost?(err: any, e: ILostContext<C>): void
|
||||
}
|
||||
|
||||
interface IPreparedStatement {
|
||||
name?: string
|
||||
text?: string | QueryFile
|
||||
values?: any[]
|
||||
binary?: boolean
|
||||
rowMode?: 'array' | null | void
|
||||
rows?: number
|
||||
}
|
||||
|
||||
interface IParameterizedQuery {
|
||||
text?: string | QueryFile
|
||||
values?: any[]
|
||||
binary?: boolean
|
||||
rowMode?: void | 'array'
|
||||
}
|
||||
|
||||
interface IPreparedParsed {
|
||||
name: string
|
||||
text: string
|
||||
values: any[]
|
||||
binary: boolean
|
||||
rowMode: void | 'array'
|
||||
rows: number
|
||||
}
|
||||
|
||||
interface IParameterizedParsed {
|
||||
text: string
|
||||
values: any[]
|
||||
binary: boolean
|
||||
rowMode: void | 'array'
|
||||
}
|
||||
|
||||
interface IColumnDescriptor<T> {
|
||||
source: T
|
||||
name: string
|
||||
value: any
|
||||
exists: boolean
|
||||
}
|
||||
|
||||
interface IColumnConfig<T> {
|
||||
name: string
|
||||
prop?: string
|
||||
mod?: FormattingFilter
|
||||
cast?: string
|
||||
cnd?: boolean
|
||||
def?: any
|
||||
|
||||
init?(col: IColumnDescriptor<T>): any
|
||||
|
||||
skip?(col: IColumnDescriptor<T>): boolean
|
||||
}
|
||||
|
||||
interface IColumnSetOptions {
|
||||
table?: string | ITable | TableName
|
||||
inherit?: boolean
|
||||
}
|
||||
|
||||
interface ITable {
|
||||
table: string
|
||||
schema?: string
|
||||
}
|
||||
|
||||
interface IPromiseConfig {
|
||||
create(resolve: (value?: any) => void, reject?: (reason?: any) => void): XPromise<any>
|
||||
|
||||
resolve(value?: any): void
|
||||
|
||||
reject(reason?: any): void
|
||||
|
||||
all(iterable: any): XPromise<any>
|
||||
}
|
||||
|
||||
type FormattingFilter = '^' | '~' | '#' | ':raw' | ':alias' | ':name' | ':json' | ':csv' | ':list' | ':value';
|
||||
|
||||
type QueryColumns<T> = Column<T> | ColumnSet<T> | Array<string | IColumnConfig<T> | Column<T>>;
|
||||
|
||||
type QueryParam =
|
||||
string
|
||||
| QueryFile
|
||||
| IPreparedStatement
|
||||
| IParameterizedQuery
|
||||
| PreparedStatement
|
||||
| ParameterizedQuery
|
||||
| ((values?: any) => QueryParam);
|
||||
|
||||
type ValidSchema = string | string[] | null | void;
|
||||
|
||||
// helpers.TableName class;
|
||||
// API: http://vitaly-t.github.io/pg-promise/helpers.TableName.html
|
||||
class TableName {
|
||||
constructor(table: string | ITable)
|
||||
|
||||
// these are all read-only:
|
||||
readonly name: string;
|
||||
readonly table: string;
|
||||
readonly schema: string;
|
||||
|
||||
toString(): string
|
||||
}
|
||||
|
||||
// helpers.Column class;
|
||||
// API: http://vitaly-t.github.io/pg-promise/helpers.Column.html
|
||||
class Column<T = unknown> {
|
||||
constructor(col: string | IColumnConfig<T>);
|
||||
|
||||
// these are all read-only:
|
||||
readonly name: string;
|
||||
readonly prop: string;
|
||||
readonly mod: FormattingFilter;
|
||||
readonly cast: string;
|
||||
readonly cnd: boolean;
|
||||
readonly def: any;
|
||||
readonly castText: string;
|
||||
readonly escapedName: string;
|
||||
readonly variable: string;
|
||||
readonly init: (col: IColumnDescriptor<T>) => any
|
||||
readonly skip: (col: IColumnDescriptor<T>) => boolean
|
||||
|
||||
toString(level?: number): string
|
||||
}
|
||||
|
||||
// helpers.Column class;
|
||||
// API: http://vitaly-t.github.io/pg-promise/helpers.ColumnSet.html
|
||||
class ColumnSet<T = unknown> {
|
||||
constructor(columns: Column<T>, options?: IColumnSetOptions)
|
||||
constructor(columns: Array<string | IColumnConfig<T> | Column<T>>, options?: IColumnSetOptions)
|
||||
constructor(columns: object, options?: IColumnSetOptions)
|
||||
|
||||
readonly columns: Column<T>[];
|
||||
readonly names: string;
|
||||
readonly table: TableName;
|
||||
readonly variables: string;
|
||||
|
||||
assign(source?: { source?: object, prefix?: string }): string
|
||||
|
||||
assignColumns(options?: { from?: string, to?: string, skip?: string | string[] | ((c: Column<T>) => boolean) }): string
|
||||
|
||||
extend<S>(columns: Column<T> | ColumnSet<T> | Array<string | IColumnConfig<T> | Column<T>>): ColumnSet<S>
|
||||
|
||||
merge<S>(columns: Column<T> | ColumnSet<T> | Array<string | IColumnConfig<T> | Column<T>>): ColumnSet<S>
|
||||
|
||||
prepare(obj: object): object
|
||||
|
||||
toString(level?: number): string
|
||||
}
|
||||
|
||||
const minify: typeof pgMinify;
|
||||
|
||||
// Query Result Mask;
|
||||
// API: http://vitaly-t.github.io/pg-promise/global.html#queryResult
|
||||
enum queryResult {
|
||||
one = 1,
|
||||
many = 2,
|
||||
none = 4,
|
||||
any = 6
|
||||
}
|
||||
|
||||
// PreparedStatement class;
|
||||
// API: http://vitaly-t.github.io/pg-promise/PreparedStatement.html
|
||||
class PreparedStatement {
|
||||
|
||||
constructor(options?: IPreparedStatement)
|
||||
|
||||
// standard properties:
|
||||
name: string;
|
||||
text: string | QueryFile;
|
||||
values: any[];
|
||||
|
||||
// advanced properties:
|
||||
binary: boolean;
|
||||
rowMode: void | 'array';
|
||||
rows: number;
|
||||
|
||||
parse(): IPreparedParsed | errors.PreparedStatementError
|
||||
|
||||
toString(level?: number): string
|
||||
}
|
||||
|
||||
// ParameterizedQuery class;
|
||||
// API: http://vitaly-t.github.io/pg-promise/ParameterizedQuery.html
|
||||
class ParameterizedQuery {
|
||||
|
||||
constructor(options?: string | QueryFile | IParameterizedQuery)
|
||||
|
||||
// standard properties:
|
||||
text: string | QueryFile;
|
||||
values: any[];
|
||||
|
||||
// advanced properties:
|
||||
binary: boolean;
|
||||
rowMode: void | 'array';
|
||||
|
||||
parse(): IParameterizedParsed | errors.ParameterizedQueryError
|
||||
|
||||
toString(level?: number): string
|
||||
}
|
||||
|
||||
// QueryFile class;
|
||||
// API: http://vitaly-t.github.io/pg-promise/QueryFile.html
|
||||
class QueryFile {
|
||||
constructor(file: string, options?: IQueryFileOptions)
|
||||
|
||||
readonly error: Error;
|
||||
readonly file: string;
|
||||
readonly options: any;
|
||||
|
||||
prepare(): void
|
||||
|
||||
toString(level?: number): string
|
||||
}
|
||||
|
||||
// PromiseAdapter class;
|
||||
// API: http://vitaly-t.github.io/pg-promise/PromiseAdapter.html
|
||||
class PromiseAdapter {
|
||||
constructor(api: IPromiseConfig)
|
||||
}
|
||||
|
||||
const txMode: typeof _txMode;
|
||||
const utils: IUtils;
|
||||
const as: IFormatting;
|
||||
|
||||
// Database full protocol;
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html
|
||||
//
|
||||
// We export this interface only to be able to help IntelliSense cast extension types correctly,
|
||||
// which doesn't always work, depending on the version of IntelliSense being used.
|
||||
interface IDatabase<Ext, C extends pg.IClient = pg.IClient> extends IBaseProtocol<Ext> {
|
||||
connect(options?: IConnectionOptions<C>): XPromise<IConnected<Ext, C>>
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Hidden, read-only properties, for integrating with third-party libraries:
|
||||
|
||||
readonly $config: ILibConfig<Ext, C>
|
||||
readonly $cn: string | pg.IConnectionParameters<C>
|
||||
readonly $dc: any
|
||||
readonly $pool: pg.IPool
|
||||
}
|
||||
|
||||
interface IResultExt<T = unknown> extends pg.IResult<T> {
|
||||
// Property 'duration' exists only in the following context:
|
||||
// - for single-query events 'receive'
|
||||
// - for method Database.result
|
||||
duration?: number
|
||||
}
|
||||
|
||||
// Post-initialization interface;
|
||||
// API: http://vitaly-t.github.io/pg-promise/module-pg-promise.html
|
||||
interface IMain<Ext = {}, C extends pg.IClient = pg.IClient> {
|
||||
<T = Ext, C extends pg.IClient = pg.IClient>(cn: string | pg.IConnectionParameters<C>, dc?: any): IDatabase<T, C> & T
|
||||
|
||||
readonly PromiseAdapter: typeof PromiseAdapter
|
||||
readonly PreparedStatement: typeof PreparedStatement
|
||||
readonly ParameterizedQuery: typeof ParameterizedQuery
|
||||
readonly QueryFile: typeof QueryFile
|
||||
readonly queryResult: typeof queryResult
|
||||
readonly minify: typeof pgMinify
|
||||
readonly spex: spexLib.ISpex
|
||||
readonly errors: typeof errors
|
||||
readonly utils: IUtils
|
||||
readonly txMode: typeof txMode
|
||||
readonly helpers: IHelpers
|
||||
readonly as: IFormatting
|
||||
readonly pg: typeof pg
|
||||
|
||||
end(): void
|
||||
}
|
||||
|
||||
// Additional methods available inside tasks + transactions;
|
||||
// API: http://vitaly-t.github.io/pg-promise/Task.html
|
||||
interface ITask<Ext> extends IBaseProtocol<Ext>, spexLib.ISpexBase {
|
||||
readonly ctx: ITaskContext
|
||||
}
|
||||
|
||||
// Base database protocol
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html
|
||||
interface IBaseProtocol<Ext> {
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#query
|
||||
query<T = any>(query: QueryParam, values?: any, qrm?: queryResult): XPromise<T>
|
||||
|
||||
// result-specific methods;
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#none
|
||||
none(query: QueryParam, values?: any): XPromise<null>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#one
|
||||
one<T = any>(query: QueryParam, values?: any, cb?: (value: any) => T, thisArg?: any): XPromise<T>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#oneOrNone
|
||||
oneOrNone<T = any>(query: QueryParam, values?: any, cb?: (value: any) => T, thisArg?: any): XPromise<T | null>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#many
|
||||
many<T = any>(query: QueryParam, values?: any): XPromise<T[]>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#manyOrNone
|
||||
manyOrNone<T = any>(query: QueryParam, values?: any): XPromise<T[]>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#any
|
||||
any<T = any>(query: QueryParam, values?: any): XPromise<T[]>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#result
|
||||
result<T, R = IResultExt<T>>(query: QueryParam, values?: any, cb?: (value: IResultExt<T>) => R, thisArg?: any): XPromise<R>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#multiResult
|
||||
multiResult(query: QueryParam, values?: any): XPromise<pg.IResult[]>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#multi
|
||||
multi<T = any>(query: QueryParam, values?: any): XPromise<Array<T[]>>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#stream
|
||||
stream(qs: NodeJS.ReadableStream, init: (stream: NodeJS.ReadableStream) => void): XPromise<{ processed: number, duration: number }>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#func
|
||||
func<T = any>(funcName: string, values?: any, qrm?: queryResult): XPromise<T>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#proc
|
||||
proc<T = any>(procName: string, values?: any, cb?: (value: any) => T, thisArg?: any): XPromise<T | null>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#map
|
||||
map<T = any>(query: QueryParam, values: any, cb: (row: any, index: number, data: any[]) => T, thisArg?: any): XPromise<T[]>
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#each
|
||||
each<T = any>(query: QueryParam, values: any, cb: (row: any, index: number, data: any[]) => void, thisArg?: any): XPromise<T[]>
|
||||
|
||||
// Tasks;
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#task
|
||||
task<T = any>(cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
task<T = any>(tag: string | number, cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
task<T = any>(options: { tag?: any }, cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
// Conditional Tasks;
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#taskIf
|
||||
taskIf<T = any>(cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
taskIf<T = any>(tag: string | number, cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
taskIf<T = any>(options: { tag?: any, cnd?: boolean | ((t: ITask<Ext> & Ext) => boolean) }, cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
// Transactions;
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#tx
|
||||
tx<T = any>(cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
tx<T = any>(tag: string | number, cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
tx<T = any>(options: { tag?: any, mode?: _txMode.TransactionMode | null }, cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
// Conditional Transactions;
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#txIf
|
||||
txIf<T = any>(cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
txIf<T = any>(tag: string | number, cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
|
||||
txIf<T = any>(options: { tag?: any, mode?: _txMode.TransactionMode | null, reusable?: boolean | ((t: ITask<Ext> & Ext) => boolean), cnd?: boolean | ((t: ITask<Ext> & Ext) => boolean) }, cb: (t: ITask<Ext> & Ext) => T | XPromise<T>): XPromise<T>
|
||||
}
|
||||
|
||||
// Database object in connected state;
|
||||
// API: https://vitaly-t.github.io/pg-promise/Database.html#connect
|
||||
interface IConnected<Ext, C extends pg.IClient> extends IBaseProtocol<Ext>, spexLib.ISpexBase {
|
||||
readonly client: C
|
||||
|
||||
// Note that for normal connections (working with the pool), method `done` accepts `kill`
|
||||
// flag to terminate the connection within the pool, so it can be auto-recreated;
|
||||
// And in this case the method returns nothing / void.
|
||||
|
||||
// But for direct connections (connect({direct: true})), `kill` flag is ignored, because
|
||||
// the connection is always closed physically, which may take time, and so in this case
|
||||
// the method returns a Promise, to indicate when the connection finished closing.
|
||||
done(kill?: boolean): void | XPromise<void>;
|
||||
|
||||
// Repeated calls are not allowed, and will throw an error.
|
||||
}
|
||||
|
||||
// Event context extension for tasks + transactions;
|
||||
// See: http://vitaly-t.github.io/pg-promise/global.html#TaskContext
|
||||
interface ITaskContext {
|
||||
|
||||
// these are set in the beginning of each task/transaction:
|
||||
readonly context: any
|
||||
readonly parent: ITaskContext | null
|
||||
readonly connected: boolean
|
||||
readonly inTransaction: boolean
|
||||
readonly level: number
|
||||
readonly useCount: number
|
||||
readonly isTX: boolean
|
||||
readonly start: Date
|
||||
readonly tag: any
|
||||
readonly dc: any
|
||||
|
||||
// these are set at the end of each task/transaction:
|
||||
readonly finish?: Date
|
||||
readonly duration?: number
|
||||
readonly success?: boolean
|
||||
readonly result?: any
|
||||
|
||||
// this exists only inside transactions (isTX = true):
|
||||
readonly txLevel?: number
|
||||
|
||||
// Version of PostgreSQL Server to which we are connected;
|
||||
// This property is not available with Native Bindings!
|
||||
readonly serverVersion: string
|
||||
}
|
||||
|
||||
// Generic Event Context interface;
|
||||
// See: http://vitaly-t.github.io/pg-promise/global.html#EventContext
|
||||
interface IEventContext<C extends pg.IClient = pg.IClient> {
|
||||
client: C
|
||||
cn: any
|
||||
dc: any
|
||||
query: any
|
||||
params: any
|
||||
ctx: ITaskContext
|
||||
}
|
||||
|
||||
// Errors namespace
|
||||
// API: http://vitaly-t.github.io/pg-promise/errors.html
|
||||
namespace errors {
|
||||
// QueryResultError interface;
|
||||
// API: http://vitaly-t.github.io/pg-promise/errors.QueryResultError.html
|
||||
class QueryResultError extends Error {
|
||||
|
||||
// standard error properties:
|
||||
name: string;
|
||||
message: string;
|
||||
stack: string;
|
||||
|
||||
// extended properties:
|
||||
result: pg.IResult;
|
||||
received: number;
|
||||
code: queryResultErrorCode;
|
||||
query: string;
|
||||
values: any;
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/errors.QueryResultError.html#toString
|
||||
toString(): string
|
||||
}
|
||||
|
||||
// QueryFileError interface;
|
||||
// API: http://vitaly-t.github.io/pg-promise/errors.QueryFileError.html
|
||||
class QueryFileError extends Error {
|
||||
|
||||
// standard error properties:
|
||||
name: string;
|
||||
message: string;
|
||||
stack: string;
|
||||
|
||||
// extended properties:
|
||||
file: string;
|
||||
options: IQueryFileOptions;
|
||||
error: pgMinify.SQLParsingError;
|
||||
|
||||
toString(level?: number): string
|
||||
}
|
||||
|
||||
// PreparedStatementError interface;
|
||||
// API: http://vitaly-t.github.io/pg-promise/errors.PreparedStatementError.html
|
||||
class PreparedStatementError extends Error {
|
||||
|
||||
// standard error properties:
|
||||
name: string;
|
||||
message: string;
|
||||
stack: string;
|
||||
|
||||
// extended properties:
|
||||
error: QueryFileError;
|
||||
|
||||
toString(level?: number): string
|
||||
}
|
||||
|
||||
// ParameterizedQueryError interface;
|
||||
// API: http://vitaly-t.github.io/pg-promise/errors.ParameterizedQueryError.html
|
||||
class ParameterizedQueryError extends Error {
|
||||
|
||||
// standard error properties:
|
||||
name: string;
|
||||
message: string;
|
||||
stack: string;
|
||||
|
||||
// extended properties:
|
||||
error: QueryFileError;
|
||||
|
||||
toString(level?: number): string
|
||||
}
|
||||
|
||||
// Query Result Error Code;
|
||||
// API: http://vitaly-t.github.io/pg-promise/errors.html#.queryResultErrorCode
|
||||
enum queryResultErrorCode {
|
||||
noData = 0,
|
||||
notEmpty = 1,
|
||||
multiple = 2
|
||||
}
|
||||
}
|
||||
|
||||
// Library's Initialization Options
|
||||
// API: http://vitaly-t.github.io/pg-promise/module-pg-promise.html
|
||||
interface IInitOptions<Ext = {}, C extends pg.IClient = pg.IClient> {
|
||||
noWarnings?: boolean
|
||||
pgFormatting?: boolean
|
||||
pgNative?: boolean
|
||||
promiseLib?: any
|
||||
noLocking?: boolean
|
||||
capSQL?: boolean
|
||||
schema?: ValidSchema | ((dc: any) => ValidSchema)
|
||||
|
||||
connect?(client: C, dc: any, useCount: number): void
|
||||
|
||||
disconnect?(client: C, dc: any): void
|
||||
|
||||
query?(e: IEventContext<C>): void
|
||||
|
||||
// NOTE: result is undefined when data comes from QueryStream, i.e. via method Database.stream
|
||||
receive?(data: any[], result: IResultExt | void, e: IEventContext<C>): void
|
||||
|
||||
task?(e: IEventContext<C>): void
|
||||
|
||||
transact?(e: IEventContext<C>): void
|
||||
|
||||
error?(err: any, e: IEventContext<C>): void
|
||||
|
||||
extend?(obj: IDatabase<Ext, C> & Ext, dc: any): void
|
||||
}
|
||||
|
||||
// API: http://vitaly-t.github.io/pg-promise/Database.html#$config
|
||||
interface ILibConfig<Ext, C extends pg.IClient = pg.IClient> {
|
||||
version: string
|
||||
promiseLib: any
|
||||
promise: IGenericPromise
|
||||
options: IInitOptions<Ext, C>
|
||||
pgp: IMain<Ext, C>
|
||||
$npm: any
|
||||
}
|
||||
|
||||
// Custom-Type Formatting object
|
||||
// API: https://github.com/vitaly-t/pg-promise#custom-type-formatting
|
||||
interface ICTFObject {
|
||||
toPostgres(a: any): any
|
||||
}
|
||||
|
||||
// Query formatting namespace;
|
||||
// API: http://vitaly-t.github.io/pg-promise/formatting.html
|
||||
interface IFormatting {
|
||||
|
||||
ctf: { toPostgres: symbol, rawType: symbol }
|
||||
|
||||
alias(name: string | (() => string)): string
|
||||
|
||||
array(arr: any[] | (() => any[]), options?: { capSQL?: boolean }): string
|
||||
|
||||
bool(value: any | (() => any)): string
|
||||
|
||||
buffer(obj: object | (() => object), raw?: boolean): string
|
||||
|
||||
csv(values: any | (() => any)): string
|
||||
|
||||
date(d: Date | (() => Date), raw?: boolean): string
|
||||
|
||||
format(query: string | QueryFile | ICTFObject, values?: any, options?: IFormattingOptions): string
|
||||
|
||||
func(func: (cc: any) => any, raw?: boolean, cc?: any): string
|
||||
|
||||
json(data: any | (() => any), raw?: boolean): string
|
||||
|
||||
name(name: any | (() => any)): string
|
||||
|
||||
number(value: number | bigint | (() => number | bigint)): string
|
||||
|
||||
text(value: any | (() => any), raw?: boolean): string
|
||||
|
||||
value(value: any | (() => any)): string
|
||||
}
|
||||
|
||||
interface ITaskArguments<T> extends IArguments {
|
||||
options: { tag?: any, cnd?: any, mode?: _txMode.TransactionMode | null } & T
|
||||
|
||||
cb(): any
|
||||
}
|
||||
|
||||
// General-purpose functions
|
||||
// API: http://vitaly-t.github.io/pg-promise/utils.html
|
||||
interface IUtils {
|
||||
camelize(text: string): string
|
||||
|
||||
camelizeVar(text: string): string
|
||||
|
||||
enumSql(dir: string, options?: { recursive?: boolean, ignoreErrors?: boolean }, cb?: (file: string, name: string, path: string) => any): any
|
||||
|
||||
taskArgs<T = {}>(args: IArguments): ITaskArguments<T>
|
||||
}
|
||||
|
||||
// Query Formatting Helpers
|
||||
// API: http://vitaly-t.github.io/pg-promise/helpers.html
|
||||
interface IHelpers {
|
||||
|
||||
concat(queries: Array<string | QueryFile | { query: string | QueryFile, values?: any, options?: IFormattingOptions }>): string
|
||||
|
||||
insert(data: object | object[], columns?: QueryColumns<any> | null, table?: string | ITable | TableName): string
|
||||
|
||||
update(data: object | object[], columns?: QueryColumns<any> | null, table?: string | ITable | TableName, options?: { tableAlias?: string, valueAlias?: string, emptyUpdate?: any }): any
|
||||
|
||||
values(data: object | object[], columns?: QueryColumns<any> | null): string
|
||||
|
||||
sets(data: object, columns?: QueryColumns<any> | null): string
|
||||
|
||||
Column: typeof Column
|
||||
ColumnSet: typeof ColumnSet
|
||||
TableName: typeof TableName
|
||||
}
|
||||
|
||||
interface IGenericPromise {
|
||||
(cb: (resolve: (value?: any) => void, reject: (reason?: any) => void) => void): XPromise<any>
|
||||
|
||||
resolve(value?: any): void
|
||||
|
||||
reject(reason?: any): void
|
||||
|
||||
all(iterable: any): XPromise<any>
|
||||
}
|
||||
}
|
||||
|
||||
// Default library interface (before initialization)
|
||||
// API: http://vitaly-t.github.io/pg-promise/module-pg-promise.html
|
||||
declare function pgPromise<Ext = {}, C extends pg.IClient = pg.IClient>(options?: pgPromise.IInitOptions<Ext, C>): pgPromise.IMain<Ext, C>
|
||||
|
||||
export = pgPromise;
|
||||
334
ProjectSourceCode/node_modules/pg-promise/typescript/pg-subset.d.ts
generated
vendored
Normal file
334
ProjectSourceCode/node_modules/pg-promise/typescript/pg-subset.d.ts
generated
vendored
Normal file
@@ -0,0 +1,334 @@
|
||||
/*
|
||||
* Copyright (c) 2015-present, Vitaly Tomilov
|
||||
*
|
||||
* See the LICENSE file at the top-level directory of this distribution
|
||||
* for licensing information.
|
||||
*
|
||||
* Removal or modification of this copyright notice is prohibited.
|
||||
*/
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
// Declaring only a subset of the 'pg' module that's useful within pg-promise.
|
||||
//
|
||||
// Calling it 'pg-subset' to avoid a conflict in case the application also
|
||||
// includes the official 'pg' typings.
|
||||
//
|
||||
// Supported version of pg: 8.7.1 and later.
|
||||
//
|
||||
// pg: https://github.com/brianc/node-postgres
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
import {EventEmitter} from 'events';
|
||||
import {checkServerIdentity} from 'tls';
|
||||
|
||||
declare namespace pg {
|
||||
|
||||
import Socket = NodeJS.Socket;
|
||||
|
||||
interface IColumn {
|
||||
name: string
|
||||
oid: number
|
||||
dataTypeID: number
|
||||
|
||||
// NOTE: properties below are not available within Native Bindings:
|
||||
|
||||
tableID: number
|
||||
columnID: number
|
||||
dataTypeSize: number
|
||||
dataTypeModifier: number
|
||||
format: string
|
||||
}
|
||||
|
||||
interface IResult<T = unknown> extends Iterable<T> {
|
||||
command: string
|
||||
rowCount: number
|
||||
rows: T[]
|
||||
fields: IColumn[]
|
||||
|
||||
// properties below are not available within Native Bindings:
|
||||
rowAsArray: boolean
|
||||
|
||||
_types: {
|
||||
_types: any,
|
||||
text: any,
|
||||
binary: any
|
||||
};
|
||||
_parsers: Array<Function>;
|
||||
}
|
||||
|
||||
// SSL configuration;
|
||||
// For property types and documentation see:
|
||||
// http://nodejs.org/api/tls.html#tls_tls_connect_options_callback
|
||||
interface ISSLConfig {
|
||||
ca?: string | Buffer | Array<string | Buffer>
|
||||
pfx?: string | Buffer | Array<string | Buffer | object>
|
||||
cert?: string | Buffer | Array<string | Buffer>
|
||||
key?: string | Buffer | Array<Buffer | object>
|
||||
passphrase?: string
|
||||
rejectUnauthorized?: boolean
|
||||
checkServerIdentity?: typeof checkServerIdentity
|
||||
secureOptions?: number
|
||||
NPNProtocols?: string[] | Buffer | Buffer[] | Uint8Array | Uint8Array[]
|
||||
}
|
||||
|
||||
type DynamicPassword = string | (() => string) | (() => Promise<string>);
|
||||
|
||||
// See:
|
||||
// 1) https://github.com/brianc/node-postgres/blob/master/packages/pg/lib/defaults.js
|
||||
// 2) https://github.com/brianc/node-pg-pool
|
||||
interface IConnectionParameters<C extends IClient = IClient> {
|
||||
connectionString?: string
|
||||
host?: string
|
||||
database?: string
|
||||
user?: string
|
||||
password?: DynamicPassword
|
||||
port?: number
|
||||
ssl?: boolean | ISSLConfig
|
||||
binary?: boolean
|
||||
client_encoding?: string
|
||||
encoding?: string
|
||||
application_name?: string
|
||||
fallback_application_name?: string
|
||||
isDomainSocket?: boolean
|
||||
max?: number
|
||||
maxUses?: number
|
||||
idleTimeoutMillis?: number
|
||||
parseInputDatesAsUTC?: boolean
|
||||
rows?: number
|
||||
statement_timeout?: boolean | number
|
||||
query_timeout?: boolean | number
|
||||
connectionTimeoutMillis?: number
|
||||
keepAliveInitialDelayMillis?: number
|
||||
keepAlive?: boolean
|
||||
keepalives?: number
|
||||
keepalives_idle?: number
|
||||
Client?: new(config: string | IConnectionParameters) => C
|
||||
Promise?: any
|
||||
types?: ITypeOverrides
|
||||
allowExitOnIdle?: boolean
|
||||
maxLifetimeSeconds?: number
|
||||
}
|
||||
|
||||
// Type id-s supported by PostgreSQL, copied from:
|
||||
// http://github.com/brianc/node-pg-types/blob/master/lib/builtins.js
|
||||
enum TypeId {
|
||||
BOOL = 16,
|
||||
BYTEA = 17,
|
||||
CHAR = 18,
|
||||
INT8 = 20,
|
||||
INT2 = 21,
|
||||
INT4 = 23,
|
||||
REGPROC = 24,
|
||||
TEXT = 25,
|
||||
OID = 26,
|
||||
TID = 27,
|
||||
XID = 28,
|
||||
CID = 29,
|
||||
JSON = 114,
|
||||
XML = 142,
|
||||
PG_NODE_TREE = 194,
|
||||
SMGR = 210,
|
||||
PATH = 602,
|
||||
POLYGON = 604,
|
||||
CIDR = 650,
|
||||
FLOAT4 = 700,
|
||||
FLOAT8 = 701,
|
||||
ABSTIME = 702,
|
||||
RELTIME = 703,
|
||||
TINTERVAL = 704,
|
||||
CIRCLE = 718,
|
||||
MACADDR8 = 774,
|
||||
MONEY = 790,
|
||||
MACADDR = 829,
|
||||
INET = 869,
|
||||
ACLITEM = 1033,
|
||||
BPCHAR = 1042,
|
||||
VARCHAR = 1043,
|
||||
DATE = 1082,
|
||||
TIME = 1083,
|
||||
TIMESTAMP = 1114,
|
||||
TIMESTAMPTZ = 1184,
|
||||
INTERVAL = 1186,
|
||||
TIMETZ = 1266,
|
||||
BIT = 1560,
|
||||
VARBIT = 1562,
|
||||
NUMERIC = 1700,
|
||||
REFCURSOR = 1790,
|
||||
REGPROCEDURE = 2202,
|
||||
REGOPER = 2203,
|
||||
REGOPERATOR = 2204,
|
||||
REGCLASS = 2205,
|
||||
REGTYPE = 2206,
|
||||
UUID = 2950,
|
||||
TXID_SNAPSHOT = 2970,
|
||||
PG_LSN = 3220,
|
||||
PG_NDISTINCT = 3361,
|
||||
PG_DEPENDENCIES = 3402,
|
||||
TSVECTOR = 3614,
|
||||
TSQUERY = 3615,
|
||||
GTSVECTOR = 3642,
|
||||
REGCONFIG = 3734,
|
||||
REGDICTIONARY = 3769,
|
||||
JSONB = 3802,
|
||||
REGNAMESPACE = 4089,
|
||||
REGROLE = 4096
|
||||
}
|
||||
|
||||
type ParserFormat = 'text' | 'binary';
|
||||
|
||||
// Interface for TypeOverrides;
|
||||
// See: https://github.com/brianc/node-postgres/blob/master/packages/pg/lib/type-overrides.js
|
||||
interface ITypeOverrides {
|
||||
setTypeParser(id: TypeId, parseFn: string | ((value: string) => any)): void
|
||||
|
||||
setTypeParser(id: TypeId, format: ParserFormat, parseFn: string | ((value: string) => any)): void
|
||||
|
||||
getTypeParser(id: TypeId, format?: ParserFormat): any
|
||||
}
|
||||
|
||||
// Interface of 'pg-types' module;
|
||||
// See: https://github.com/brianc/node-pg-types
|
||||
interface ITypes extends ITypeOverrides {
|
||||
arrayParser(source: string, transform: (entry: any) => any): any[]
|
||||
|
||||
builtins: typeof TypeId
|
||||
}
|
||||
|
||||
interface IDefaults {
|
||||
|
||||
// connection string for overriding defaults
|
||||
connectionString: string
|
||||
|
||||
// database host. defaults to localhost
|
||||
host: string
|
||||
|
||||
// database user's name
|
||||
user: string
|
||||
|
||||
// name of database to connect
|
||||
database: string
|
||||
|
||||
// database user's password
|
||||
password: DynamicPassword
|
||||
|
||||
// database port
|
||||
port: number
|
||||
|
||||
// number of rows to return at a time from a prepared statement's
|
||||
// portal. 0 will return all rows at once
|
||||
rows: number
|
||||
|
||||
// binary result mode
|
||||
binary: boolean
|
||||
|
||||
// Connection pool options - see https://github.com/brianc/node-pg-pool
|
||||
|
||||
// number of connections to use in connection pool
|
||||
// 0 will disable connection pooling
|
||||
max: number
|
||||
|
||||
// max milliseconds a client can go unused before it is removed from the pool and destroyed;
|
||||
//
|
||||
// Made unavailable in v10.5.0, due to the following:
|
||||
// - https://github.com/brianc/node-postgres/issues/2139
|
||||
// - https://github.com/vitaly-t/pg-promise/issues/703
|
||||
//
|
||||
// idleTimeoutMillis: number
|
||||
|
||||
client_encoding: string
|
||||
|
||||
ssl: boolean | ISSLConfig
|
||||
|
||||
application_name: string
|
||||
|
||||
fallback_application_name: string
|
||||
|
||||
parseInputDatesAsUTC: boolean
|
||||
|
||||
// max milliseconds any query using this connection will execute for before timing out in error.
|
||||
// false=unlimited
|
||||
statement_timeout: boolean | number
|
||||
|
||||
// max milliseconds to wait for query to complete (client side)
|
||||
query_timeout: boolean | number
|
||||
|
||||
keepalives: number
|
||||
|
||||
keepalives_idle: number
|
||||
}
|
||||
|
||||
// interface IPool, as per the following implementation:
|
||||
// https://github.com/brianc/node-postgres/blob/master/packages/pg-pool/index.js#L61
|
||||
// NOTE: We declare only what can be used from pg-promise
|
||||
interface IPool extends EventEmitter {
|
||||
|
||||
connect(): Promise<IClient>;
|
||||
|
||||
end(): Promise<undefined>;
|
||||
|
||||
end(cb: (err: Error) => any): any;
|
||||
|
||||
readonly options: { [name: string]: any }; // connection options
|
||||
|
||||
readonly ended: boolean;
|
||||
readonly ending: boolean;
|
||||
|
||||
readonly waitingCount: number;
|
||||
readonly idleCount: number;
|
||||
readonly totalCount: number;
|
||||
}
|
||||
|
||||
interface IQuery {
|
||||
// this type is not used within pg-promise;
|
||||
}
|
||||
|
||||
interface IConnection extends EventEmitter {
|
||||
/*
|
||||
While there are many other properties exist within the connection,
|
||||
the only one that may be remotely useful is the stream, to be able
|
||||
to listen to its events, from within a custom Client class.
|
||||
*/
|
||||
stream: Socket
|
||||
}
|
||||
|
||||
interface IClient extends EventEmitter {
|
||||
|
||||
query<T>(config: any, values: any[], callback: (err: Error, result: IResult<T>) => void): void
|
||||
|
||||
query<T>(config: any, callback: (err: Error, result: IResult<T>) => void): void
|
||||
|
||||
query<T>(config: any, values: any[]): Promise<IResult<T>>
|
||||
|
||||
query<T>(config: any): Promise<IResult<T>>
|
||||
|
||||
release(): void
|
||||
|
||||
connectionParameters: IConnectionParameters
|
||||
database: string
|
||||
user: string
|
||||
password: DynamicPassword
|
||||
port: number
|
||||
host: string
|
||||
|
||||
//////////////////////////////////////////////////////////////
|
||||
// Properties below are not available within Native Bindings:
|
||||
|
||||
readonly serverVersion: string // PostgreSQL Server to which the client is connected
|
||||
|
||||
connection: IConnection
|
||||
queryQueue: IQuery[]
|
||||
binary: boolean
|
||||
ssl: boolean | ISSLConfig
|
||||
secretKey: number
|
||||
processID: number
|
||||
encoding: string
|
||||
readyForQuery: boolean
|
||||
activeQuery: IQuery
|
||||
}
|
||||
|
||||
const defaults: IDefaults;
|
||||
const types: ITypes;
|
||||
const Client: new(config: string | IConnectionParameters) => IClient;
|
||||
}
|
||||
|
||||
export = pg;
|
||||
21
ProjectSourceCode/node_modules/pg-promise/typescript/tslint.json
generated
vendored
Normal file
21
ProjectSourceCode/node_modules/pg-promise/typescript/tslint.json
generated
vendored
Normal file
@@ -0,0 +1,21 @@
|
||||
{
|
||||
"rules": {
|
||||
"trailing-comma": [
|
||||
true,
|
||||
{
|
||||
"multiline": "never",
|
||||
"singleline": "never"
|
||||
}
|
||||
],
|
||||
"quotemark": [
|
||||
true,
|
||||
"single"
|
||||
],
|
||||
"class-name": true,
|
||||
"interface-name": [
|
||||
true,
|
||||
"always-prefix"
|
||||
],
|
||||
"no-consecutive-blank-lines": true
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user