mastercache
Version:
Multi-tier cache module for Node.js. Redis, Upstash, CloudfareKV, File, in-memory and others drivers
1 lines • 294 kB
Source Map (JSON)
{"version":3,"sources":["../../../../src/drivers/database/index.ts","../../../../../../node_modules/.pnpm/@lukeed+ms@2.0.2/node_modules/@lukeed/ms/dist/index.mjs","../../../../src/helpers.ts","../../../../src/drivers/base-driver.ts","../../../../src/drivers/database/database.ts","../../../../src/drivers/database/adapters/knex.ts","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/util/object-utils.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/identifier-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/schemable-identifier-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/alias-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/table-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/operation-node-source.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/expression/expression.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/select-modifier-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/and-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/or-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/on-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/join-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/binary-operation-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/operator-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/column-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/select-all-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/reference-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/dynamic/dynamic-reference-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/order-by-item-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/raw-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/order-by-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/json-reference-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/json-operator-chain-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/json-path-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/reference-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/primitive-value-list-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/value-list-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/value-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/value-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/parens-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/binary-operation-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/order-by-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/partition-by-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/over-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/from-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/group-by-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/having-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/select-query-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/util/prevent-await.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-builder/join-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/partition-by-item-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/partition-by-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-builder/over-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/selection-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/select-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/insert-query-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/update-query-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/using-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/delete-query-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/where-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/returning-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/explain-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/when-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/merge-query-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/output-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/query-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-builder/no-result-error.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/top-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/top-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/limit-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/util/random-string.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/util/query-id.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/util/require-all-props.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/operation-node-transformer.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/plugin/with-schema/with-schema-transformer.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/plugin/with-schema/with-schema-plugin.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/util/deferred.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/util/log-once.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-executor/query-executor-base.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-executor/noop-query-executor.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/parse-utils.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/join-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/offset-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/group-by-item-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/group-by-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/set-operation-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/set-operation-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/expression/expression-wrapper.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/fetch-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/fetch-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-builder/select-query-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/aggregate-function-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/function-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-builder/aggregate-function-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-builder/function-module.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/unary-operation-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/unary-operation-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/case-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-builder/case-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/json-path-leg-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/query-builder/json-path-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/tuple-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/data-type-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/data-type-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/operation-node/cast-node.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/expression/expression-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/expression-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/parser/table-parser.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/raw-builder/raw-builder.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/raw-builder/sql.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/dialect/dialect-adapter-base.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/dialect/sqlite/sqlite-adapter.js","../../../../../../node_modules/.pnpm/kysely@0.27.4/node_modules/kysely/dist/esm/dialect/mysql/mysql-adapter.js","../../../../src/drivers/database/adapters/kysely.ts","../../../../src/drivers/database/adapters/orchid.ts"],"sourcesContent":["export * from './adapters';\nexport * from './database';","var RGX = /^(-?(?:\\d+)?\\.?\\d+) *(m(?:illiseconds?|s(?:ecs?)?))?(s(?:ec(?:onds?|s)?)?)?(m(?:in(?:utes?|s)?)?)?(h(?:ours?|rs?)?)?(d(?:ays?)?)?(w(?:eeks?|ks?)?)?(y(?:ears?|rs?)?)?$/,\n\tSEC = 1e3,\n\tMIN = SEC * 60,\n\tHOUR = MIN * 60,\n\tDAY = HOUR * 24,\n\tYEAR = DAY * 365.25;\n\nexport function parse(val) {\n\tvar num, arr = val.toLowerCase().match(RGX);\n\tif (arr != null && (num = parseFloat(arr[1]))) {\n\t\tif (arr[3] != null) return num * SEC;\n\t\tif (arr[4] != null) return num * MIN;\n\t\tif (arr[5] != null) return num * HOUR;\n\t\tif (arr[6] != null) return num * DAY;\n\t\tif (arr[7] != null) return num * DAY * 7;\n\t\tif (arr[8] != null) return num * YEAR;\n\t\treturn num;\n\t}\n}\n\nfunction fmt(val, pfx, str, long) {\n\tvar num = (val | 0) === val ? val : ~~(val + 0.5);\n\treturn pfx + num + (long ? (' ' + str + (num != 1 ? 's' : '')) : str[0]);\n}\n\nexport function format(num, long) {\n\tvar pfx = num < 0 ? '-' : '', abs = num < 0 ? -num : num;\n\tif (abs < SEC) return num + (long ? ' ms' : 'ms');\n\tif (abs < MIN) return fmt(abs / SEC, pfx, 'second', long);\n\tif (abs < HOUR) return fmt(abs / MIN, pfx, 'minute', long);\n\tif (abs < DAY) return fmt(abs / HOUR, pfx, 'hour', long);\n\tif (abs < YEAR) return fmt(abs / DAY, pfx, 'day', long);\n\treturn fmt(abs / YEAR, pfx, 'year', long);\n}\n","import { parse } from '@lukeed/ms';\n\nimport type { Duration } from './types/main';\n\n/**\n * Resolve a TTL value to a number in milliseconds\n */\nexport function resolveTtl(ttl?: Duration, defaultTtl: Duration = 30_000) {\n if (typeof ttl === 'number') return ttl;\n\n /**\n * If the TTL is null, it means the value should never expire\n */\n if (ttl === null) {\n return undefined;\n }\n\n if (ttl === undefined) {\n if (typeof defaultTtl === 'number') return defaultTtl;\n if (typeof defaultTtl === 'string') return parse(defaultTtl);\n\n return undefined;\n }\n\n return parse(ttl);\n}\n\n/**\n * Useful for creating a return value that can be destructured\n * or iterated over.\n *\n * See : https://antfu.me/posts/destructuring-with-object-or-array\n */\nexport function createIsomorphicDestructurable<\n T extends Record<string, unknown>,\n A extends readonly any[],\n>(obj: T, arr: A): T & A {\n const clone = { ...obj };\n\n Object.defineProperty(clone, Symbol.iterator, {\n enumerable: false,\n value() {\n let index = 0;\n return {\n next: () => ({\n value: arr[index++],\n done: index > arr.length,\n }),\n };\n },\n });\n\n return clone as T & A;\n}\n","import type { DriverCommonOptions } from '../types/main';\n\nexport abstract class BaseDriver {\n /**\n * Current cache prefix\n */\n protected prefix: string;\n\n constructor(protected config: DriverCommonOptions) {\n this.prefix = this.#sanitizePrefix(config.prefix);\n }\n\n /**\n * Sanitizes the cache prefix by removing any trailing colons\n */\n #sanitizePrefix(prefix?: string) {\n if (!prefix) return '';\n return prefix.replace(/:+$/, '');\n }\n\n /**\n * Creates a namespace prefix by concatenating the cache prefix with the given namespace\n * If the cache prefix is not defined, the namespace is returned as is\n */\n protected createNamespacePrefix(namespace: string) {\n const sanitizedPrefix = this.#sanitizePrefix(this.prefix);\n return sanitizedPrefix ? `${sanitizedPrefix}:${namespace}` : namespace;\n }\n\n /**\n * Returns the cache key with the prefix added to it, if a prefix is defined\n */\n protected getItemKey(key: string) {\n return this.prefix ? `${this.prefix}:${key}` : key;\n }\n}\n","import { resolveTtl } from '../../helpers';\nimport { BaseDriver } from '../base-driver';\nimport type { DatabaseConfig, CacheDriver, DatabaseAdapter } from '../../types/main';\n\n/**\n * A store that use a database to store cache entries\n *\n * You should provide an adapter that will handle the database interactions\n */\nexport class DatabaseDriver extends BaseDriver implements CacheDriver<true> {\n type = 'l2' as const;\n\n /**\n * The underlying adapter\n */\n #adapter: DatabaseAdapter;\n\n /**\n * A promise that resolves when the table is created\n */\n #initialized: Promise<void>;\n\n /**\n * Pruning interval\n */\n #pruneInterval?: NodeJS.Timeout;\n\n constructor(adapter: DatabaseAdapter, config: DatabaseConfig, isNamespace = false) {\n super(config);\n this.#adapter = adapter;\n\n if (isNamespace) {\n this.#initialized = Promise.resolve();\n return;\n }\n\n this.#adapter.setTableName(config.tableName || 'mastercache');\n\n if (config.autoCreateTable !== false) {\n this.#initialized = this.#adapter.createTableIfNotExists();\n } else {\n this.#initialized = Promise.resolve();\n }\n\n if (config.pruneInterval === false) return;\n this.#startPruneInterval(resolveTtl(config.pruneInterval)!);\n }\n\n /**\n * Start the interval that will prune expired entries\n * Maybe rework this using a node Worker ?\n */\n #startPruneInterval(interval: number) {\n this.#pruneInterval = setInterval(async () => {\n await this.#initialized;\n await this.#adapter\n .pruneExpiredEntries()\n .catch((err) => console.error('[mastercache] failed to prune expired entries', err));\n }, interval);\n }\n\n /**\n * Check if the given timestamp is expired\n */\n #isExpired(expiration: number | null) {\n return expiration !== null && expiration < Date.now();\n }\n\n /**\n * Returns a new instance of the driver namespaced\n */\n namespace(namespace: string) {\n const store = new (this.constructor as any)(\n this.#adapter,\n { ...this.config, prefix: this.createNamespacePrefix(namespace) },\n true,\n );\n\n return store;\n }\n\n /**\n * Get a value from the cache\n */\n async get(key: string) {\n await this.#initialized;\n\n const result = await this.#adapter.get(this.getItemKey(key));\n if (!result) return;\n\n if (this.#isExpired(result.expiresAt)) {\n await this.#adapter.delete(key);\n return;\n }\n\n return result.value;\n }\n\n /**\n * Get the value of a key and delete it\n *\n * Returns the value if the key exists, undefined otherwise\n */\n async pull(key: string): Promise<string | undefined> {\n const value = await this.get(key);\n if (value) await this.delete(key);\n\n return value;\n }\n\n /**\n * Set a value in the cache\n * Returns true if the value was set, false otherwise\n */\n async set(key: string, value: any, ttl?: number) {\n await this.#initialized;\n await this.#adapter.set({\n key: this.getItemKey(key),\n value,\n expiresAt: ttl ? new Date(Date.now() + ttl) : null,\n });\n\n return true;\n }\n\n /**\n * Check if a key exists in the cache\n */\n async has(key: string) {\n await this.#initialized;\n const result = await this.get(key);\n\n if (!result) return false;\n return true;\n }\n\n /**\n * Remove all items from the cache\n */\n async clear() {\n await this.#initialized;\n\n await this.#adapter.clear(this.prefix);\n }\n\n /**\n * Delete a key from the cache\n * Returns true if the key was deleted, false otherwise\n */\n async delete(key: string) {\n await this.#initialized;\n return this.#adapter.delete(this.getItemKey(key));\n }\n\n /**\n * Delete multiple keys from the cache\n */\n async deleteMany(keys: string[]) {\n await this.#initialized;\n\n keys = keys.map((key) => this.getItemKey(key));\n const result = await this.#adapter.deleteMany(keys);\n\n return result > 0;\n }\n\n /**\n * Disconnect from the database\n */\n async disconnect() {\n if (this.#pruneInterval) {\n clearInterval(this.#pruneInterval);\n }\n\n await this.#adapter.disconnect();\n }\n}\n","import type { Knex } from 'knex';\n\nimport { DatabaseDriver } from '../database';\nimport type { CreateDriverResult, DatabaseAdapter, KnexConfig } from '../../../types/main';\n\n\n/**\n * Knex adapter for the DatabaseDriver\n */\nexport class KnexAdapter implements DatabaseAdapter {\n #connection: Knex;\n #tableName!: string;\n\n constructor(config: KnexConfig) {\n this.#connection = config.connection;\n }\n\n setTableName(tableName: string): void {\n this.#tableName = tableName;\n }\n\n async get(key: string): Promise<{ value: string; expiresAt: number | null } | undefined> {\n const result = await this.#connection\n .from(this.#tableName)\n .select(['value', 'expires_at'])\n .where('key', key)\n .first();\n\n if (!result) return;\n\n return { value: result.value, expiresAt: result.expires_at };\n }\n\n async delete(key: string): Promise<boolean> {\n const result = await this.#connection.from(this.#tableName).where('key', key).delete();\n return result > 0;\n }\n\n async deleteMany(keys: string[]): Promise<number> {\n return await this.#connection.from(this.#tableName).whereIn('key', keys).delete();\n }\n\n async disconnect(): Promise<void> {\n await this.#connection.destroy();\n }\n\n async createTableIfNotExists(): Promise<void> {\n const hasTable = await this.#connection.schema.hasTable(this.#tableName);\n if (hasTable) return;\n\n await this.#connection.schema.createTable(this.#tableName, (table) => {\n table.string('key', 255).notNullable().primary();\n table.text('value', 'longtext');\n table.timestamp('expires_at').nullable();\n });\n }\n\n async pruneExpiredEntries(): Promise<void> {\n await this.#connection.from(this.#tableName).where('expires_at', '<', new Date()).delete();\n }\n\n async clear(prefix: string): Promise<void> {\n await this.#connection.from(this.#tableName).where('key', 'like', `${prefix}%`).delete();\n }\n\n async set(row: { key: string; value: any; expiresAt: Date | null }): Promise<void> {\n await this.#connection\n .from(this.#tableName)\n .insert({ key: row.key, value: row.value, expires_at: row.expiresAt })\n .onConflict('key')\n .merge(['value', 'expires_at']);\n }\n}\n\n/**\n * Create a knex driver\n * You will need to install the underlying database package (mysql2, pg, sqlite3, etc)\n */\nexport function knexDriver(options: KnexConfig): CreateDriverResult<DatabaseDriver> {\n return {\n options,\n factory: (config: KnexConfig) => {\n const adapter = new KnexAdapter(config);\n return new DatabaseDriver(adapter, config);\n },\n };\n}\n","/// <reference types=\"./object-utils.d.ts\" />\nexport function isEmpty(obj) {\n if (Array.isArray(obj) || isString(obj) || isBuffer(obj)) {\n return obj.length === 0;\n }\n else if (obj) {\n return Object.keys(obj).length === 0;\n }\n return false;\n}\nexport function isUndefined(obj) {\n return typeof obj === 'undefined' || obj === undefined;\n}\nexport function isString(obj) {\n return typeof obj === 'string';\n}\nexport function isNumber(obj) {\n return typeof obj === 'number';\n}\nexport function isBoolean(obj) {\n return typeof obj === 'boolean';\n}\nexport function isNull(obj) {\n return obj === null;\n}\nexport function isDate(obj) {\n return obj instanceof Date;\n}\nexport function isBigInt(obj) {\n return typeof obj === 'bigint';\n}\n// Don't change the returnd type to `obj is Buffer` to not create a\n// hard dependency to node.\nexport function isBuffer(obj) {\n return typeof Buffer !== 'undefined' && Buffer.isBuffer(obj);\n}\nexport function isFunction(obj) {\n return typeof obj === 'function';\n}\nexport function isObject(obj) {\n return typeof obj === 'object' && obj !== null;\n}\nexport function isArrayBufferOrView(obj) {\n return obj instanceof ArrayBuffer || ArrayBuffer.isView(obj);\n}\nexport function isPlainObject(obj) {\n if (!isObject(obj) || getTag(obj) !== '[object Object]') {\n return false;\n }\n if (Object.getPrototypeOf(obj) === null) {\n return true;\n }\n let proto = obj;\n while (Object.getPrototypeOf(proto) !== null) {\n proto = Object.getPrototypeOf(proto);\n }\n return Object.getPrototypeOf(obj) === proto;\n}\nexport function getLast(arr) {\n return arr[arr.length - 1];\n}\nexport function freeze(obj) {\n return Object.freeze(obj);\n}\nexport function asArray(arg) {\n if (isReadonlyArray(arg)) {\n return arg;\n }\n else {\n return [arg];\n }\n}\nexport function asReadonlyArray(arg) {\n if (isReadonlyArray(arg)) {\n return arg;\n }\n else {\n return freeze([arg]);\n }\n}\nexport function isReadonlyArray(arg) {\n return Array.isArray(arg);\n}\nexport function noop(obj) {\n return obj;\n}\nexport function compare(obj1, obj2) {\n if (isReadonlyArray(obj1) && isReadonlyArray(obj2)) {\n return compareArrays(obj1, obj2);\n }\n else if (isObject(obj1) && isObject(obj2)) {\n return compareObjects(obj1, obj2);\n }\n return obj1 === obj2;\n}\nfunction compareArrays(arr1, arr2) {\n if (arr1.length !== arr2.length) {\n return false;\n }\n for (let i = 0; i < arr1.length; ++i) {\n if (!compare(arr1[i], arr2[i])) {\n return false;\n }\n }\n return true;\n}\nfunction compareObjects(obj1, obj2) {\n if (isBuffer(obj1) && isBuffer(obj2)) {\n return compareBuffers(obj1, obj2);\n }\n else if (isDate(obj1) && isDate(obj2)) {\n return compareDates(obj1, obj2);\n }\n return compareGenericObjects(obj1, obj2);\n}\nfunction compareBuffers(buf1, buf2) {\n return Buffer.compare(buf1, buf2) === 0;\n}\nfunction compareDates(date1, date2) {\n return date1.getTime() === date2.getTime();\n}\nfunction compareGenericObjects(obj1, obj2) {\n const keys1 = Object.keys(obj1);\n const keys2 = Object.keys(obj2);\n if (keys1.length !== keys2.length) {\n return false;\n }\n for (const key of keys1) {\n if (!compare(obj1[key], obj2[key])) {\n return false;\n }\n }\n return true;\n}\nconst toString = Object.prototype.toString;\nfunction getTag(value) {\n if (value == null) {\n return value === undefined ? '[object Undefined]' : '[object Null]';\n }\n return toString.call(value);\n}\n","/// <reference types=\"./identifier-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const IdentifierNode = freeze({\n is(node) {\n return node.kind === 'IdentifierNode';\n },\n create(name) {\n return freeze({\n kind: 'IdentifierNode',\n name,\n });\n },\n});\n","/// <reference types=\"./schemable-identifier-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\nimport { IdentifierNode } from './identifier-node.js';\n/**\n * @internal\n */\nexport const SchemableIdentifierNode = freeze({\n is(node) {\n return node.kind === 'SchemableIdentifierNode';\n },\n create(identifier) {\n return freeze({\n kind: 'SchemableIdentifierNode',\n identifier: IdentifierNode.create(identifier),\n });\n },\n createWithSchema(schema, identifier) {\n return freeze({\n kind: 'SchemableIdentifierNode',\n schema: IdentifierNode.create(schema),\n identifier: IdentifierNode.create(identifier),\n });\n },\n});\n","/// <reference types=\"./alias-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const AliasNode = freeze({\n is(node) {\n return node.kind === 'AliasNode';\n },\n create(node, alias) {\n return freeze({\n kind: 'AliasNode',\n node,\n alias,\n });\n },\n});\n","/// <reference types=\"./table-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\nimport { SchemableIdentifierNode } from './schemable-identifier-node.js';\n/**\n * @internal\n */\nexport const TableNode = freeze({\n is(node) {\n return node.kind === 'TableNode';\n },\n create(table) {\n return freeze({\n kind: 'TableNode',\n table: SchemableIdentifierNode.create(table),\n });\n },\n createWithSchema(schema, table) {\n return freeze({\n kind: 'TableNode',\n table: SchemableIdentifierNode.createWithSchema(schema, table),\n });\n },\n});\n","/// <reference types=\"./operation-node-source.d.ts\" />\nimport { isFunction, isObject } from '../util/object-utils.js';\nexport function isOperationNodeSource(obj) {\n return isObject(obj) && isFunction(obj.toOperationNode);\n}\n","/// <reference types=\"./expression.d.ts\" />\nimport { isOperationNodeSource, } from '../operation-node/operation-node-source.js';\nimport { isObject, isString } from '../util/object-utils.js';\nexport function isExpression(obj) {\n return isObject(obj) && 'expressionType' in obj && isOperationNodeSource(obj);\n}\nexport function isAliasedExpression(obj) {\n return (isObject(obj) &&\n 'expression' in obj &&\n isString(obj.alias) &&\n isOperationNodeSource(obj));\n}\n","/// <reference types=\"./select-modifier-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const SelectModifierNode = freeze({\n is(node) {\n return node.kind === 'SelectModifierNode';\n },\n create(modifier, of) {\n return freeze({\n kind: 'SelectModifierNode',\n modifier,\n of,\n });\n },\n createWithExpression(modifier) {\n return freeze({\n kind: 'SelectModifierNode',\n rawModifier: modifier,\n });\n },\n});\n","/// <reference types=\"./and-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const AndNode = freeze({\n is(node) {\n return node.kind === 'AndNode';\n },\n create(left, right) {\n return freeze({\n kind: 'AndNode',\n left,\n right,\n });\n },\n});\n","/// <reference types=\"./or-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const OrNode = freeze({\n is(node) {\n return node.kind === 'OrNode';\n },\n create(left, right) {\n return freeze({\n kind: 'OrNode',\n left,\n right,\n });\n },\n});\n","/// <reference types=\"./on-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\nimport { AndNode } from './and-node.js';\nimport { OrNode } from './or-node.js';\n/**\n * @internal\n */\nexport const OnNode = freeze({\n is(node) {\n return node.kind === 'OnNode';\n },\n create(filter) {\n return freeze({\n kind: 'OnNode',\n on: filter,\n });\n },\n cloneWithOperation(onNode, operator, operation) {\n return freeze({\n ...onNode,\n on: operator === 'And'\n ? AndNode.create(onNode.on, operation)\n : OrNode.create(onNode.on, operation),\n });\n },\n});\n","/// <reference types=\"./join-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\nimport { OnNode } from './on-node.js';\n/**\n * @internal\n */\nexport const JoinNode = freeze({\n is(node) {\n return node.kind === 'JoinNode';\n },\n create(joinType, table) {\n return freeze({\n kind: 'JoinNode',\n joinType,\n table,\n on: undefined,\n });\n },\n createWithOn(joinType, table, on) {\n return freeze({\n kind: 'JoinNode',\n joinType,\n table,\n on: OnNode.create(on),\n });\n },\n cloneWithOn(joinNode, operation) {\n return freeze({\n ...joinNode,\n on: joinNode.on\n ? OnNode.cloneWithOperation(joinNode.on, 'And', operation)\n : OnNode.create(operation),\n });\n },\n});\n","/// <reference types=\"./binary-operation-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const BinaryOperationNode = freeze({\n is(node) {\n return node.kind === 'BinaryOperationNode';\n },\n create(leftOperand, operator, rightOperand) {\n return freeze({\n kind: 'BinaryOperationNode',\n leftOperand,\n operator,\n rightOperand,\n });\n },\n});\n","/// <reference types=\"./operator-node.d.ts\" />\nimport { freeze, isString } from '../util/object-utils.js';\nexport const COMPARISON_OPERATORS = [\n '=',\n '==',\n '!=',\n '<>',\n '>',\n '>=',\n '<',\n '<=',\n 'in',\n 'not in',\n 'is',\n 'is not',\n 'like',\n 'not like',\n 'match',\n 'ilike',\n 'not ilike',\n '@>',\n '<@',\n '^@',\n '&&',\n '?',\n '?&',\n '?|',\n '!<',\n '!>',\n '<=>',\n '!~',\n '~',\n '~*',\n '!~*',\n '@@',\n '@@@',\n '!!',\n '<->',\n 'regexp',\n 'is distinct from',\n 'is not distinct from',\n];\nexport const ARITHMETIC_OPERATORS = [\n '+',\n '-',\n '*',\n '/',\n '%',\n '^',\n '&',\n '|',\n '#',\n '<<',\n '>>',\n];\nexport const JSON_OPERATORS = ['->', '->>'];\nexport const BINARY_OPERATORS = [\n ...COMPARISON_OPERATORS,\n ...ARITHMETIC_OPERATORS,\n '&&',\n '||',\n];\nexport const UNARY_FILTER_OPERATORS = ['exists', 'not exists'];\nexport const UNARY_OPERATORS = ['not', '-', ...UNARY_FILTER_OPERATORS];\nexport const OPERATORS = [\n ...BINARY_OPERATORS,\n ...JSON_OPERATORS,\n ...UNARY_OPERATORS,\n 'between',\n 'between symmetric',\n];\n/**\n * @internal\n */\nexport const OperatorNode = freeze({\n is(node) {\n return node.kind === 'OperatorNode';\n },\n create(operator) {\n return freeze({\n kind: 'OperatorNode',\n operator,\n });\n },\n});\nexport function isOperator(op) {\n return isString(op) && OPERATORS.includes(op);\n}\nexport function isBinaryOperator(op) {\n return isString(op) && BINARY_OPERATORS.includes(op);\n}\nexport function isComparisonOperator(op) {\n return isString(op) && COMPARISON_OPERATORS.includes(op);\n}\nexport function isArithmeticOperator(op) {\n return isString(op) && ARITHMETIC_OPERATORS.includes(op);\n}\nexport function isJSONOperator(op) {\n return isString(op) && JSON_OPERATORS.includes(op);\n}\n","/// <reference types=\"./column-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\nimport { IdentifierNode } from './identifier-node.js';\n/**\n * @internal\n */\nexport const ColumnNode = freeze({\n is(node) {\n return node.kind === 'ColumnNode';\n },\n create(column) {\n return freeze({\n kind: 'ColumnNode',\n column: IdentifierNode.create(column),\n });\n },\n});\n","/// <reference types=\"./select-all-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const SelectAllNode = freeze({\n is(node) {\n return node.kind === 'SelectAllNode';\n },\n create() {\n return freeze({\n kind: 'SelectAllNode',\n });\n },\n});\n","/// <reference types=\"./reference-node.d.ts\" />\nimport { SelectAllNode } from './select-all-node.js';\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const ReferenceNode = freeze({\n is(node) {\n return node.kind === 'ReferenceNode';\n },\n create(column, table) {\n return freeze({\n kind: 'ReferenceNode',\n table,\n column,\n });\n },\n createSelectAll(table) {\n return freeze({\n kind: 'ReferenceNode',\n table,\n column: SelectAllNode.create(),\n });\n },\n});\n","/// <reference types=\"./dynamic-reference-builder.d.ts\" />\nimport { isOperationNodeSource, } from '../operation-node/operation-node-source.js';\nimport { parseSimpleReferenceExpression } from '../parser/reference-parser.js';\nimport { isObject, isString } from '../util/object-utils.js';\nexport class DynamicReferenceBuilder {\n #dynamicReference;\n get dynamicReference() {\n return this.#dynamicReference;\n }\n /**\n * @private\n *\n * This needs to be here just so that the typings work. Without this\n * the generated .d.ts file contains no reference to the type param R\n * which causes this type to be equal to DynamicReferenceBuilder with\n * any R.\n */\n get refType() {\n return undefined;\n }\n constructor(reference) {\n this.#dynamicReference = reference;\n }\n toOperationNode() {\n return parseSimpleReferenceExpression(this.#dynamicReference);\n }\n}\nexport function isDynamicReferenceBuilder(obj) {\n return (isObject(obj) &&\n isOperationNodeSource(obj) &&\n isString(obj.dynamicReference));\n}\n","/// <reference types=\"./order-by-item-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const OrderByItemNode = freeze({\n is(node) {\n return node.kind === 'OrderByItemNode';\n },\n create(orderBy, direction) {\n return freeze({\n kind: 'OrderByItemNode',\n orderBy,\n direction,\n });\n },\n});\n","/// <reference types=\"./raw-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const RawNode = freeze({\n is(node) {\n return node.kind === 'RawNode';\n },\n create(sqlFragments, parameters) {\n return freeze({\n kind: 'RawNode',\n sqlFragments: freeze(sqlFragments),\n parameters: freeze(parameters),\n });\n },\n createWithSql(sql) {\n return RawNode.create([sql], []);\n },\n createWithChild(child) {\n return RawNode.create(['', ''], [child]);\n },\n createWithChildren(children) {\n return RawNode.create(new Array(children.length + 1).fill(''), children);\n },\n});\n","/// <reference types=\"./order-by-parser.d.ts\" />\nimport { isDynamicReferenceBuilder } from '../dynamic/dynamic-reference-builder.js';\nimport { OrderByItemNode } from '../operation-node/order-by-item-node.js';\nimport { RawNode } from '../operation-node/raw-node.js';\nimport { isExpressionOrFactory, parseExpression } from './expression-parser.js';\nimport { parseStringReference } from './reference-parser.js';\nexport function isOrderByDirection(thing) {\n return thing === 'asc' || thing === 'desc';\n}\nexport function parseOrderBy(args) {\n if (args.length === 2) {\n return [parseOrderByItem(args[0], args[1])];\n }\n if (args.length === 1) {\n const [orderBy] = args;\n if (Array.isArray(orderBy)) {\n return orderBy.map((item) => parseOrderByItem(item));\n }\n return [parseOrderByItem(orderBy)];\n }\n throw new Error(`Invalid number of arguments at order by! expected 1-2, received ${args.length}`);\n}\nexport function parseOrderByItem(ref, direction) {\n const parsedRef = parseOrderByExpression(ref);\n if (OrderByItemNode.is(parsedRef)) {\n if (direction) {\n throw new Error('Cannot specify direction twice!');\n }\n return parsedRef;\n }\n return OrderByItemNode.create(parsedRef, parseOrderByDirectionExpression(direction));\n}\nfunction parseOrderByExpression(expr) {\n if (isExpressionOrFactory(expr)) {\n return parseExpression(expr);\n }\n if (isDynamicReferenceBuilder(expr)) {\n return expr.toOperationNode();\n }\n const [ref, direction] = expr.split(' ');\n if (direction) {\n if (!isOrderByDirection(direction)) {\n throw new Error(`Invalid order by direction: ${direction}`);\n }\n return OrderByItemNode.create(parseStringReference(ref), parseOrderByDirectionExpression(direction));\n }\n return parseStringReference(expr);\n}\nfunction parseOrderByDirectionExpression(expr) {\n if (!expr) {\n return undefined;\n }\n if (expr === 'asc' || expr === 'desc') {\n return RawNode.createWithSql(expr);\n }\n return expr.toOperationNode();\n}\n","/// <reference types=\"./json-reference-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const JSONReferenceNode = freeze({\n is(node) {\n return node.kind === 'JSONReferenceNode';\n },\n create(reference, traversal) {\n return freeze({\n kind: 'JSONReferenceNode',\n reference,\n traversal,\n });\n },\n cloneWithTraversal(node, traversal) {\n return freeze({\n ...node,\n traversal,\n });\n },\n});\n","/// <reference types=\"./json-operator-chain-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const JSONOperatorChainNode = freeze({\n is(node) {\n return node.kind === 'JSONOperatorChainNode';\n },\n create(operator) {\n return freeze({\n kind: 'JSONOperatorChainNode',\n operator,\n values: freeze([]),\n });\n },\n cloneWithValue(node, value) {\n return freeze({\n ...node,\n values: freeze([...node.values, value]),\n });\n },\n});\n","/// <reference types=\"./json-path-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const JSONPathNode = freeze({\n is(node) {\n return node.kind === 'JSONPathNode';\n },\n create(inOperator) {\n return freeze({\n kind: 'JSONPathNode',\n inOperator,\n pathLegs: freeze([]),\n });\n },\n cloneWithLeg(jsonPathNode, pathLeg) {\n return freeze({\n ...jsonPathNode,\n pathLegs: freeze([...jsonPathNode.pathLegs, pathLeg]),\n });\n },\n});\n","/// <reference types=\"./reference-parser.d.ts\" />\nimport { AliasNode } from '../operation-node/alias-node.js';\nimport { ColumnNode } from '../operation-node/column-node.js';\nimport { ReferenceNode } from '../operation-node/reference-node.js';\nimport { TableNode } from '../operation-node/table-node.js';\nimport { isReadonlyArray, isString } from '../util/object-utils.js';\nimport { parseExpression, isExpressionOrFactory, } from './expression-parser.js';\nimport { IdentifierNode } from '../operation-node/identifier-node.js';\nimport { isOrderByDirection, parseOrderBy, } from './order-by-parser.js';\nimport { OperatorNode, isJSONOperator, } from '../operation-node/operator-node.js';\nimport { JSONReferenceNode } from '../operation-node/json-reference-node.js';\nimport { JSONOperatorChainNode } from '../operation-node/json-operator-chain-node.js';\nimport { JSONPathNode } from '../operation-node/json-path-node.js';\nexport function parseSimpleReferenceExpression(exp) {\n if (isString(exp)) {\n return parseStringReference(exp);\n }\n return exp.toOperationNode();\n}\nexport function parseReferenceExpressionOrList(arg) {\n if (isReadonlyArray(arg)) {\n return arg.map((it) => parseReferenceExpression(it));\n }\n else {\n return [parseReferenceExpression(arg)];\n }\n}\nexport function parseReferenceExpression(exp) {\n if (isExpressionOrFactory(exp)) {\n return parseExpression(exp);\n }\n return parseSimpleReferenceExpression(exp);\n}\nexport function parseJSONReference(ref, op) {\n const referenceNode = parseStringReference(ref);\n if (isJSONOperator(op)) {\n return JSONReferenceNode.create(referenceNode, JSONOperatorChainNode.create(OperatorNode.create(op)));\n }\n const opWithoutLastChar = op.slice(0, -1);\n if (isJSONOperator(opWithoutLastChar)) {\n return JSONReferenceNode.create(referenceNode, JSONPathNode.create(OperatorNode.create(opWithoutLastChar)));\n }\n throw new Error(`Invalid JSON operator: ${op}`);\n}\nexport function parseStringReference(ref) {\n const COLUMN_SEPARATOR = '.';\n if (!ref.includes(COLUMN_SEPARATOR)) {\n return ReferenceNode.create(ColumnNode.create(ref));\n }\n const parts = ref.split(COLUMN_SEPARATOR).map(trim);\n if (parts.length === 3) {\n return parseStringReferenceWithTableAndSchema(parts);\n }\n if (parts.length === 2) {\n return parseStringReferenceWithTable(parts);\n }\n throw new Error(`invalid column reference ${ref}`);\n}\nexport function parseAliasedStringReference(ref) {\n const ALIAS_SEPARATOR = ' as ';\n if (ref.includes(ALIAS_SEPARATOR)) {\n const [columnRef, alias] = ref.split(ALIAS_SEPARATOR).map(trim);\n return AliasNode.create(parseStringReference(columnRef), IdentifierNode.create(alias));\n }\n else {\n return parseStringReference(ref);\n }\n}\nexport function parseColumnName(column) {\n return ColumnNode.create(column);\n}\nexport function parseOrderedColumnName(column) {\n const ORDER_SEPARATOR = ' ';\n if (column.includes(ORDER_SEPARATOR)) {\n const [columnName, order] = column.split(ORDER_SEPARATOR).map(trim);\n if (!isOrderByDirection(order)) {\n throw new Error(`invalid order direction \"${order}\" next to \"${columnName}\"`);\n }\n return parseOrderBy([columnName, order])[0];\n }\n else {\n return parseColumnName(column);\n }\n}\nfunction parseStringReferenceWithTableAndSchema(parts) {\n const [schema, table, column] = parts;\n return ReferenceNode.create(ColumnNode.create(column), TableNode.createWithSchema(schema, table));\n}\nfunction parseStringReferenceWithTable(parts) {\n const [table, column] = parts;\n return ReferenceNode.create(ColumnNode.create(column), TableNode.create(table));\n}\nfunction trim(str) {\n return str.trim();\n}\n","/// <reference types=\"./primitive-value-list-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const PrimitiveValueListNode = freeze({\n is(node) {\n return node.kind === 'PrimitiveValueListNode';\n },\n create(values) {\n return freeze({\n kind: 'PrimitiveValueListNode',\n values: freeze([...values]),\n });\n },\n});\n","/// <reference types=\"./value-list-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const ValueListNode = freeze({\n is(node) {\n return node.kind === 'ValueListNode';\n },\n create(values) {\n return freeze({\n kind: 'ValueListNode',\n values: freeze(values),\n });\n },\n});\n","/// <reference types=\"./value-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const ValueNode = freeze({\n is(node) {\n return node.kind === 'ValueNode';\n },\n create(value) {\n return freeze({\n kind: 'ValueNode',\n value,\n });\n },\n createImmediate(value) {\n return freeze({\n kind: 'ValueNode',\n value,\n immediate: true,\n });\n },\n});\n","/// <reference types=\"./value-parser.d.ts\" />\nimport { PrimitiveValueListNode } from '../operation-node/primitive-value-list-node.js';\nimport { ValueListNode } from '../operation-node/value-list-node.js';\nimport { ValueNode } from '../operation-node/value-node.js';\nimport { isBoolean, isNull, isNumber, isReadonlyArray, } from '../util/object-utils.js';\nimport { parseExpression, isExpressionOrFactory, } from './expression-parser.js';\nexport function parseValueExpressionOrList(arg) {\n if (isReadonlyArray(arg)) {\n return parseValueExpressionList(arg);\n }\n return parseValueExpression(arg);\n}\nexport function parseValueExpression(exp) {\n if (isExpressionOrFactory(exp)) {\n return parseExpression(exp);\n }\n return ValueNode.create(exp);\n}\nexport function isSafeImmediateValue(value) {\n return isNumber(value) || isBoolean(value) || isNull(value);\n}\nexport function parseSafeImmediateValue(value) {\n if (!isSafeImmediateValue(value)) {\n throw new Error(`unsafe immediate value ${JSON.stringify(value)}`);\n }\n return ValueNode.createImmediate(value);\n}\nfunction parseValueExpressionList(arg) {\n if (arg.some(isExpressionOrFactory)) {\n return ValueListNode.create(arg.map((it) => parseValueExpression(it)));\n }\n return PrimitiveValueListNode.create(arg);\n}\n","/// <reference types=\"./parens-node.d.ts\" />\nimport { freeze } from '../util/object-utils.js';\n/**\n * @internal\n */\nexport const ParensNode = freeze({\n is(node) {\n return node.kind === 'ParensNode';\n },\n create(node) {\n return freeze({\n kind: 'ParensNode',\n node,\n });\n },\n});\n","/// <reference types=\"./binary-operation-parser.d.ts\" />\nimport { BinaryOperationNode } from '../operation-node/binary-operation-node.js';\nimport { isBoolean, isNull, isString, isUndefined, } from '../util/object-utils.js';\nimport { isOperationNodeSource, } from '../operation-node/operation-node-source.js';\nimport { OperatorNode, OPERATORS, } from '../operation-node/operator-node.js';\nimport { parseReferenceExpression, } from './reference-parser.js';\nimport { parseValueExpression, parseValueExpressionOrList, } from './value-parser.js';\nimport { Va