@famgia/omnify-core 0.0.116 → 0.0.118
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 +156 -1
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +156 -1
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -887,6 +887,13 @@ async function loadSchemas(directoryPath, options = {}) {
|
|
|
887
887
|
}
|
|
888
888
|
const target = schemas[targetName];
|
|
889
889
|
if (!target) {
|
|
890
|
+
if (partial.name === targetName) {
|
|
891
|
+
schemas[partial.name] = {
|
|
892
|
+
...partial,
|
|
893
|
+
kind: "object"
|
|
894
|
+
};
|
|
895
|
+
continue;
|
|
896
|
+
}
|
|
890
897
|
console.warn(`Partial schema '${partial.name}' targets unknown schema '${targetName}', skipping`);
|
|
891
898
|
continue;
|
|
892
899
|
}
|
|
@@ -1327,11 +1334,45 @@ var textTypes = [
|
|
|
1327
1334
|
];
|
|
1328
1335
|
|
|
1329
1336
|
// src/validation/types/numeric.ts
|
|
1337
|
+
var INTEGER_DB_KEYWORDS = [
|
|
1338
|
+
"AUTO_INCREMENT",
|
|
1339
|
+
"IDENTITY",
|
|
1340
|
+
"SERIAL",
|
|
1341
|
+
"BIGSERIAL",
|
|
1342
|
+
"SMALLSERIAL",
|
|
1343
|
+
"NEXTVAL",
|
|
1344
|
+
"RAND()",
|
|
1345
|
+
"RANDOM()",
|
|
1346
|
+
"FLOOR()",
|
|
1347
|
+
"CEIL()",
|
|
1348
|
+
"ROUND()",
|
|
1349
|
+
"ABS()"
|
|
1350
|
+
];
|
|
1351
|
+
var FLOAT_DB_KEYWORDS = [
|
|
1352
|
+
"RAND()",
|
|
1353
|
+
"RANDOM()",
|
|
1354
|
+
"PI()",
|
|
1355
|
+
"FLOOR()",
|
|
1356
|
+
"CEIL()",
|
|
1357
|
+
"ROUND()",
|
|
1358
|
+
"ABS()",
|
|
1359
|
+
"SQRT()"
|
|
1360
|
+
];
|
|
1361
|
+
function isDbKeyword(value, keywords) {
|
|
1362
|
+
const upperValue = value.toUpperCase().trim();
|
|
1363
|
+
return keywords.some((keyword) => upperValue === keyword.toUpperCase());
|
|
1364
|
+
}
|
|
1330
1365
|
function validateIntegerDefault(value) {
|
|
1331
1366
|
if (value === void 0 || value === null || value === "") {
|
|
1332
1367
|
return { valid: true };
|
|
1333
1368
|
}
|
|
1334
1369
|
const strValue = String(value);
|
|
1370
|
+
if (isDbKeyword(strValue, INTEGER_DB_KEYWORDS)) {
|
|
1371
|
+
return {
|
|
1372
|
+
valid: false,
|
|
1373
|
+
error: `Database function '${strValue}' is not allowed as default. Use a static integer value instead.`
|
|
1374
|
+
};
|
|
1375
|
+
}
|
|
1335
1376
|
if (!/^-?\d+$/.test(strValue)) {
|
|
1336
1377
|
return { valid: false, error: "Must be an integer" };
|
|
1337
1378
|
}
|
|
@@ -1342,6 +1383,12 @@ function validateNumberDefault(value) {
|
|
|
1342
1383
|
return { valid: true };
|
|
1343
1384
|
}
|
|
1344
1385
|
const strValue = String(value);
|
|
1386
|
+
if (isDbKeyword(strValue, FLOAT_DB_KEYWORDS)) {
|
|
1387
|
+
return {
|
|
1388
|
+
valid: false,
|
|
1389
|
+
error: `Database function '${strValue}' is not allowed as default. Use a static number value instead.`
|
|
1390
|
+
};
|
|
1391
|
+
}
|
|
1345
1392
|
if (!/^-?\d+(\.\d+)?$/.test(strValue)) {
|
|
1346
1393
|
return { valid: false, error: "Must be a number" };
|
|
1347
1394
|
}
|
|
@@ -1452,11 +1499,50 @@ var numericTypes = [
|
|
|
1452
1499
|
];
|
|
1453
1500
|
|
|
1454
1501
|
// src/validation/types/temporal.ts
|
|
1502
|
+
var TIMESTAMP_DB_KEYWORDS = [
|
|
1503
|
+
"CURRENT_TIMESTAMP",
|
|
1504
|
+
"NOW()",
|
|
1505
|
+
"GETDATE()",
|
|
1506
|
+
"GETUTCDATE()",
|
|
1507
|
+
"SYSDATE",
|
|
1508
|
+
"SYSDATETIME()",
|
|
1509
|
+
"LOCALTIMESTAMP",
|
|
1510
|
+
"CURRENT_DATE",
|
|
1511
|
+
"CURRENT_TIME"
|
|
1512
|
+
];
|
|
1513
|
+
var DATETIME_DB_KEYWORDS = [
|
|
1514
|
+
"CURRENT_TIMESTAMP",
|
|
1515
|
+
"NOW()",
|
|
1516
|
+
"GETDATE()",
|
|
1517
|
+
"GETUTCDATE()",
|
|
1518
|
+
"SYSDATE",
|
|
1519
|
+
"SYSDATETIME()",
|
|
1520
|
+
"LOCALTIMESTAMP"
|
|
1521
|
+
];
|
|
1522
|
+
var DATE_DB_KEYWORDS = [
|
|
1523
|
+
"CURRENT_DATE",
|
|
1524
|
+
"CURDATE()",
|
|
1525
|
+
"GETDATE()"
|
|
1526
|
+
];
|
|
1527
|
+
var TIME_DB_KEYWORDS = [
|
|
1528
|
+
"CURRENT_TIME",
|
|
1529
|
+
"CURTIME()"
|
|
1530
|
+
];
|
|
1531
|
+
function isDbKeyword2(value, keywords) {
|
|
1532
|
+
const upperValue = value.toUpperCase().trim();
|
|
1533
|
+
return keywords.some((keyword) => upperValue === keyword.toUpperCase());
|
|
1534
|
+
}
|
|
1455
1535
|
function validateDateDefault(value) {
|
|
1456
1536
|
if (value === void 0 || value === null || value === "") {
|
|
1457
1537
|
return { valid: true };
|
|
1458
1538
|
}
|
|
1459
1539
|
const strValue = String(value);
|
|
1540
|
+
if (isDbKeyword2(strValue, DATE_DB_KEYWORDS)) {
|
|
1541
|
+
return {
|
|
1542
|
+
valid: false,
|
|
1543
|
+
error: `Database function '${strValue}' is not allowed as default. Date type only accepts static date values in YYYY-MM-DD format.`
|
|
1544
|
+
};
|
|
1545
|
+
}
|
|
1460
1546
|
if (!/^\d{4}-\d{2}-\d{2}$/.test(strValue)) {
|
|
1461
1547
|
return { valid: false, error: "Must be in YYYY-MM-DD format" };
|
|
1462
1548
|
}
|
|
@@ -1467,16 +1553,44 @@ function validateTimeDefault(value) {
|
|
|
1467
1553
|
return { valid: true };
|
|
1468
1554
|
}
|
|
1469
1555
|
const strValue = String(value);
|
|
1556
|
+
if (isDbKeyword2(strValue, TIME_DB_KEYWORDS)) {
|
|
1557
|
+
return {
|
|
1558
|
+
valid: false,
|
|
1559
|
+
error: `Database function '${strValue}' is not allowed as default. Time type only accepts static time values in HH:MM or HH:MM:SS format.`
|
|
1560
|
+
};
|
|
1561
|
+
}
|
|
1470
1562
|
if (!/^\d{2}:\d{2}(:\d{2})?$/.test(strValue)) {
|
|
1471
1563
|
return { valid: false, error: "Must be in HH:MM or HH:MM:SS format" };
|
|
1472
1564
|
}
|
|
1473
1565
|
return { valid: true };
|
|
1474
1566
|
}
|
|
1567
|
+
function validateDateTimeDefault(value) {
|
|
1568
|
+
if (value === void 0 || value === null || value === "") {
|
|
1569
|
+
return { valid: true };
|
|
1570
|
+
}
|
|
1571
|
+
const strValue = String(value);
|
|
1572
|
+
if (isDbKeyword2(strValue, DATETIME_DB_KEYWORDS)) {
|
|
1573
|
+
return {
|
|
1574
|
+
valid: false,
|
|
1575
|
+
error: `Database function '${strValue}' is not allowed as default for DateTime. Use a static datetime value in YYYY-MM-DD HH:MM:SS format instead.`
|
|
1576
|
+
};
|
|
1577
|
+
}
|
|
1578
|
+
if (!/^\d{4}-\d{2}-\d{2}(T|\s)\d{2}:\d{2}(:\d{2})?/.test(strValue)) {
|
|
1579
|
+
return { valid: false, error: "Must be in YYYY-MM-DD HH:MM:SS format" };
|
|
1580
|
+
}
|
|
1581
|
+
return { valid: true };
|
|
1582
|
+
}
|
|
1475
1583
|
function validateTimestampDefault(value) {
|
|
1476
1584
|
if (value === void 0 || value === null || value === "") {
|
|
1477
1585
|
return { valid: true };
|
|
1478
1586
|
}
|
|
1479
1587
|
const strValue = String(value);
|
|
1588
|
+
if (isDbKeyword2(strValue, TIMESTAMP_DB_KEYWORDS)) {
|
|
1589
|
+
return {
|
|
1590
|
+
valid: false,
|
|
1591
|
+
error: `Database function '${strValue}' is not allowed as default. Use 'useCurrent: true' instead for CURRENT_TIMESTAMP, or 'useCurrentOnUpdate: true' for ON UPDATE CURRENT_TIMESTAMP.`
|
|
1592
|
+
};
|
|
1593
|
+
}
|
|
1480
1594
|
if (!/^\d{4}-\d{2}-\d{2}(T|\s)\d{2}:\d{2}(:\d{2})?/.test(strValue)) {
|
|
1481
1595
|
return { valid: false, error: "Must be in YYYY-MM-DD HH:MM:SS format" };
|
|
1482
1596
|
}
|
|
@@ -1516,7 +1630,7 @@ var DateTimeType = {
|
|
|
1516
1630
|
validate() {
|
|
1517
1631
|
return [];
|
|
1518
1632
|
},
|
|
1519
|
-
validateDefaultValue:
|
|
1633
|
+
validateDefaultValue: validateDateTimeDefault
|
|
1520
1634
|
};
|
|
1521
1635
|
var TimestampType = {
|
|
1522
1636
|
name: "Timestamp",
|
|
@@ -1543,11 +1657,33 @@ var temporalTypes = [
|
|
|
1543
1657
|
|
|
1544
1658
|
// src/validation/types/special.ts
|
|
1545
1659
|
var FILE_VALID_FIELDS = ["multiple", "maxFiles", "accept", "maxSize"];
|
|
1660
|
+
var UUID_DB_KEYWORDS = [
|
|
1661
|
+
"UUID()",
|
|
1662
|
+
"UUID_GENERATE_V4()",
|
|
1663
|
+
"GEN_RANDOM_UUID()",
|
|
1664
|
+
"NEWID()",
|
|
1665
|
+
"SYS_GUID()",
|
|
1666
|
+
"UUID_SHORT()"
|
|
1667
|
+
];
|
|
1668
|
+
var JSON_DB_KEYWORDS = [
|
|
1669
|
+
"JSON_ARRAY()",
|
|
1670
|
+
"JSON_OBJECT()"
|
|
1671
|
+
];
|
|
1672
|
+
function isDbKeyword3(value, keywords) {
|
|
1673
|
+
const upperValue = value.toUpperCase().trim();
|
|
1674
|
+
return keywords.some((keyword) => upperValue === keyword.toUpperCase());
|
|
1675
|
+
}
|
|
1546
1676
|
function validateJsonDefault(value) {
|
|
1547
1677
|
if (value === void 0 || value === null || value === "") {
|
|
1548
1678
|
return { valid: true };
|
|
1549
1679
|
}
|
|
1550
1680
|
const strValue = String(value);
|
|
1681
|
+
if (isDbKeyword3(strValue, JSON_DB_KEYWORDS)) {
|
|
1682
|
+
return {
|
|
1683
|
+
valid: false,
|
|
1684
|
+
error: `Database function '${strValue}' is not allowed as default. Use valid JSON like '{}' or '[]' instead.`
|
|
1685
|
+
};
|
|
1686
|
+
}
|
|
1551
1687
|
try {
|
|
1552
1688
|
JSON.parse(strValue);
|
|
1553
1689
|
return { valid: true };
|
|
@@ -1560,6 +1696,12 @@ function validateUuidDefault(value) {
|
|
|
1560
1696
|
return { valid: true };
|
|
1561
1697
|
}
|
|
1562
1698
|
const strValue = String(value);
|
|
1699
|
+
if (isDbKeyword3(strValue, UUID_DB_KEYWORDS)) {
|
|
1700
|
+
return {
|
|
1701
|
+
valid: false,
|
|
1702
|
+
error: `Database function '${strValue}' is not allowed as default. For auto-generated UUIDs, configure at the application or database level, not in schema default.`
|
|
1703
|
+
};
|
|
1704
|
+
}
|
|
1563
1705
|
if (!/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(strValue)) {
|
|
1564
1706
|
return { valid: false, error: "Must be a valid UUID" };
|
|
1565
1707
|
}
|
|
@@ -2922,6 +3064,19 @@ function validateSchema(schema, options = {}) {
|
|
|
2922
3064
|
warnings.push(...dbCompat.warnings);
|
|
2923
3065
|
const rulesErrors = validateRules(name, property, schema.filePath);
|
|
2924
3066
|
errors.push(...rulesErrors);
|
|
3067
|
+
const baseProp = property;
|
|
3068
|
+
if (baseProp.default !== void 0) {
|
|
3069
|
+
const defaultResult = validateDefaultValue(property.type, baseProp.default, baseProp);
|
|
3070
|
+
if (!defaultResult.valid) {
|
|
3071
|
+
errors.push(
|
|
3072
|
+
validationError(
|
|
3073
|
+
`Property '${name}' has invalid default value: ${defaultResult.error}`,
|
|
3074
|
+
buildLocation7(schema.filePath),
|
|
3075
|
+
property.type === "Timestamp" ? `For Timestamp type, use 'useCurrent: true' for CURRENT_TIMESTAMP behavior` : void 0
|
|
3076
|
+
)
|
|
3077
|
+
);
|
|
3078
|
+
}
|
|
3079
|
+
}
|
|
2925
3080
|
}
|
|
2926
3081
|
}
|
|
2927
3082
|
const localizedStringWarnings = validateLocalizedStrings(schema, options.localeConfig);
|