@famgia/omnify-laravel 0.0.29 → 0.0.31
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/{chunk-4LHIH7NX.js → chunk-BYMCYVUK.js} +121 -28
- package/dist/chunk-BYMCYVUK.js.map +1 -0
- package/dist/index.cjs +123 -30
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +19 -3
- package/dist/index.d.ts +19 -3
- package/dist/index.js +1 -1
- package/dist/plugin.cjs +123 -30
- package/dist/plugin.cjs.map +1 -1
- package/dist/plugin.js +1 -1
- package/package.json +7 -7
- package/dist/chunk-4LHIH7NX.js.map +0 -1
package/dist/index.cjs
CHANGED
|
@@ -47,8 +47,10 @@ __export(index_exports, {
|
|
|
47
47
|
module.exports = __toCommonJS(index_exports);
|
|
48
48
|
|
|
49
49
|
// src/migration/schema-builder.ts
|
|
50
|
+
var import_omnify_types = require("@famgia/omnify-types");
|
|
50
51
|
var TYPE_METHOD_MAP = {
|
|
51
52
|
String: "string",
|
|
53
|
+
TinyInt: "tinyInteger",
|
|
52
54
|
Int: "integer",
|
|
53
55
|
BigInt: "bigInteger",
|
|
54
56
|
Float: "double",
|
|
@@ -63,7 +65,9 @@ var TYPE_METHOD_MAP = {
|
|
|
63
65
|
Json: "json",
|
|
64
66
|
Email: "string",
|
|
65
67
|
Password: "string",
|
|
66
|
-
Enum: "enum"
|
|
68
|
+
Enum: "enum",
|
|
69
|
+
EnumRef: "string"
|
|
70
|
+
// EnumRef stores the enum value as string (lookup via schema)
|
|
67
71
|
// Note: File type is now polymorphic - no column generated, uses files table
|
|
68
72
|
};
|
|
69
73
|
var PK_METHOD_MAP = {
|
|
@@ -91,7 +95,7 @@ function toTableName(schemaName) {
|
|
|
91
95
|
return snakeCase + "s";
|
|
92
96
|
}
|
|
93
97
|
}
|
|
94
|
-
function propertyToColumnMethod(propertyName, property) {
|
|
98
|
+
function propertyToColumnMethod(propertyName, property, options = {}) {
|
|
95
99
|
if (property.type === "Association") {
|
|
96
100
|
return null;
|
|
97
101
|
}
|
|
@@ -105,6 +109,8 @@ function propertyToColumnMethod(propertyName, property) {
|
|
|
105
109
|
const propWithLength = property;
|
|
106
110
|
if (method === "string" && propWithLength.length) {
|
|
107
111
|
args.push(propWithLength.length);
|
|
112
|
+
} else if (property.type === "EnumRef") {
|
|
113
|
+
args.push(50);
|
|
108
114
|
}
|
|
109
115
|
if (property.type === "Decimal") {
|
|
110
116
|
const decimalProp = property;
|
|
@@ -128,12 +134,15 @@ function propertyToColumnMethod(propertyName, property) {
|
|
|
128
134
|
if (baseProp.default !== void 0 && baseProp.default !== null) {
|
|
129
135
|
modifiers.push({ method: "default", args: [baseProp.default] });
|
|
130
136
|
}
|
|
131
|
-
if (baseProp.unsigned && (method === "integer" || method === "bigInteger")) {
|
|
137
|
+
if (baseProp.unsigned && (method === "tinyInteger" || method === "integer" || method === "bigInteger")) {
|
|
132
138
|
modifiers.push({ method: "unsigned" });
|
|
133
139
|
}
|
|
134
|
-
const
|
|
135
|
-
if (
|
|
136
|
-
|
|
140
|
+
const rawDisplayName = property.displayName;
|
|
141
|
+
if (rawDisplayName) {
|
|
142
|
+
const displayName = (0, import_omnify_types.resolveLocalizedString)(rawDisplayName, options.locale);
|
|
143
|
+
if (displayName) {
|
|
144
|
+
modifiers.push({ method: "comment", args: [displayName] });
|
|
145
|
+
}
|
|
137
146
|
}
|
|
138
147
|
return {
|
|
139
148
|
name: columnName,
|
|
@@ -239,7 +248,7 @@ function generatePolymorphicColumns(propertyName, property, allSchemas) {
|
|
|
239
248
|
];
|
|
240
249
|
return { typeColumn, idColumn, indexes };
|
|
241
250
|
}
|
|
242
|
-
function generateForeignKey(propertyName, property, allSchemas) {
|
|
251
|
+
function generateForeignKey(propertyName, property, allSchemas, options = {}) {
|
|
243
252
|
if (property.type !== "Association") {
|
|
244
253
|
return null;
|
|
245
254
|
}
|
|
@@ -270,7 +279,10 @@ function generateForeignKey(propertyName, property, allSchemas) {
|
|
|
270
279
|
modifiers.push({ method: "default", args: [assocProp.default] });
|
|
271
280
|
}
|
|
272
281
|
if (assocProp.displayName) {
|
|
273
|
-
|
|
282
|
+
const displayName = (0, import_omnify_types.resolveLocalizedString)(assocProp.displayName, options.locale);
|
|
283
|
+
if (displayName) {
|
|
284
|
+
modifiers.push({ method: "comment", args: [displayName] });
|
|
285
|
+
}
|
|
274
286
|
}
|
|
275
287
|
const column = {
|
|
276
288
|
name: columnName,
|
|
@@ -291,7 +303,7 @@ function generateForeignKey(propertyName, property, allSchemas) {
|
|
|
291
303
|
};
|
|
292
304
|
return { column, foreignKey, index };
|
|
293
305
|
}
|
|
294
|
-
function expandCompoundType(propName, property, customTypes) {
|
|
306
|
+
function expandCompoundType(propName, property, customTypes, options = {}) {
|
|
295
307
|
const typeDef = customTypes.get(property.type);
|
|
296
308
|
if (!typeDef || !typeDef.compound || !typeDef.expand) {
|
|
297
309
|
return null;
|
|
@@ -305,13 +317,26 @@ function expandCompoundType(propName, property, customTypes) {
|
|
|
305
317
|
type: "String"
|
|
306
318
|
// Default type, will be overridden by sql definition
|
|
307
319
|
};
|
|
308
|
-
|
|
320
|
+
const fieldOverrides = baseProp.fields;
|
|
321
|
+
const fieldOverride = fieldOverrides?.[field.suffix];
|
|
322
|
+
const fieldWithEnumRef = field;
|
|
323
|
+
if (fieldWithEnumRef.enumRef) {
|
|
324
|
+
expandedProp.type = "EnumRef";
|
|
325
|
+
expandedProp.enum = fieldWithEnumRef.enumRef;
|
|
326
|
+
if (fieldOverride?.nullable !== void 0) {
|
|
327
|
+
expandedProp.nullable = fieldOverride.nullable;
|
|
328
|
+
} else if (baseProp.nullable !== void 0) {
|
|
329
|
+
expandedProp.nullable = baseProp.nullable;
|
|
330
|
+
}
|
|
331
|
+
} else if (field.sql) {
|
|
309
332
|
const sqlType = field.sql.sqlType.toUpperCase();
|
|
310
333
|
if (sqlType === "VARCHAR" || sqlType === "CHAR" || sqlType === "STRING") {
|
|
311
334
|
expandedProp.type = "String";
|
|
312
335
|
if (field.sql.length) {
|
|
313
336
|
expandedProp.length = field.sql.length;
|
|
314
337
|
}
|
|
338
|
+
} else if (sqlType === "TINYINT") {
|
|
339
|
+
expandedProp.type = "TinyInt";
|
|
315
340
|
} else if (sqlType === "INT" || sqlType === "INTEGER") {
|
|
316
341
|
expandedProp.type = "Int";
|
|
317
342
|
} else if (sqlType === "BIGINT") {
|
|
@@ -329,17 +354,29 @@ function expandCompoundType(propName, property, customTypes) {
|
|
|
329
354
|
} else if (sqlType === "TIMESTAMP" || sqlType === "DATETIME") {
|
|
330
355
|
expandedProp.type = "Timestamp";
|
|
331
356
|
}
|
|
357
|
+
if (field.sql.unsigned) {
|
|
358
|
+
expandedProp.unsigned = true;
|
|
359
|
+
}
|
|
360
|
+
if (field.sql.default !== void 0) {
|
|
361
|
+
expandedProp.default = field.sql.default;
|
|
362
|
+
}
|
|
332
363
|
if (field.sql.nullable !== void 0) {
|
|
333
364
|
expandedProp.nullable = field.sql.nullable;
|
|
334
365
|
} else if (baseProp.nullable !== void 0) {
|
|
335
366
|
expandedProp.nullable = baseProp.nullable;
|
|
336
367
|
}
|
|
337
|
-
if (
|
|
338
|
-
expandedProp.
|
|
368
|
+
if (fieldOverride?.nullable !== void 0) {
|
|
369
|
+
expandedProp.nullable = fieldOverride.nullable;
|
|
339
370
|
}
|
|
340
371
|
}
|
|
341
372
|
if (baseProp.displayName) {
|
|
342
|
-
|
|
373
|
+
const resolvedDisplayName = (0, import_omnify_types.resolveLocalizedString)(
|
|
374
|
+
baseProp.displayName,
|
|
375
|
+
options.locale
|
|
376
|
+
);
|
|
377
|
+
if (resolvedDisplayName) {
|
|
378
|
+
expandedProp.displayName = `${resolvedDisplayName} (${field.suffix})`;
|
|
379
|
+
}
|
|
343
380
|
}
|
|
344
381
|
expanded.push({
|
|
345
382
|
name: columnName,
|
|
@@ -349,7 +386,8 @@ function expandCompoundType(propName, property, customTypes) {
|
|
|
349
386
|
return expanded;
|
|
350
387
|
}
|
|
351
388
|
function schemaToBlueprint(schema, allSchemas, options = {}) {
|
|
352
|
-
const { customTypes = /* @__PURE__ */ new Map() } = options;
|
|
389
|
+
const { customTypes = /* @__PURE__ */ new Map(), locale } = options;
|
|
390
|
+
const columnOptions = { locale };
|
|
353
391
|
const tableName = toTableName(schema.name);
|
|
354
392
|
const columns = [];
|
|
355
393
|
const foreignKeys = [];
|
|
@@ -360,21 +398,21 @@ function schemaToBlueprint(schema, allSchemas, options = {}) {
|
|
|
360
398
|
}
|
|
361
399
|
if (schema.properties) {
|
|
362
400
|
for (const [propName, property] of Object.entries(schema.properties)) {
|
|
363
|
-
const expandedProps = expandCompoundType(propName, property, customTypes);
|
|
401
|
+
const expandedProps = expandCompoundType(propName, property, customTypes, columnOptions);
|
|
364
402
|
if (expandedProps) {
|
|
365
403
|
for (const { name: expandedName, property: expandedProp } of expandedProps) {
|
|
366
|
-
const columnMethod2 = propertyToColumnMethod(expandedName, expandedProp);
|
|
404
|
+
const columnMethod2 = propertyToColumnMethod(expandedName, expandedProp, columnOptions);
|
|
367
405
|
if (columnMethod2) {
|
|
368
406
|
columns.push(columnMethod2);
|
|
369
407
|
}
|
|
370
408
|
}
|
|
371
409
|
continue;
|
|
372
410
|
}
|
|
373
|
-
const columnMethod = propertyToColumnMethod(propName, property);
|
|
411
|
+
const columnMethod = propertyToColumnMethod(propName, property, columnOptions);
|
|
374
412
|
if (columnMethod) {
|
|
375
413
|
columns.push(columnMethod);
|
|
376
414
|
}
|
|
377
|
-
const fkResult = generateForeignKey(propName, property, allSchemas);
|
|
415
|
+
const fkResult = generateForeignKey(propName, property, allSchemas, columnOptions);
|
|
378
416
|
if (fkResult) {
|
|
379
417
|
columns.push(fkResult.column);
|
|
380
418
|
foreignKeys.push(fkResult.foreignKey);
|
|
@@ -817,7 +855,8 @@ function generateMigrations(schemas, options = {}) {
|
|
|
817
855
|
const offsetTimestamp = incrementTimestamp(timestamp, timestampOffset);
|
|
818
856
|
timestampOffset++;
|
|
819
857
|
const blueprint = schemaToBlueprint(schema, schemas, {
|
|
820
|
-
customTypes: options.customTypes
|
|
858
|
+
customTypes: options.customTypes,
|
|
859
|
+
locale: options.locale
|
|
821
860
|
});
|
|
822
861
|
const migration = generateCreateMigration(blueprint, {
|
|
823
862
|
...options,
|
|
@@ -1167,7 +1206,7 @@ function generateMigrationsFromChanges(changes, options = {}) {
|
|
|
1167
1206
|
}
|
|
1168
1207
|
|
|
1169
1208
|
// src/model/generator.ts
|
|
1170
|
-
var
|
|
1209
|
+
var import_omnify_types2 = require("@famgia/omnify-types");
|
|
1171
1210
|
|
|
1172
1211
|
// src/utils.ts
|
|
1173
1212
|
function toSnakeCase(str) {
|
|
@@ -1196,7 +1235,8 @@ var DEFAULT_OPTIONS = {
|
|
|
1196
1235
|
modelNamespace: "App\\Models",
|
|
1197
1236
|
baseModelClassName: "BaseModel",
|
|
1198
1237
|
baseModelPath: "app/Models/OmnifyBase",
|
|
1199
|
-
modelPath: "app/Models"
|
|
1238
|
+
modelPath: "app/Models",
|
|
1239
|
+
customTypes: /* @__PURE__ */ new Map()
|
|
1200
1240
|
};
|
|
1201
1241
|
function generateLocalizedDisplayNames(displayName, indent = " ") {
|
|
1202
1242
|
if (displayName === void 0) {
|
|
@@ -1205,7 +1245,7 @@ function generateLocalizedDisplayNames(displayName, indent = " ") {
|
|
|
1205
1245
|
if (typeof displayName === "string") {
|
|
1206
1246
|
return `${indent}'en' => '${escapePhpString(displayName)}',`;
|
|
1207
1247
|
}
|
|
1208
|
-
if ((0,
|
|
1248
|
+
if ((0, import_omnify_types2.isLocaleMap)(displayName)) {
|
|
1209
1249
|
const entries = Object.entries(displayName).map(([locale, value]) => `${indent}'${locale}' => '${escapePhpString(value)}',`).join("\n");
|
|
1210
1250
|
return entries;
|
|
1211
1251
|
}
|
|
@@ -1225,7 +1265,7 @@ function generatePropertyLocalizedDisplayNames(schema, indent = " ") {
|
|
|
1225
1265
|
entries.push(`${indent}'${snakeName}' => [
|
|
1226
1266
|
${innerIndent}'en' => '${escapePhpString(displayName)}',
|
|
1227
1267
|
${indent}],`);
|
|
1228
|
-
} else if ((0,
|
|
1268
|
+
} else if ((0, import_omnify_types2.isLocaleMap)(displayName)) {
|
|
1229
1269
|
const localeEntries = Object.entries(displayName).map(([locale, value]) => `${innerIndent}'${locale}' => '${escapePhpString(value)}',`).join("\n");
|
|
1230
1270
|
entries.push(`${indent}'${snakeName}' => [
|
|
1231
1271
|
${localeEntries}
|
|
@@ -1243,7 +1283,8 @@ function resolveOptions(options) {
|
|
|
1243
1283
|
modelNamespace: options?.modelNamespace ?? DEFAULT_OPTIONS.modelNamespace,
|
|
1244
1284
|
baseModelClassName: options?.baseModelClassName ?? DEFAULT_OPTIONS.baseModelClassName,
|
|
1245
1285
|
baseModelPath: options?.baseModelPath ?? DEFAULT_OPTIONS.baseModelPath,
|
|
1246
|
-
modelPath: options?.modelPath ?? DEFAULT_OPTIONS.modelPath
|
|
1286
|
+
modelPath: options?.modelPath ?? DEFAULT_OPTIONS.modelPath,
|
|
1287
|
+
customTypes: options?.customTypes ?? /* @__PURE__ */ new Map()
|
|
1247
1288
|
};
|
|
1248
1289
|
}
|
|
1249
1290
|
function getCastType(propDef) {
|
|
@@ -1374,7 +1415,10 @@ function generateEntityBaseModel(schema, schemas, options, stubContent, authStub
|
|
|
1374
1415
|
}
|
|
1375
1416
|
}
|
|
1376
1417
|
} else if (propDef.type === "Password") {
|
|
1377
|
-
|
|
1418
|
+
const propWithFillable = propDef;
|
|
1419
|
+
if (propWithFillable.fillable !== false) {
|
|
1420
|
+
fillable.push(` '${snakeName}',`);
|
|
1421
|
+
}
|
|
1378
1422
|
hidden.push(` '${snakeName}',`);
|
|
1379
1423
|
const cast = getCastType(propDef);
|
|
1380
1424
|
if (cast) {
|
|
@@ -1384,10 +1428,58 @@ function generateEntityBaseModel(schema, schemas, options, stubContent, authStub
|
|
|
1384
1428
|
const relMethod = generateFileRelation(propName, propDef);
|
|
1385
1429
|
relations.push(relMethod);
|
|
1386
1430
|
} else {
|
|
1387
|
-
|
|
1388
|
-
const
|
|
1389
|
-
|
|
1390
|
-
|
|
1431
|
+
const propWithOptions = propDef;
|
|
1432
|
+
const isFillable = propWithOptions.fillable !== false;
|
|
1433
|
+
const isHidden = propWithOptions.hidden === true;
|
|
1434
|
+
const typeDef = options.customTypes.get(propDef.type);
|
|
1435
|
+
const isCompoundType = typeDef?.compound && typeDef.expand;
|
|
1436
|
+
if (isCompoundType && typeDef.expand) {
|
|
1437
|
+
const fieldOverrides = propWithOptions.fields ?? {};
|
|
1438
|
+
for (const field of typeDef.expand) {
|
|
1439
|
+
const suffixSnake = toSnakeCase(field.suffix);
|
|
1440
|
+
const fieldName = `${snakeName}_${suffixSnake}`;
|
|
1441
|
+
const override = fieldOverrides[field.suffix];
|
|
1442
|
+
const fieldFillable = override?.fillable !== void 0 ? override.fillable : isFillable;
|
|
1443
|
+
if (fieldFillable) {
|
|
1444
|
+
fillable.push(` '${fieldName}',`);
|
|
1445
|
+
}
|
|
1446
|
+
const fieldHidden = override?.hidden !== void 0 ? override.hidden : isHidden;
|
|
1447
|
+
if (fieldHidden) {
|
|
1448
|
+
hidden.push(` '${fieldName}',`);
|
|
1449
|
+
}
|
|
1450
|
+
}
|
|
1451
|
+
} else {
|
|
1452
|
+
if (isFillable) {
|
|
1453
|
+
fillable.push(` '${snakeName}',`);
|
|
1454
|
+
}
|
|
1455
|
+
const cast = getCastType(propDef);
|
|
1456
|
+
if (cast) {
|
|
1457
|
+
casts.push(` '${snakeName}' => '${cast}',`);
|
|
1458
|
+
}
|
|
1459
|
+
if (isHidden) {
|
|
1460
|
+
hidden.push(` '${snakeName}',`);
|
|
1461
|
+
}
|
|
1462
|
+
}
|
|
1463
|
+
if (typeDef?.compound && typeDef.accessors) {
|
|
1464
|
+
for (const accessor of typeDef.accessors) {
|
|
1465
|
+
const accessorName = `${snakeName}_${toSnakeCase(accessor.name)}`;
|
|
1466
|
+
appends.push(` '${accessorName}',`);
|
|
1467
|
+
const methodName = toPascalCase(accessorName);
|
|
1468
|
+
const separator = accessor.separator ?? " ";
|
|
1469
|
+
const fieldRefs = accessor.fields.map((field) => {
|
|
1470
|
+
const fieldName = `${snakeName}_${toSnakeCase(field)}`;
|
|
1471
|
+
return `$this->${fieldName}`;
|
|
1472
|
+
});
|
|
1473
|
+
const accessorMethod = ` /**
|
|
1474
|
+
* Get the ${accessor.name.replace(/_/g, " ")} attribute.
|
|
1475
|
+
*/
|
|
1476
|
+
public function get${methodName}Attribute(): ?string
|
|
1477
|
+
{
|
|
1478
|
+
$parts = array_filter([${fieldRefs.join(", ")}], fn($v) => $v !== null && $v !== '');
|
|
1479
|
+
return count($parts) > 0 ? implode('${separator}', $parts) : null;
|
|
1480
|
+
}`;
|
|
1481
|
+
relations.push(accessorMethod);
|
|
1482
|
+
}
|
|
1391
1483
|
}
|
|
1392
1484
|
}
|
|
1393
1485
|
}
|
|
@@ -2598,7 +2690,8 @@ function laravelPlugin(options) {
|
|
|
2598
2690
|
modelNamespace: resolved.modelNamespace,
|
|
2599
2691
|
baseModelNamespace: resolved.baseModelNamespace,
|
|
2600
2692
|
modelPath: resolved.modelsPath,
|
|
2601
|
-
baseModelPath: resolved.baseModelsPath
|
|
2693
|
+
baseModelPath: resolved.baseModelsPath,
|
|
2694
|
+
customTypes: ctx.customTypes
|
|
2602
2695
|
};
|
|
2603
2696
|
const models = generateModels(ctx.schemas, modelOptions);
|
|
2604
2697
|
const outputs = models.map((model) => ({
|