sonamu 0.0.38 → 0.0.40

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.
Files changed (40) hide show
  1. package/dist/api/code-converters.d.ts +1 -0
  2. package/dist/api/code-converters.d.ts.map +1 -1
  3. package/dist/api/code-converters.js +68 -1
  4. package/dist/api/code-converters.js.map +1 -1
  5. package/dist/api/decorators.d.ts +1 -0
  6. package/dist/api/decorators.d.ts.map +1 -1
  7. package/dist/api/decorators.js.map +1 -1
  8. package/dist/index.d.ts +1 -0
  9. package/dist/index.d.ts.map +1 -1
  10. package/dist/index.js +1 -0
  11. package/dist/index.js.map +1 -1
  12. package/dist/smd/migrator.d.ts +34 -1
  13. package/dist/smd/migrator.d.ts.map +1 -1
  14. package/dist/smd/migrator.js +8 -3
  15. package/dist/smd/migrator.js.map +1 -1
  16. package/dist/smd/smd-manager.d.ts +1 -1
  17. package/dist/smd/smd-manager.d.ts.map +1 -1
  18. package/dist/smd/smd-manager.js.map +1 -1
  19. package/dist/smd/smd.d.ts +1 -1
  20. package/dist/smd/smd.d.ts.map +1 -1
  21. package/dist/smd/smd.js +5 -20
  22. package/dist/smd/smd.js.map +1 -1
  23. package/dist/syncer/syncer.d.ts +1 -1
  24. package/dist/syncer/syncer.d.ts.map +1 -1
  25. package/dist/syncer/syncer.js +40 -38
  26. package/dist/syncer/syncer.js.map +1 -1
  27. package/dist/templates/view_form.template.d.ts +1 -1
  28. package/dist/templates/view_list.template.d.ts +1 -1
  29. package/dist/types/types.d.ts +1 -0
  30. package/dist/types/types.d.ts.map +1 -1
  31. package/dist/types/types.js.map +1 -1
  32. package/package.json +1 -1
  33. package/src/api/code-converters.ts +70 -0
  34. package/src/api/decorators.ts +1 -0
  35. package/src/index.ts +1 -0
  36. package/src/smd/migrator.ts +52 -7
  37. package/src/smd/smd-manager.ts +1 -1
  38. package/src/smd/smd.ts +11 -26
  39. package/src/syncer/syncer.ts +4 -4
  40. package/src/types/types.ts +1 -0
@@ -48,6 +48,7 @@ import {
48
48
  isEnumProp,
49
49
  isIntegerProp,
50
50
  isKnexError,
51
+ RelationOn,
51
52
  } from "../types/types";
52
53
  import { propIf } from "../utils/lodash-able";
53
54
  import { SMDManager } from "./smd-manager";
@@ -479,13 +480,21 @@ export class Migrator {
479
480
  } else {
480
481
  const smdForeigns = sortBy(smdSet.foreigns, (a) =>
481
482
  [a.to, ...a.columns].join("-")
482
- );
483
+ ).map((smdForeign) => {
484
+ // MySQL에서 RESTRICT와 NO ACTION은 동일함
485
+ const { onDelete, onUpdate } = smdForeign;
486
+ return {
487
+ ...smdForeign,
488
+ onUpdate: onUpdate === "RESTRICT" ? "NO ACTION" : onUpdate,
489
+ onDelete: onDelete === "RESTRICT" ? "NO ACTION" : onDelete,
490
+ };
491
+ });
483
492
  const dbForeigns = sortBy(dbSet.foreigns, (a) =>
484
493
  [a.to, ...a.columns].join("-")
485
494
  );
486
495
 
487
496
  if (equal(smdForeigns, dbForeigns) === false) {
488
- // console.dir({ smdForeigns, dbForeigns }, { depth: null });
497
+ console.dir({ smdForeigns, dbForeigns }, { depth: null });
489
498
  return this.generateAlterCode_Foreigns(
490
499
  smdSet.table,
491
500
  smdForeigns,
@@ -526,7 +535,7 @@ export class Migrator {
526
535
  기존 테이블 정보 읽어서 MigrationSet 형식으로 리턴
527
536
  */
528
537
  async getMigrationSetFromDB(table: string): Promise<MigrationSet | null> {
529
- let dbColumns: any[], dbIndexes: any[], dbForeigns: any[];
538
+ let dbColumns: DBColumn[], dbIndexes: DBIndex[], dbForeigns: DBForeign[];
530
539
  try {
531
540
  [dbColumns, dbIndexes, dbForeigns] = await this.readTable(table);
532
541
  } catch (e: unknown) {
@@ -546,7 +555,7 @@ export class Migrator {
546
555
  ...propIf(dbColumn.Default !== null, {
547
556
  defaultTo:
548
557
  dbColType.type === "float"
549
- ? parseFloat(dbColumn.Default).toString()
558
+ ? parseFloat(dbColumn.Default ?? "0").toString()
550
559
  : dbColumn.Default,
551
560
  }),
552
561
  };
@@ -584,8 +593,8 @@ export class Migrator {
584
593
  return {
585
594
  columns: [dbForeign.from],
586
595
  to: `${dbForeign.referencesTable}.${dbForeign.referencesField}`,
587
- onUpdate: dbForeign.onUpdate,
588
- onDelete: dbForeign.onDelete,
596
+ onUpdate: dbForeign.onUpdate as RelationOn,
597
+ onDelete: dbForeign.onDelete as RelationOn,
589
598
  };
590
599
  });
591
600
 
@@ -683,7 +692,9 @@ export class Migrator {
683
692
  /*
684
693
  기존 테이블 읽어서 cols, indexes 반환
685
694
  */
686
- async readTable(tableName: string): Promise<[any, any, any]> {
695
+ async readTable(
696
+ tableName: string
697
+ ): Promise<[DBColumn[], DBIndex[], DBForeign[]]> {
687
698
  // 테이블 정보
688
699
  try {
689
700
  const [cols] = await this.targets.compare!.raw(
@@ -1555,3 +1566,37 @@ export class Migrator {
1555
1566
  );
1556
1567
  }
1557
1568
  }
1569
+
1570
+ type DBColumn = {
1571
+ Field: string;
1572
+ Type: string;
1573
+ Null: string;
1574
+ Key: string;
1575
+ Default: string | null;
1576
+ Extra: string;
1577
+ };
1578
+ type DBIndex = {
1579
+ Table: string;
1580
+ Non_unique: number;
1581
+ Key_name: string;
1582
+ Seq_in_index: number;
1583
+ Column_name: string;
1584
+ Collation: string | null;
1585
+ Cardinality: number | null;
1586
+ Sub_part: number | null;
1587
+ Packed: string | null;
1588
+ Null: string;
1589
+ Index_type: string;
1590
+ Comment: string;
1591
+ Index_comment: string;
1592
+ Visible: string;
1593
+ Expression: string | null;
1594
+ };
1595
+ type DBForeign = {
1596
+ keyName: string;
1597
+ from: string;
1598
+ referencesTable: string;
1599
+ referencesField: string;
1600
+ onDelete: string;
1601
+ onUpdate: string;
1602
+ };
@@ -24,7 +24,7 @@ type TableSpec = {
24
24
  };
25
25
  class SMDManagerClass {
26
26
  private SMDs: Map<string, SMD> = new Map();
27
- private modulePaths: Map<string, string> = new Map();
27
+ public modulePaths: Map<string, string> = new Map();
28
28
  private tableSpecs: Map<string, TableSpec> = new Map();
29
29
  public isAutoloaded: boolean = false;
30
30
 
package/src/smd/smd.ts CHANGED
@@ -132,7 +132,11 @@ export class SMD {
132
132
 
133
133
  /*
134
134
  */
135
- resolveSubsetQuery(prefix: string, fields: string[]): SubsetQuery {
135
+ resolveSubsetQuery(
136
+ prefix: string,
137
+ fields: string[],
138
+ isAlreadyOuterJoined: boolean = false
139
+ ): SubsetQuery {
136
140
  // prefix 치환 (prefix는 ToOneRelation이 복수로 붙은 경우 모두 __로 변경됨)
137
141
  prefix = prefix.replace(/\./g, "__");
138
142
 
@@ -203,9 +207,13 @@ export class SMD {
203
207
  return r;
204
208
  }
205
209
 
210
+ // innerOrOuter
211
+ const innerOrOuter =
212
+ isAlreadyOuterJoined || relation.nullable ? "outer" : "inner";
206
213
  const relSubsetQuery = relSMD.resolveSubsetQuery(
207
214
  `${prefix !== "" ? prefix + "." : ""}${groupKey}`,
208
- relFields
215
+ relFields,
216
+ innerOrOuter === "outer"
209
217
  );
210
218
  r.select = r.select.concat(relSubsetQuery.select);
211
219
  r.virtual = r.virtual.concat(relSubsetQuery.virtual);
@@ -240,32 +248,9 @@ export class SMD {
240
248
  };
241
249
  }
242
250
 
243
- const outerOrInner = (() => {
244
- // 대상 컬럼이 nullable인 경우 outer, 아닌 경우 inner
245
- // OneToOneRelation의 경우 joinColumn이 없는 경우 해당 relation을 찾아가 확인해야 함 (customJoin의 경우 고려하지 않음)
246
- if (
247
- isOneToOneRelationProp(relation) &&
248
- relation.hasJoinColumn === false
249
- ) {
250
- const oppositeRelationProp = relSMD.props.find(
251
- (prop) =>
252
- isOneToOneRelationProp(prop) &&
253
- prop.with === this.id &&
254
- prop.hasJoinColumn === true
255
- );
256
- if (oppositeRelationProp?.nullable === true) {
257
- return "outer";
258
- } else {
259
- return "inner";
260
- }
261
- }
262
-
263
- return relation.nullable === true ? "outer" : "inner";
264
- })();
265
-
266
251
  r.joins.push({
267
252
  as: joinAs,
268
- join: outerOrInner,
253
+ join: innerOrOuter,
269
254
  table: relSMD.table,
270
255
  ...joinClause,
271
256
  });
@@ -801,7 +801,7 @@ export class Syncer {
801
801
  }
802
802
 
803
803
  const rendered = template.render(options, ...extra);
804
- const resolved = this.resolveRenderedTemplate(key, rendered);
804
+ const resolved = await this.resolveRenderedTemplate(key, rendered);
805
805
 
806
806
  let preTemplateResolved: PathAndCode[] = [];
807
807
  if (rendered.preTemplates) {
@@ -817,10 +817,10 @@ export class Syncer {
817
817
  return [resolved, ...preTemplateResolved];
818
818
  }
819
819
 
820
- resolveRenderedTemplate(
820
+ async resolveRenderedTemplate(
821
821
  key: TemplateKey,
822
822
  result: RenderedTemplate
823
- ): PathAndCode {
823
+ ): Promise<PathAndCode> {
824
824
  const { target, path: filePath, body, importKeys, customHeaders } = result;
825
825
 
826
826
  // import 할 대상의 대상 path 추출
@@ -873,7 +873,7 @@ export class Syncer {
873
873
  const formatted =
874
874
  key === "generated_http"
875
875
  ? [header, body].join("\n\n")
876
- : prettier.format([header, body].join("\n\n"), {
876
+ : await prettier.format([header, body].join("\n\n"), {
877
877
  parser: "typescript",
878
878
  });
879
879
 
@@ -127,6 +127,7 @@ type _RelationProp = {
127
127
  with: string;
128
128
  nullable?: boolean;
129
129
  toFilter?: true;
130
+ desc?: string;
130
131
  };
131
132
  export type OneToOneRelationProp = _RelationProp & {
132
133
  relationType: "OneToOne";