@famgia/omnify-laravel 0.0.106 → 0.0.108

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.
@@ -556,6 +556,9 @@ function extractManyToManyRelations(schema, allSchemas) {
556
556
  if (assocProp.relation !== "ManyToMany") {
557
557
  continue;
558
558
  }
559
+ if (assocProp.mappedBy) {
560
+ continue;
561
+ }
559
562
  const targetName = assocProp.target;
560
563
  if (!targetName) {
561
564
  continue;
@@ -570,6 +573,19 @@ function extractManyToManyRelations(schema, allSchemas) {
570
573
  const pivotTableName = generatePivotTableName(sourceTable, targetTable, assocProp.joinTable);
571
574
  const sourceColumn = sourceTable.replace(/ies$/, "y").replace(/s$/, "") + "_id";
572
575
  const targetColumn = targetTable.replace(/ies$/, "y").replace(/s$/, "") + "_id";
576
+ const pivotFields = [];
577
+ if (assocProp.pivotFields) {
578
+ for (const [fieldName, fieldDef] of Object.entries(assocProp.pivotFields)) {
579
+ pivotFields.push({
580
+ name: toColumnName(fieldName),
581
+ type: fieldDef.type,
582
+ nullable: fieldDef.nullable,
583
+ default: fieldDef.default,
584
+ length: fieldDef.length,
585
+ unsigned: fieldDef.unsigned
586
+ });
587
+ }
588
+ }
573
589
  pivotTables.push({
574
590
  tableName: pivotTableName,
575
591
  sourceTable,
@@ -579,11 +595,35 @@ function extractManyToManyRelations(schema, allSchemas) {
579
595
  sourcePkType,
580
596
  targetPkType,
581
597
  onDelete: assocProp.onDelete,
582
- onUpdate: assocProp.onUpdate
598
+ onUpdate: assocProp.onUpdate,
599
+ pivotFields: pivotFields.length > 0 ? pivotFields : void 0
583
600
  });
584
601
  }
585
602
  return pivotTables;
586
603
  }
604
+ function pivotFieldToColumn(field) {
605
+ const method = TYPE_METHOD_MAP[field.type] ?? "string";
606
+ const args = [field.name];
607
+ const modifiers = [];
608
+ if (method === "string" && field.length) {
609
+ args.push(field.length);
610
+ }
611
+ if (field.nullable) {
612
+ modifiers.push({ method: "nullable" });
613
+ }
614
+ if (field.default !== void 0 && field.default !== null) {
615
+ modifiers.push({ method: "default", args: [field.default] });
616
+ }
617
+ if (field.unsigned && (method === "tinyInteger" || method === "integer" || method === "bigInteger")) {
618
+ modifiers.push({ method: "unsigned" });
619
+ }
620
+ return {
621
+ name: field.name,
622
+ method,
623
+ args,
624
+ modifiers
625
+ };
626
+ }
587
627
  function generatePivotTableBlueprint(pivot) {
588
628
  const columns = [];
589
629
  const foreignKeys = [];
@@ -612,6 +652,11 @@ function generatePivotTableBlueprint(pivot) {
612
652
  args: [pivot.targetColumn],
613
653
  modifiers: []
614
654
  });
655
+ if (pivot.pivotFields && pivot.pivotFields.length > 0) {
656
+ for (const field of pivot.pivotFields) {
657
+ columns.push(pivotFieldToColumn(field));
658
+ }
659
+ }
615
660
  columns.push(...generateTimestampColumns());
616
661
  foreignKeys.push({
617
662
  columns: [pivot.sourceColumn],
@@ -647,6 +692,126 @@ function generatePivotTableBlueprint(pivot) {
647
692
  indexes
648
693
  };
649
694
  }
695
+ function extractMorphToManyRelations(schema, allSchemas) {
696
+ const morphPivotTables = [];
697
+ if (!schema.properties) {
698
+ return morphPivotTables;
699
+ }
700
+ for (const [propName, property] of Object.entries(schema.properties)) {
701
+ if (property.type !== "Association") {
702
+ continue;
703
+ }
704
+ const assocProp = property;
705
+ if (assocProp.relation !== "MorphToMany") {
706
+ continue;
707
+ }
708
+ const targetName = assocProp.target;
709
+ if (!targetName) {
710
+ continue;
711
+ }
712
+ const targetSchema = allSchemas[targetName];
713
+ const targetTable = toTableName(targetName);
714
+ const targetPkType = targetSchema ? getIdType(targetSchema) : "BigInt";
715
+ const isOwningSide = assocProp.owning ?? schema.name < targetName;
716
+ if (!isOwningSide) {
717
+ continue;
718
+ }
719
+ const morphTargets = [];
720
+ morphTargets.push(schema.name);
721
+ for (const [otherName, otherSchema] of Object.entries(allSchemas)) {
722
+ if (otherName === schema.name) continue;
723
+ if (!otherSchema.properties) continue;
724
+ for (const otherProp of Object.values(otherSchema.properties)) {
725
+ if (otherProp.type !== "Association") continue;
726
+ const otherAssoc = otherProp;
727
+ if (otherAssoc.relation === "MorphToMany" && otherAssoc.target === targetName) {
728
+ if (!morphTargets.includes(otherName)) {
729
+ morphTargets.push(otherName);
730
+ }
731
+ }
732
+ }
733
+ }
734
+ const defaultTableName = targetTable.replace(/s$/, "") + "ables";
735
+ const tableName = assocProp.joinTable ?? defaultTableName;
736
+ const targetColumn = targetTable.replace(/ies$/, "y").replace(/s$/, "") + "_id";
737
+ const morphName = propName.replace(/s$/, "") + "able";
738
+ morphPivotTables.push({
739
+ tableName,
740
+ targetTable,
741
+ targetColumn,
742
+ targetPkType,
743
+ morphName,
744
+ morphTargets,
745
+ onDelete: assocProp.onDelete,
746
+ onUpdate: assocProp.onUpdate
747
+ });
748
+ }
749
+ return morphPivotTables;
750
+ }
751
+ function generateMorphToManyPivotBlueprint(pivot) {
752
+ const columns = [];
753
+ const foreignKeys = [];
754
+ const indexes = [];
755
+ const getMethodForPkType = (pkType) => {
756
+ switch (pkType) {
757
+ case "Int":
758
+ return "unsignedInteger";
759
+ case "Uuid":
760
+ return "uuid";
761
+ case "String":
762
+ return "string";
763
+ default:
764
+ return "unsignedBigInteger";
765
+ }
766
+ };
767
+ columns.push({
768
+ name: pivot.targetColumn,
769
+ method: getMethodForPkType(pivot.targetPkType),
770
+ args: [pivot.targetColumn],
771
+ modifiers: []
772
+ });
773
+ const typeColumnName = `${pivot.morphName}_type`;
774
+ columns.push({
775
+ name: typeColumnName,
776
+ method: "enum",
777
+ args: [typeColumnName, pivot.morphTargets],
778
+ modifiers: []
779
+ });
780
+ const idColumnName = `${pivot.morphName}_id`;
781
+ columns.push({
782
+ name: idColumnName,
783
+ method: "unsignedBigInteger",
784
+ // Default to BigInt for polymorphic IDs
785
+ args: [idColumnName],
786
+ modifiers: []
787
+ });
788
+ foreignKeys.push({
789
+ columns: [pivot.targetColumn],
790
+ references: "id",
791
+ on: [pivot.targetTable],
792
+ onDelete: pivot.onDelete ?? "cascade",
793
+ onUpdate: pivot.onUpdate ?? "cascade"
794
+ });
795
+ indexes.push({
796
+ columns: [pivot.targetColumn, typeColumnName, idColumnName],
797
+ unique: true
798
+ });
799
+ indexes.push({
800
+ columns: [typeColumnName, idColumnName],
801
+ unique: false
802
+ });
803
+ indexes.push({
804
+ columns: [pivot.targetColumn],
805
+ unique: false
806
+ });
807
+ return {
808
+ tableName: pivot.tableName,
809
+ columns,
810
+ primaryKey: [pivot.targetColumn, typeColumnName, idColumnName],
811
+ foreignKeys,
812
+ indexes
813
+ };
814
+ }
650
815
 
651
816
  // src/migration/generator.ts
652
817
  function generateTimestamp() {
@@ -713,6 +878,16 @@ function generateCreateMigration(blueprint, options = {}) {
713
878
  const indexContent = renderIndexes(blueprint);
714
879
  const content = `<?php
715
880
 
881
+ /**
882
+ * DO NOT EDIT - This file is auto-generated by Omnify.
883
+ * Any changes will be overwritten on next generation.
884
+ *
885
+ * To modify the schema, edit the corresponding YAML file in schemas/
886
+ * and run: npx omnify generate
887
+ *
888
+ * @generated by @famgia/omnify-laravel
889
+ */
890
+
716
891
  use Illuminate\\Database\\Migrations\\Migration;
717
892
  use Illuminate\\Database\\Schema\\Blueprint;
718
893
  use Illuminate\\Support\\Facades\\Schema;
@@ -754,6 +929,13 @@ function generateDropMigration(tableName, options = {}) {
754
929
  ` : "";
755
930
  const content = `<?php
756
931
 
932
+ /**
933
+ * DO NOT EDIT - This file is auto-generated by Omnify.
934
+ * Any changes will be overwritten on next generation.
935
+ *
936
+ * @generated by @famgia/omnify-laravel
937
+ */
938
+
757
939
  use Illuminate\\Database\\Migrations\\Migration;
758
940
  use Illuminate\\Database\\Schema\\Blueprint;
759
941
  use Illuminate\\Support\\Facades\\Schema;
@@ -1066,6 +1248,16 @@ function generateAlterMigrationContent(tableName, change, options = {}) {
1066
1248
  ` : "";
1067
1249
  return `<?php
1068
1250
 
1251
+ /**
1252
+ * DO NOT EDIT - This file is auto-generated by Omnify.
1253
+ * Any changes will be overwritten on next generation.
1254
+ *
1255
+ * To modify the schema, edit the corresponding YAML file in schemas/
1256
+ * and run: npx omnify generate
1257
+ *
1258
+ * @generated by @famgia/omnify-laravel
1259
+ */
1260
+
1069
1261
  use Illuminate\\Database\\Migrations\\Migration;
1070
1262
  use Illuminate\\Database\\Schema\\Blueprint;
1071
1263
  use Illuminate\\Support\\Facades\\Schema;
@@ -1123,6 +1315,13 @@ function generateDropTableMigration(schemaName, options = {}) {
1123
1315
  ` : "";
1124
1316
  const content = `<?php
1125
1317
 
1318
+ /**
1319
+ * DO NOT EDIT - This file is auto-generated by Omnify.
1320
+ * Any changes will be overwritten on next generation.
1321
+ *
1322
+ * @generated by @famgia/omnify-laravel
1323
+ */
1324
+
1126
1325
  use Illuminate\\Database\\Migrations\\Migration;
1127
1326
  use Illuminate\\Database\\Schema\\Blueprint;
1128
1327
  use Illuminate\\Support\\Facades\\Schema;
@@ -1600,12 +1799,30 @@ function generateRelation(propName, assoc, schema, schemas, options) {
1600
1799
  }
1601
1800
  case "ManyToMany": {
1602
1801
  const pivotTable = assoc.joinTable ?? `${toSnakeCase(propName)}_pivot`;
1802
+ let pivotFieldNames = [];
1803
+ if (assoc.pivotFields && Object.keys(assoc.pivotFields).length > 0) {
1804
+ pivotFieldNames = Object.keys(assoc.pivotFields).map((f) => toSnakeCase(f));
1805
+ } else if (assoc.mappedBy && assoc.target) {
1806
+ const targetSchema = schemas[assoc.target];
1807
+ if (targetSchema?.properties) {
1808
+ const owningProp = targetSchema.properties[assoc.mappedBy];
1809
+ if (owningProp?.type === "Association") {
1810
+ const owningAssoc = owningProp;
1811
+ if (owningAssoc.pivotFields && Object.keys(owningAssoc.pivotFields).length > 0) {
1812
+ pivotFieldNames = Object.keys(owningAssoc.pivotFields).map((f) => toSnakeCase(f));
1813
+ }
1814
+ }
1815
+ }
1816
+ }
1817
+ const pivotFieldsCode = pivotFieldNames.length > 0 ? pivotFieldNames.map((f) => `'${f}'`).join(", ") : null;
1818
+ const withPivotLine = pivotFieldsCode ? `
1819
+ ->withPivot(${pivotFieldsCode})` : "";
1603
1820
  return ` /**
1604
1821
  * The ${propName} that belong to this model.
1605
1822
  */
1606
1823
  public function ${methodName}(): BelongsToMany
1607
1824
  {
1608
- return $this->belongsToMany(${targetClass}::class, '${pivotTable}')
1825
+ return $this->belongsToMany(${targetClass}::class, '${pivotTable}')${withPivotLine}
1609
1826
  ->withTimestamps();
1610
1827
  }`;
1611
1828
  }
@@ -4578,6 +4795,11 @@ export {
4578
4795
  formatColumnMethod,
4579
4796
  formatForeignKey,
4580
4797
  formatIndex,
4798
+ generatePivotTableName,
4799
+ extractManyToManyRelations,
4800
+ generatePivotTableBlueprint,
4801
+ extractMorphToManyRelations,
4802
+ generateMorphToManyPivotBlueprint,
4581
4803
  generateMigrations,
4582
4804
  generateMigrationFromSchema,
4583
4805
  generateDropMigrationForTable,
@@ -4595,4 +4817,4 @@ export {
4595
4817
  shouldGenerateAIGuides,
4596
4818
  laravelPlugin
4597
4819
  };
4598
- //# sourceMappingURL=chunk-XR2DTIIS.js.map
4820
+ //# sourceMappingURL=chunk-GDFAEEEG.js.map