@drzl/validation-core 2.0.0 → 3.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +39 -4
- package/dist/index.d.cts +44 -2
- package/dist/index.d.ts +44 -2
- package/dist/index.js +38 -4
- package/package.json +2 -2
package/dist/index.cjs
CHANGED
|
@@ -100187,6 +100187,7 @@ __export(index_exports2, {
|
|
|
100187
100187
|
moduleSpecifier: () => moduleSpecifier,
|
|
100188
100188
|
pascalCase: () => pascalCase,
|
|
100189
100189
|
resolveAffix: () => resolveAffix,
|
|
100190
|
+
resolveConfiguredImport: () => resolveConfiguredImport,
|
|
100190
100191
|
schemaName: () => schemaName,
|
|
100191
100192
|
selectColumns: () => selectColumns,
|
|
100192
100193
|
typeName: () => typeName,
|
|
@@ -100196,6 +100197,8 @@ __export(index_exports2, {
|
|
|
100196
100197
|
module.exports = __toCommonJS(index_exports2);
|
|
100197
100198
|
|
|
100198
100199
|
// src/files.ts
|
|
100200
|
+
var import_node_fs = __toESM(require("fs"), 1);
|
|
100201
|
+
var import_node_path = __toESM(require("path"), 1);
|
|
100199
100202
|
var IMPORT_EXTENSIONS = ["js", "none", "ts"];
|
|
100200
100203
|
var DEFAULT_IMPORT_EXTENSION = "js";
|
|
100201
100204
|
var TS_EXTENSIONS = [
|
|
@@ -100219,6 +100222,38 @@ function importSpecifier(relativePath, importExtension = DEFAULT_IMPORT_EXTENSIO
|
|
|
100219
100222
|
function moduleSpecifier(tsName, fileSuffix, importExtension = DEFAULT_IMPORT_EXTENSION) {
|
|
100220
100223
|
return importSpecifier(`./${moduleFileName(tsName, fileSuffix)}`, importExtension);
|
|
100221
100224
|
}
|
|
100225
|
+
function resolveConfiguredImport(configured, outDirAbs, cwd, importExtension = DEFAULT_IMPORT_EXTENSION) {
|
|
100226
|
+
if (isPackageSpecifier(configured)) return configured;
|
|
100227
|
+
const targetAbs = import_node_path.default.isAbsolute(configured) ? configured : import_node_path.default.resolve(configured.startsWith(".") ? outDirAbs : cwd, configured);
|
|
100228
|
+
const withIndex = pointsAtDirectory(targetAbs) ? `${configured}/index` : configured;
|
|
100229
|
+
if (configured.startsWith(".")) {
|
|
100230
|
+
return importSpecifier(withTsExtension(withIndex), importExtension);
|
|
100231
|
+
}
|
|
100232
|
+
const resolved = pointsAtDirectory(targetAbs) ? import_node_path.default.join(targetAbs, "index") : targetAbs;
|
|
100233
|
+
const rel = import_node_path.default.relative(outDirAbs, resolved).split(import_node_path.default.sep).join("/");
|
|
100234
|
+
const prefixed = !rel ? "." : rel.startsWith(".") ? rel : `./${rel}`;
|
|
100235
|
+
return importSpecifier(withTsExtension(prefixed), importExtension);
|
|
100236
|
+
}
|
|
100237
|
+
function isPackageSpecifier(p5) {
|
|
100238
|
+
if (p5.startsWith(".") || import_node_path.default.isAbsolute(p5)) return false;
|
|
100239
|
+
if (p5.startsWith("@") || p5.includes(":")) return true;
|
|
100240
|
+
return !p5.includes("/");
|
|
100241
|
+
}
|
|
100242
|
+
function pointsAtDirectory(absPath) {
|
|
100243
|
+
try {
|
|
100244
|
+
return import_node_fs.default.statSync(absPath).isDirectory();
|
|
100245
|
+
} catch {
|
|
100246
|
+
for (const ext of [".ts", ".tsx", ".mts", ".cts", ".js", ".mjs", ".cjs"]) {
|
|
100247
|
+
if (import_node_fs.default.existsSync(`${absPath}${ext}`)) return false;
|
|
100248
|
+
}
|
|
100249
|
+
return !/\.[a-z]+$/i.test(import_node_path.default.basename(absPath));
|
|
100250
|
+
}
|
|
100251
|
+
}
|
|
100252
|
+
function withTsExtension(p5) {
|
|
100253
|
+
if (/\.(ts|tsx|mts|cts)$/.test(p5)) return p5;
|
|
100254
|
+
if (/\.(js|mjs|cjs)$/.test(p5)) return p5.replace(/\.(js|mjs|cjs)$/, ".ts");
|
|
100255
|
+
return `${p5}.ts`;
|
|
100256
|
+
}
|
|
100222
100257
|
|
|
100223
100258
|
// src/naming.ts
|
|
100224
100259
|
var NAME_MODES = ["insert", "update", "select"];
|
|
@@ -100327,12 +100362,11 @@ function validateAffix(affix, schemaSuffix) {
|
|
|
100327
100362
|
}
|
|
100328
100363
|
|
|
100329
100364
|
// src/index.ts
|
|
100330
|
-
function isGeneratedColumn(c5,
|
|
100331
|
-
return c5.isGenerated
|
|
100365
|
+
function isGeneratedColumn(c5, _primaryKeyColumns = []) {
|
|
100366
|
+
return c5.isGenerated;
|
|
100332
100367
|
}
|
|
100333
100368
|
function insertColumns(table) {
|
|
100334
|
-
|
|
100335
|
-
return table.columns.filter((c5) => !isGeneratedColumn(c5, pkCols));
|
|
100369
|
+
return table.columns.filter((c5) => !isGeneratedColumn(c5));
|
|
100336
100370
|
}
|
|
100337
100371
|
function updateColumns(table) {
|
|
100338
100372
|
const pkCols = table.primaryKey?.columns ?? [];
|
|
@@ -100384,6 +100418,7 @@ async function formatCode(code, filePath, fmt) {
|
|
|
100384
100418
|
moduleSpecifier,
|
|
100385
100419
|
pascalCase,
|
|
100386
100420
|
resolveAffix,
|
|
100421
|
+
resolveConfiguredImport,
|
|
100387
100422
|
schemaName,
|
|
100388
100423
|
selectColumns,
|
|
100389
100424
|
typeName,
|
package/dist/index.d.cts
CHANGED
|
@@ -52,6 +52,34 @@ declare function importSpecifier(relativePath: string, importExtension?: ImportE
|
|
|
52
52
|
* `./users.zod.js`.
|
|
53
53
|
*/
|
|
54
54
|
declare function moduleSpecifier(tsName: string, fileSuffix: string, importExtension?: ImportExtension): string;
|
|
55
|
+
/**
|
|
56
|
+
* Turn a configured module path into a specifier the generated file can actually import.
|
|
57
|
+
*
|
|
58
|
+
* Options like `validation.importPath`, `dbImportPath` and `schemaImportPath` get written as
|
|
59
|
+
* project-relative paths, `src/validators/zod`, because that is how the rest of the config
|
|
60
|
+
* names directories. Emitted verbatim that is a *bare* specifier: Node and tsc look for a
|
|
61
|
+
* package of that name in node_modules and never consider the local file. The config in the
|
|
62
|
+
* getting-started guide produced three such imports, none of which resolved.
|
|
63
|
+
*
|
|
64
|
+
* Two questions have to be answered, and neither can be guessed from the string alone.
|
|
65
|
+
*
|
|
66
|
+
* **Package or path?** `zod` and `@acme/schemas` are package names and pass through untouched.
|
|
67
|
+
* A path containing a separator, or starting with `.`, is a path.
|
|
68
|
+
*
|
|
69
|
+
* **File or directory?** `src/db/connection` is usually a file and `src/validators/zod` a
|
|
70
|
+
* directory holding a barrel, and they look identical. So the filesystem is asked. Where the
|
|
71
|
+
* target does not exist yet, which happens when this generator runs before the one that writes
|
|
72
|
+
* it, an extensionless path is taken to be a directory, since these options name directories by
|
|
73
|
+
* convention and the one path that can be missing is a generated barrel.
|
|
74
|
+
*
|
|
75
|
+
* A path already relative keeps its own spelling and only has its extension corrected, so
|
|
76
|
+
* anyone who followed the older guidance and wrote `../validators/zod/index.js` is unaffected.
|
|
77
|
+
*
|
|
78
|
+
* @param configured what the user put in the config
|
|
79
|
+
* @param outDirAbs absolute directory the importing file is written to
|
|
80
|
+
* @param cwd project root a non-relative path is resolved against
|
|
81
|
+
*/
|
|
82
|
+
declare function resolveConfiguredImport(configured: string, outDirAbs: string, cwd: string, importExtension?: ImportExtension): string;
|
|
55
83
|
|
|
56
84
|
/**
|
|
57
85
|
* One place that decides what a generated identifier is called.
|
|
@@ -195,10 +223,24 @@ interface ValidationRenderer<TOptions extends ValidationGenerateOptions = Valida
|
|
|
195
223
|
renderIndex?(analysis: Analysis, opts?: TOptions): string;
|
|
196
224
|
generate(opts: TOptions): Promise<string[]>;
|
|
197
225
|
}
|
|
198
|
-
|
|
226
|
+
/**
|
|
227
|
+
* Whether the database generates this column's value, so it cannot be written.
|
|
228
|
+
*
|
|
229
|
+
* `primaryKeyColumns` is accepted for backwards compatibility and no longer consulted. It used
|
|
230
|
+
* to make every primary key count as generated, which dropped it from the insert schema whether
|
|
231
|
+
* or not the database supplied it. Right for a MySQL autoincrement column; wrong for a Postgres
|
|
232
|
+
* `integer('id').primaryKey()`, which Postgres does not generate, and for any natural key such
|
|
233
|
+
* as `text('slug').primaryKey()`. Those inserts became impossible to express: the required
|
|
234
|
+
* column was simply absent, with no way to provide it.
|
|
235
|
+
*
|
|
236
|
+
* Being a key says nothing about who supplies the value. `isGenerated` marks a column that
|
|
237
|
+
* cannot be written; `hasDefault` marks one that need not be, and those stay in the schema as
|
|
238
|
+
* optional.
|
|
239
|
+
*/
|
|
240
|
+
declare function isGeneratedColumn(c: Column, _primaryKeyColumns?: string[]): boolean;
|
|
199
241
|
declare function insertColumns(table: Table): Column[];
|
|
200
242
|
declare function updateColumns(table: Table): Column[];
|
|
201
243
|
declare function selectColumns(table: Table): Column[];
|
|
202
244
|
declare function formatCode(code: string, filePath: string, fmt?: FormatOptions): Promise<any>;
|
|
203
245
|
|
|
204
|
-
export { AFFIX_PROBE_TABLE, type AffixIssue, type AffixOptions, type AffixValue, DEFAULT_IMPORT_EXTENSION, DEFAULT_MODE_PREFIX, DEFAULT_SCHEMA_SUFFIX, DEFAULT_TYPE_SUFFIX, type FormatOptions, IMPORT_EXTENSIONS, type ImportExtension, NAME_MODES, type NameMode, type ResolvedAffix, type Table, type TableCase, type ValidationGenerateOptions, type ValidationLibrary, type ValidationRenderer, applyTableCase, formatCode, importSpecifier, insertColumns, isGeneratedColumn, moduleFileName, moduleSpecifier, pascalCase, resolveAffix, schemaName, selectColumns, typeName, updateColumns, validateAffix };
|
|
246
|
+
export { AFFIX_PROBE_TABLE, type AffixIssue, type AffixOptions, type AffixValue, DEFAULT_IMPORT_EXTENSION, DEFAULT_MODE_PREFIX, DEFAULT_SCHEMA_SUFFIX, DEFAULT_TYPE_SUFFIX, type FormatOptions, IMPORT_EXTENSIONS, type ImportExtension, NAME_MODES, type NameMode, type ResolvedAffix, type Table, type TableCase, type ValidationGenerateOptions, type ValidationLibrary, type ValidationRenderer, applyTableCase, formatCode, importSpecifier, insertColumns, isGeneratedColumn, moduleFileName, moduleSpecifier, pascalCase, resolveAffix, resolveConfiguredImport, schemaName, selectColumns, typeName, updateColumns, validateAffix };
|
package/dist/index.d.ts
CHANGED
|
@@ -52,6 +52,34 @@ declare function importSpecifier(relativePath: string, importExtension?: ImportE
|
|
|
52
52
|
* `./users.zod.js`.
|
|
53
53
|
*/
|
|
54
54
|
declare function moduleSpecifier(tsName: string, fileSuffix: string, importExtension?: ImportExtension): string;
|
|
55
|
+
/**
|
|
56
|
+
* Turn a configured module path into a specifier the generated file can actually import.
|
|
57
|
+
*
|
|
58
|
+
* Options like `validation.importPath`, `dbImportPath` and `schemaImportPath` get written as
|
|
59
|
+
* project-relative paths, `src/validators/zod`, because that is how the rest of the config
|
|
60
|
+
* names directories. Emitted verbatim that is a *bare* specifier: Node and tsc look for a
|
|
61
|
+
* package of that name in node_modules and never consider the local file. The config in the
|
|
62
|
+
* getting-started guide produced three such imports, none of which resolved.
|
|
63
|
+
*
|
|
64
|
+
* Two questions have to be answered, and neither can be guessed from the string alone.
|
|
65
|
+
*
|
|
66
|
+
* **Package or path?** `zod` and `@acme/schemas` are package names and pass through untouched.
|
|
67
|
+
* A path containing a separator, or starting with `.`, is a path.
|
|
68
|
+
*
|
|
69
|
+
* **File or directory?** `src/db/connection` is usually a file and `src/validators/zod` a
|
|
70
|
+
* directory holding a barrel, and they look identical. So the filesystem is asked. Where the
|
|
71
|
+
* target does not exist yet, which happens when this generator runs before the one that writes
|
|
72
|
+
* it, an extensionless path is taken to be a directory, since these options name directories by
|
|
73
|
+
* convention and the one path that can be missing is a generated barrel.
|
|
74
|
+
*
|
|
75
|
+
* A path already relative keeps its own spelling and only has its extension corrected, so
|
|
76
|
+
* anyone who followed the older guidance and wrote `../validators/zod/index.js` is unaffected.
|
|
77
|
+
*
|
|
78
|
+
* @param configured what the user put in the config
|
|
79
|
+
* @param outDirAbs absolute directory the importing file is written to
|
|
80
|
+
* @param cwd project root a non-relative path is resolved against
|
|
81
|
+
*/
|
|
82
|
+
declare function resolveConfiguredImport(configured: string, outDirAbs: string, cwd: string, importExtension?: ImportExtension): string;
|
|
55
83
|
|
|
56
84
|
/**
|
|
57
85
|
* One place that decides what a generated identifier is called.
|
|
@@ -195,10 +223,24 @@ interface ValidationRenderer<TOptions extends ValidationGenerateOptions = Valida
|
|
|
195
223
|
renderIndex?(analysis: Analysis, opts?: TOptions): string;
|
|
196
224
|
generate(opts: TOptions): Promise<string[]>;
|
|
197
225
|
}
|
|
198
|
-
|
|
226
|
+
/**
|
|
227
|
+
* Whether the database generates this column's value, so it cannot be written.
|
|
228
|
+
*
|
|
229
|
+
* `primaryKeyColumns` is accepted for backwards compatibility and no longer consulted. It used
|
|
230
|
+
* to make every primary key count as generated, which dropped it from the insert schema whether
|
|
231
|
+
* or not the database supplied it. Right for a MySQL autoincrement column; wrong for a Postgres
|
|
232
|
+
* `integer('id').primaryKey()`, which Postgres does not generate, and for any natural key such
|
|
233
|
+
* as `text('slug').primaryKey()`. Those inserts became impossible to express: the required
|
|
234
|
+
* column was simply absent, with no way to provide it.
|
|
235
|
+
*
|
|
236
|
+
* Being a key says nothing about who supplies the value. `isGenerated` marks a column that
|
|
237
|
+
* cannot be written; `hasDefault` marks one that need not be, and those stay in the schema as
|
|
238
|
+
* optional.
|
|
239
|
+
*/
|
|
240
|
+
declare function isGeneratedColumn(c: Column, _primaryKeyColumns?: string[]): boolean;
|
|
199
241
|
declare function insertColumns(table: Table): Column[];
|
|
200
242
|
declare function updateColumns(table: Table): Column[];
|
|
201
243
|
declare function selectColumns(table: Table): Column[];
|
|
202
244
|
declare function formatCode(code: string, filePath: string, fmt?: FormatOptions): Promise<any>;
|
|
203
245
|
|
|
204
|
-
export { AFFIX_PROBE_TABLE, type AffixIssue, type AffixOptions, type AffixValue, DEFAULT_IMPORT_EXTENSION, DEFAULT_MODE_PREFIX, DEFAULT_SCHEMA_SUFFIX, DEFAULT_TYPE_SUFFIX, type FormatOptions, IMPORT_EXTENSIONS, type ImportExtension, NAME_MODES, type NameMode, type ResolvedAffix, type Table, type TableCase, type ValidationGenerateOptions, type ValidationLibrary, type ValidationRenderer, applyTableCase, formatCode, importSpecifier, insertColumns, isGeneratedColumn, moduleFileName, moduleSpecifier, pascalCase, resolveAffix, schemaName, selectColumns, typeName, updateColumns, validateAffix };
|
|
246
|
+
export { AFFIX_PROBE_TABLE, type AffixIssue, type AffixOptions, type AffixValue, DEFAULT_IMPORT_EXTENSION, DEFAULT_MODE_PREFIX, DEFAULT_SCHEMA_SUFFIX, DEFAULT_TYPE_SUFFIX, type FormatOptions, IMPORT_EXTENSIONS, type ImportExtension, NAME_MODES, type NameMode, type ResolvedAffix, type Table, type TableCase, type ValidationGenerateOptions, type ValidationLibrary, type ValidationRenderer, applyTableCase, formatCode, importSpecifier, insertColumns, isGeneratedColumn, moduleFileName, moduleSpecifier, pascalCase, resolveAffix, resolveConfiguredImport, schemaName, selectColumns, typeName, updateColumns, validateAffix };
|
package/dist/index.js
CHANGED
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
import "./chunk-MKBO26DX.js";
|
|
2
2
|
|
|
3
3
|
// src/files.ts
|
|
4
|
+
import nodeFs from "fs";
|
|
5
|
+
import nodePath from "path";
|
|
4
6
|
var IMPORT_EXTENSIONS = ["js", "none", "ts"];
|
|
5
7
|
var DEFAULT_IMPORT_EXTENSION = "js";
|
|
6
8
|
var TS_EXTENSIONS = [
|
|
@@ -24,6 +26,38 @@ function importSpecifier(relativePath, importExtension = DEFAULT_IMPORT_EXTENSIO
|
|
|
24
26
|
function moduleSpecifier(tsName, fileSuffix, importExtension = DEFAULT_IMPORT_EXTENSION) {
|
|
25
27
|
return importSpecifier(`./${moduleFileName(tsName, fileSuffix)}`, importExtension);
|
|
26
28
|
}
|
|
29
|
+
function resolveConfiguredImport(configured, outDirAbs, cwd, importExtension = DEFAULT_IMPORT_EXTENSION) {
|
|
30
|
+
if (isPackageSpecifier(configured)) return configured;
|
|
31
|
+
const targetAbs = nodePath.isAbsolute(configured) ? configured : nodePath.resolve(configured.startsWith(".") ? outDirAbs : cwd, configured);
|
|
32
|
+
const withIndex = pointsAtDirectory(targetAbs) ? `${configured}/index` : configured;
|
|
33
|
+
if (configured.startsWith(".")) {
|
|
34
|
+
return importSpecifier(withTsExtension(withIndex), importExtension);
|
|
35
|
+
}
|
|
36
|
+
const resolved = pointsAtDirectory(targetAbs) ? nodePath.join(targetAbs, "index") : targetAbs;
|
|
37
|
+
const rel = nodePath.relative(outDirAbs, resolved).split(nodePath.sep).join("/");
|
|
38
|
+
const prefixed = !rel ? "." : rel.startsWith(".") ? rel : `./${rel}`;
|
|
39
|
+
return importSpecifier(withTsExtension(prefixed), importExtension);
|
|
40
|
+
}
|
|
41
|
+
function isPackageSpecifier(p) {
|
|
42
|
+
if (p.startsWith(".") || nodePath.isAbsolute(p)) return false;
|
|
43
|
+
if (p.startsWith("@") || p.includes(":")) return true;
|
|
44
|
+
return !p.includes("/");
|
|
45
|
+
}
|
|
46
|
+
function pointsAtDirectory(absPath) {
|
|
47
|
+
try {
|
|
48
|
+
return nodeFs.statSync(absPath).isDirectory();
|
|
49
|
+
} catch {
|
|
50
|
+
for (const ext of [".ts", ".tsx", ".mts", ".cts", ".js", ".mjs", ".cjs"]) {
|
|
51
|
+
if (nodeFs.existsSync(`${absPath}${ext}`)) return false;
|
|
52
|
+
}
|
|
53
|
+
return !/\.[a-z]+$/i.test(nodePath.basename(absPath));
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
function withTsExtension(p) {
|
|
57
|
+
if (/\.(ts|tsx|mts|cts)$/.test(p)) return p;
|
|
58
|
+
if (/\.(js|mjs|cjs)$/.test(p)) return p.replace(/\.(js|mjs|cjs)$/, ".ts");
|
|
59
|
+
return `${p}.ts`;
|
|
60
|
+
}
|
|
27
61
|
|
|
28
62
|
// src/naming.ts
|
|
29
63
|
var NAME_MODES = ["insert", "update", "select"];
|
|
@@ -132,12 +166,11 @@ function validateAffix(affix, schemaSuffix) {
|
|
|
132
166
|
}
|
|
133
167
|
|
|
134
168
|
// src/index.ts
|
|
135
|
-
function isGeneratedColumn(c,
|
|
136
|
-
return c.isGenerated
|
|
169
|
+
function isGeneratedColumn(c, _primaryKeyColumns = []) {
|
|
170
|
+
return c.isGenerated;
|
|
137
171
|
}
|
|
138
172
|
function insertColumns(table) {
|
|
139
|
-
|
|
140
|
-
return table.columns.filter((c) => !isGeneratedColumn(c, pkCols));
|
|
173
|
+
return table.columns.filter((c) => !isGeneratedColumn(c));
|
|
141
174
|
}
|
|
142
175
|
function updateColumns(table) {
|
|
143
176
|
const pkCols = table.primaryKey?.columns ?? [];
|
|
@@ -188,6 +221,7 @@ export {
|
|
|
188
221
|
moduleSpecifier,
|
|
189
222
|
pascalCase,
|
|
190
223
|
resolveAffix,
|
|
224
|
+
resolveConfiguredImport,
|
|
191
225
|
schemaName,
|
|
192
226
|
selectColumns,
|
|
193
227
|
typeName,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@drzl/validation-core",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "3.0.0",
|
|
4
4
|
"private": false,
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"type": "module",
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
],
|
|
12
12
|
"sideEffects": false,
|
|
13
13
|
"dependencies": {
|
|
14
|
-
"@drzl/analyzer": "^1.
|
|
14
|
+
"@drzl/analyzer": "^1.5.0"
|
|
15
15
|
},
|
|
16
16
|
"devDependencies": {
|
|
17
17
|
"tsup": "^8.5.0",
|