xansql 1.0.8 → 1.0.9

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 (212) hide show
  1. package/core/Xansql.cjs +7 -8
  2. package/core/Xansql.cjs.map +1 -1
  3. package/core/Xansql.d.ts +2 -3
  4. package/core/Xansql.mjs +7 -8
  5. package/core/Xansql.mjs.map +1 -1
  6. package/core/classes/ForeignInfo.cjs +3 -2
  7. package/core/classes/ForeignInfo.cjs.map +1 -1
  8. package/core/classes/ForeignInfo.d.ts +1 -2
  9. package/core/classes/ForeignInfo.mjs +3 -2
  10. package/core/classes/ForeignInfo.mjs.map +1 -1
  11. package/core/classes/Migration/TableMigration.cjs +24 -15
  12. package/core/classes/Migration/TableMigration.cjs.map +1 -1
  13. package/core/classes/Migration/TableMigration.mjs +25 -16
  14. package/core/classes/Migration/TableMigration.mjs.map +1 -1
  15. package/core/classes/Migration/index.cjs +13 -10
  16. package/core/classes/Migration/index.cjs.map +1 -1
  17. package/core/classes/Migration/index.mjs +14 -11
  18. package/core/classes/Migration/index.mjs.map +1 -1
  19. package/core/classes/{ModelFormatter.cjs → ModelFactory.cjs} +82 -56
  20. package/core/classes/ModelFactory.cjs.map +1 -0
  21. package/core/classes/{ModelFormatter.d.ts → ModelFactory.d.ts} +7 -2
  22. package/core/classes/{ModelFormatter.mjs → ModelFactory.mjs} +82 -56
  23. package/core/classes/ModelFactory.mjs.map +1 -0
  24. package/core/types.d.ts +1 -1
  25. package/dialect/MysqlDialect.cjs +7 -4
  26. package/dialect/MysqlDialect.cjs.map +1 -1
  27. package/dialect/MysqlDialect.d.ts +7 -4
  28. package/dialect/MysqlDialect.mjs +7 -4
  29. package/dialect/MysqlDialect.mjs.map +1 -1
  30. package/dialect/PostgresDialect.cjs +5 -2
  31. package/dialect/PostgresDialect.cjs.map +1 -1
  32. package/dialect/PostgresDialect.d.ts +5 -2
  33. package/dialect/PostgresDialect.mjs +5 -2
  34. package/dialect/PostgresDialect.mjs.map +1 -1
  35. package/dialect/SqliteDialect.cjs +3 -2
  36. package/dialect/SqliteDialect.cjs.map +1 -1
  37. package/dialect/SqliteDialect.d.ts +3 -2
  38. package/dialect/SqliteDialect.mjs +3 -2
  39. package/dialect/SqliteDialect.mjs.map +1 -1
  40. package/dialect/XansqlBridge/XansqlBridgeServer.cjs.map +1 -1
  41. package/dialect/XansqlBridge/XansqlBridgeServer.mjs.map +1 -1
  42. package/dialect/XansqlBridge/base.cjs +10 -5
  43. package/dialect/XansqlBridge/base.cjs.map +1 -1
  44. package/dialect/XansqlBridge/base.mjs +10 -5
  45. package/dialect/XansqlBridge/base.mjs.map +1 -1
  46. package/model/Args/WhereArgs.cjs +5 -8
  47. package/model/Args/WhereArgs.cjs.map +1 -1
  48. package/model/Args/WhereArgs.mjs +6 -9
  49. package/model/Args/WhereArgs.mjs.map +1 -1
  50. package/model/Base.cjs +2 -1
  51. package/model/Base.cjs.map +1 -1
  52. package/model/Base.mjs +2 -1
  53. package/model/Base.mjs.map +1 -1
  54. package/model/Executer/Aggregate/SelectArgs.cjs +2 -1
  55. package/model/Executer/Aggregate/SelectArgs.cjs.map +1 -1
  56. package/model/Executer/Aggregate/SelectArgs.mjs +2 -1
  57. package/model/Executer/Aggregate/SelectArgs.mjs.map +1 -1
  58. package/model/Executer/Aggregate/index.cjs +4 -4
  59. package/model/Executer/Aggregate/index.cjs.map +1 -1
  60. package/model/Executer/Aggregate/index.mjs +4 -4
  61. package/model/Executer/Aggregate/index.mjs.map +1 -1
  62. package/model/Executer/Create/CreateDataArgs.cjs +9 -5
  63. package/model/Executer/Create/CreateDataArgs.cjs.map +1 -1
  64. package/model/Executer/Create/CreateDataArgs.mjs +10 -6
  65. package/model/Executer/Create/CreateDataArgs.mjs.map +1 -1
  66. package/model/Executer/Create/index.cjs +1 -1
  67. package/model/Executer/Create/index.cjs.map +1 -1
  68. package/model/Executer/Create/index.mjs +1 -1
  69. package/model/Executer/Create/index.mjs.map +1 -1
  70. package/model/Executer/Delete/index.cjs +2 -1
  71. package/model/Executer/Delete/index.cjs.map +1 -1
  72. package/model/Executer/Delete/index.mjs +2 -1
  73. package/model/Executer/Delete/index.mjs.map +1 -1
  74. package/model/Executer/Find/SelectArgs.cjs +3 -3
  75. package/model/Executer/Find/SelectArgs.cjs.map +1 -1
  76. package/model/Executer/Find/SelectArgs.mjs +3 -3
  77. package/model/Executer/Find/SelectArgs.mjs.map +1 -1
  78. package/model/Executer/Update/UpdateDataArgs.cjs +4 -4
  79. package/model/Executer/Update/UpdateDataArgs.cjs.map +1 -1
  80. package/model/Executer/Update/UpdateDataArgs.mjs +5 -5
  81. package/model/Executer/Update/UpdateDataArgs.mjs.map +1 -1
  82. package/model/Executer/Update/index.cjs +1 -1
  83. package/model/Executer/Update/index.cjs.map +1 -1
  84. package/model/Executer/Update/index.mjs +1 -1
  85. package/model/Executer/Update/index.mjs.map +1 -1
  86. package/model/include/ValueFormatter.cjs +72 -17
  87. package/model/include/ValueFormatter.cjs.map +1 -1
  88. package/model/include/ValueFormatter.d.ts +1 -1
  89. package/model/include/ValueFormatter.mjs +72 -17
  90. package/model/include/ValueFormatter.mjs.map +1 -1
  91. package/model/index.cjs +8 -7
  92. package/model/index.cjs.map +1 -1
  93. package/model/index.mjs +8 -7
  94. package/model/index.mjs.map +1 -1
  95. package/package.json +12 -7
  96. package/utils/index.cjs +5 -2
  97. package/utils/index.cjs.map +1 -1
  98. package/utils/index.d.ts +2 -1
  99. package/utils/index.mjs +5 -3
  100. package/utils/index.mjs.map +1 -1
  101. package/xt/additional/IP.cjs +22 -0
  102. package/xt/additional/IP.cjs.map +1 -0
  103. package/xt/additional/IP.d.ts +6 -0
  104. package/xt/additional/IP.mjs +20 -0
  105. package/xt/additional/IP.mjs.map +1 -0
  106. package/xt/additional/Name.cjs +21 -0
  107. package/xt/additional/Name.cjs.map +1 -0
  108. package/xt/additional/Name.d.ts +6 -0
  109. package/xt/additional/Name.mjs +19 -0
  110. package/xt/additional/Name.mjs.map +1 -0
  111. package/xt/additional/Password.cjs +25 -0
  112. package/xt/additional/Password.cjs.map +1 -0
  113. package/xt/additional/Password.d.ts +6 -0
  114. package/xt/additional/Password.mjs +23 -0
  115. package/xt/additional/Password.mjs.map +1 -0
  116. package/xt/additional/Phone.cjs +21 -0
  117. package/xt/additional/Phone.cjs.map +1 -0
  118. package/xt/additional/Phone.d.ts +6 -0
  119. package/xt/additional/Phone.mjs +19 -0
  120. package/xt/additional/Phone.mjs.map +1 -0
  121. package/xt/additional/Photo.cjs +21 -0
  122. package/xt/additional/Photo.cjs.map +1 -0
  123. package/xt/additional/Photo.d.ts +6 -0
  124. package/xt/additional/Photo.mjs +19 -0
  125. package/xt/additional/Photo.mjs.map +1 -0
  126. package/xt/additional/Slug.cjs +21 -0
  127. package/xt/additional/Slug.cjs.map +1 -0
  128. package/xt/additional/Slug.d.ts +6 -0
  129. package/xt/additional/Slug.mjs +19 -0
  130. package/xt/additional/Slug.mjs.map +1 -0
  131. package/xt/additional/Url.cjs +26 -0
  132. package/xt/additional/Url.cjs.map +1 -0
  133. package/xt/additional/Url.d.ts +6 -0
  134. package/xt/additional/Url.mjs +24 -0
  135. package/xt/additional/Url.mjs.map +1 -0
  136. package/xt/additional/Username.cjs +21 -0
  137. package/xt/additional/Username.cjs.map +1 -0
  138. package/xt/additional/Username.d.ts +6 -0
  139. package/xt/additional/Username.mjs +19 -0
  140. package/xt/additional/Username.mjs.map +1 -0
  141. package/xt/fields/Array.cjs +9 -2
  142. package/xt/fields/Array.cjs.map +1 -1
  143. package/xt/fields/Array.d.ts +2 -0
  144. package/xt/fields/Array.mjs +9 -2
  145. package/xt/fields/Array.mjs.map +1 -1
  146. package/xt/fields/Boolean.cjs +10 -5
  147. package/xt/fields/Boolean.cjs.map +1 -1
  148. package/xt/fields/Boolean.d.ts +2 -0
  149. package/xt/fields/Boolean.mjs +10 -5
  150. package/xt/fields/Boolean.mjs.map +1 -1
  151. package/xt/fields/Date.cjs +12 -12
  152. package/xt/fields/Date.cjs.map +1 -1
  153. package/xt/fields/Date.d.ts +2 -0
  154. package/xt/fields/Date.mjs +12 -12
  155. package/xt/fields/Date.mjs.map +1 -1
  156. package/xt/fields/Enum.cjs +10 -4
  157. package/xt/fields/Enum.cjs.map +1 -1
  158. package/xt/fields/Enum.d.ts +2 -0
  159. package/xt/fields/Enum.mjs +10 -4
  160. package/xt/fields/Enum.mjs.map +1 -1
  161. package/xt/fields/File.cjs +9 -2
  162. package/xt/fields/File.cjs.map +1 -1
  163. package/xt/fields/File.d.ts +2 -0
  164. package/xt/fields/File.mjs +9 -2
  165. package/xt/fields/File.mjs.map +1 -1
  166. package/xt/fields/IDField.cjs +8 -0
  167. package/xt/fields/IDField.cjs.map +1 -1
  168. package/xt/fields/IDField.d.ts +2 -0
  169. package/xt/fields/IDField.mjs +8 -0
  170. package/xt/fields/IDField.mjs.map +1 -1
  171. package/xt/fields/Number.cjs +10 -5
  172. package/xt/fields/Number.cjs.map +1 -1
  173. package/xt/fields/Number.d.ts +2 -0
  174. package/xt/fields/Number.mjs +10 -5
  175. package/xt/fields/Number.mjs.map +1 -1
  176. package/xt/fields/Object.cjs +10 -5
  177. package/xt/fields/Object.cjs.map +1 -1
  178. package/xt/fields/Object.d.ts +2 -0
  179. package/xt/fields/Object.mjs +10 -5
  180. package/xt/fields/Object.mjs.map +1 -1
  181. package/xt/fields/Record.cjs +10 -5
  182. package/xt/fields/Record.cjs.map +1 -1
  183. package/xt/fields/Record.d.ts +2 -0
  184. package/xt/fields/Record.mjs +10 -5
  185. package/xt/fields/Record.mjs.map +1 -1
  186. package/xt/fields/Schema.cjs +12 -1
  187. package/xt/fields/Schema.cjs.map +1 -1
  188. package/xt/fields/Schema.d.ts +4 -1
  189. package/xt/fields/Schema.mjs +12 -1
  190. package/xt/fields/Schema.mjs.map +1 -1
  191. package/xt/fields/String.cjs +12 -9
  192. package/xt/fields/String.cjs.map +1 -1
  193. package/xt/fields/String.d.ts +2 -0
  194. package/xt/fields/String.mjs +12 -9
  195. package/xt/fields/String.mjs.map +1 -1
  196. package/xt/fields/Tuple.cjs +10 -5
  197. package/xt/fields/Tuple.cjs.map +1 -1
  198. package/xt/fields/Tuple.d.ts +2 -0
  199. package/xt/fields/Tuple.mjs +10 -5
  200. package/xt/fields/Tuple.mjs.map +1 -1
  201. package/xt/fields/Union.cjs +10 -5
  202. package/xt/fields/Union.cjs.map +1 -1
  203. package/xt/fields/Union.d.ts +2 -0
  204. package/xt/fields/Union.mjs +10 -5
  205. package/xt/fields/Union.mjs.map +1 -1
  206. package/xt/index.cjs +16 -100
  207. package/xt/index.cjs.map +1 -1
  208. package/xt/index.d.ts +16 -9
  209. package/xt/index.mjs +16 -100
  210. package/xt/index.mjs.map +1 -1
  211. package/core/classes/ModelFormatter.cjs.map +0 -1
  212. package/core/classes/ModelFormatter.mjs.map +0 -1
@@ -7,65 +7,86 @@ var core_XansqlError = require('../XansqlError.cjs');
7
7
  /**
8
8
  * this class will format the models and assign relationships
9
9
  */
10
- class ModelFormatter {
10
+ class ModelFactgory {
11
11
  constructor(xansql) {
12
12
  this.isFormated = false;
13
- this.restricted_columns = [
14
- // custom
15
- // "OPTIONAL", "NULLABLE", "META", "METAARRAY", "SCHEMA", "ARRAY",
16
- // "EQUALS", "NOT", "LT", "LTE", "GT", "GTE", "IN", "NOTIN", "BETWEEN", "NOTBETWEEN", "CONTAINS", "NOTCONTAINS", "STARTSWITH", "ENDSWITH", "ISNULL", "ISNOTNULL", "ISEMPTY", "ISNOTEMPTY", "ISTRUE", "ISFALSE",
17
- // "AGGREGATE",
18
- ];
13
+ this.restricted_columns = [];
14
+ this.models = new Map();
19
15
  this.xansql = xansql;
20
16
  }
21
17
  restrictedColumn(column) {
22
18
  return this.restricted_columns.includes(column.toUpperCase());
23
19
  }
24
- format() {
25
- if (this.isFormated)
26
- return this.xansql.ModelFactory;
27
- this.isFormated = true;
28
- const models = this.xansql.ModelFactory;
29
- // sort models by foreign key dependencies
30
- const sortedTables = [];
31
- for (let table of models.keys()) {
32
- const model = models.get(table);
33
- const schema = model.schema;
34
- for (let column in schema) {
35
- let field = schema[column];
20
+ /**
21
+ * Topological sort with cycle detection
22
+ */
23
+ sortModelsByDependencies(models) {
24
+ const graph = new Map();
25
+ const visiting = new Set();
26
+ const visited = new Set();
27
+ const result = [];
28
+ // build dependency graph
29
+ for (const [table, model] of models) {
30
+ const deps = new Set();
31
+ for (const column in model.schema) {
32
+ const field = model.schema[column];
36
33
  if (core_classes_ForeignInfo.isSchema(field)) {
37
- const foreignInfo = core_classes_ForeignInfo.get(model, column);
38
- const foreignTable = foreignInfo.table;
39
- const indexOfMainTable = sortedTables.indexOf(table);
40
- const indexOfForeignTable = sortedTables.indexOf(foreignTable);
41
- if (indexOfForeignTable === -1) {
42
- // foreign table not in sorted list, add it before main table
43
- sortedTables.splice(indexOfMainTable, 0, foreignTable);
44
- }
45
- else if (indexOfForeignTable > indexOfMainTable) {
46
- // foreign table is after main table, move it before
47
- sortedTables.splice(indexOfForeignTable, 1);
48
- sortedTables.splice(indexOfMainTable, 0, foreignTable);
49
- }
34
+ deps.add(field.table);
50
35
  }
51
36
  }
52
- if (!sortedTables.includes(table)) {
53
- sortedTables.push(table);
37
+ graph.set(table, deps);
38
+ }
39
+ const visit = (table) => {
40
+ if (visiting.has(table)) {
41
+ throw new core_XansqlError({
42
+ message: `Circular foreign key detected involving "${table}"`,
43
+ model: table
44
+ });
54
45
  }
46
+ if (visited.has(table))
47
+ return;
48
+ visiting.add(table);
49
+ const deps = graph.get(table);
50
+ if (deps) {
51
+ for (const dep of deps) {
52
+ if (!models.has(dep)) {
53
+ throw new core_XansqlError({
54
+ message: `Foreign model "${dep}" not found while sorting "${table}"`,
55
+ model: table
56
+ });
57
+ }
58
+ visit(dep);
59
+ }
60
+ }
61
+ visiting.delete(table);
62
+ visited.add(table);
63
+ result.push(table);
64
+ };
65
+ for (const table of models.keys()) {
66
+ visit(table);
55
67
  }
56
- // update models based with sorted tables
68
+ return result;
69
+ }
70
+ format() {
71
+ if (this.isFormated) {
72
+ return this.models;
73
+ }
74
+ const models = this.models;
75
+ // Proper, safe table sorting
76
+ const sortedTables = this.sortModelsByDependencies(models);
77
+ // rebuild model map in correct order
57
78
  const sortedModels = new Map();
58
- for (let table of sortedTables) {
79
+ for (const table of sortedTables) {
59
80
  const model = models.get(table);
60
81
  sortedModels.set(table, model);
61
82
  }
62
- // assign relationships
63
83
  models.clear();
64
- for (let [table, model] of sortedModels) {
84
+ for (const [table, model] of sortedModels) {
65
85
  models.set(table, model);
66
86
  }
67
- for (let model of models.values()) {
68
- for (let column in model.schema) {
87
+ // relationship wiring
88
+ for (const model of models.values()) {
89
+ for (const column in model.schema) {
69
90
  if (this.restrictedColumn(column)) {
70
91
  throw new core_XansqlError({
71
92
  message: `Column name "${column}" in model "${model.table}" is restricted and cannot be used.`,
@@ -73,7 +94,7 @@ class ModelFormatter {
73
94
  column,
74
95
  });
75
96
  }
76
- let field = model.schema[column];
97
+ const field = model.schema[column];
77
98
  if (core_classes_ForeignInfo.isSchema(field)) {
78
99
  this.formatIsSchema(model, column);
79
100
  }
@@ -82,19 +103,21 @@ class ModelFormatter {
82
103
  }
83
104
  }
84
105
  }
106
+ this.isFormated = true;
85
107
  return models;
86
108
  }
87
109
  formatIsSchema(model, column) {
88
- const models = this.xansql.ModelFactory;
89
- let field = model.schema[column];
110
+ const models = this.models;
111
+ const field = model.schema[column];
90
112
  const FModel = models.get(field.table);
91
113
  if (!FModel) {
92
114
  throw new core_XansqlError({
93
- message: `Foreign model ${field.table} not found for ${model.table}.${column}`,
115
+ message: `Foreign model "${field.table}" not found for ${model.table}.${column}`,
94
116
  model: model.table,
95
117
  column
96
118
  });
97
119
  }
120
+ // ensure reciprocal field exists
98
121
  if (field.column in FModel.schema) {
99
122
  const foreignCol = FModel.schema[field.column];
100
123
  if (core_classes_ForeignInfo.isArray(foreignCol)) {
@@ -117,26 +140,29 @@ class ModelFormatter {
117
140
  }
118
141
  else {
119
142
  const n = xt_index.schema(model.table, column).nullable();
120
- n.dynamic = true; // to identify that this is a dynamically added field
143
+ n.dynamic = true;
121
144
  FModel.schema[field.column] = xt_index.array(n);
122
145
  models.set(FModel.table, FModel);
123
146
  }
124
147
  }
125
148
  formatIsArray(model, column) {
126
- const models = this.xansql.ModelFactory;
127
- let field = model.schema[column];
149
+ var _a, _b, _c, _d;
150
+ const models = this.models;
151
+ const field = model.schema[column];
128
152
  const FSchemaField = field.type;
129
153
  const FModel = models.get(FSchemaField.table);
130
154
  if (!FModel) {
131
155
  throw new core_XansqlError({
132
- message: `Foreign model ${FSchemaField.table} not found for ${model.table}.${column}`,
156
+ message: `Foreign model "${FSchemaField.table}" not found for ${model.table}.${column}`,
133
157
  model: model.table,
134
158
  column
135
159
  });
136
160
  }
137
161
  if (FSchemaField.column in FModel.schema) {
138
162
  const foreignCol = FModel.schema[FSchemaField.column];
139
- if (!core_classes_ForeignInfo.isSchema(foreignCol) || foreignCol.table !== model.table || foreignCol.column !== column) {
163
+ if (!core_classes_ForeignInfo.isSchema(foreignCol) ||
164
+ foreignCol.table !== model.table ||
165
+ foreignCol.column !== column) {
140
166
  throw new core_XansqlError({
141
167
  message: `Foreign column ${FSchemaField.table}.${FSchemaField.column} does not reference back to ${model.table}.${column}`,
142
168
  model: model.table,
@@ -146,20 +172,20 @@ class ModelFormatter {
146
172
  }
147
173
  else {
148
174
  const n = xt_index.schema(model.table, column);
149
- if (FSchemaField.meta.nullable)
175
+ if ((_a = FSchemaField.meta) === null || _a === void 0 ? void 0 : _a.nullable)
150
176
  n.nullable();
151
- if (FSchemaField.meta.optional)
177
+ if ((_b = FSchemaField.meta) === null || _b === void 0 ? void 0 : _b.optional)
152
178
  n.optional();
153
- if (FSchemaField.meta.default !== undefined)
179
+ if (((_c = FSchemaField.meta) === null || _c === void 0 ? void 0 : _c.default) !== undefined)
154
180
  n.default(FSchemaField.meta.default);
155
- if (FSchemaField.meta.transform)
181
+ if ((_d = FSchemaField.meta) === null || _d === void 0 ? void 0 : _d.transform)
156
182
  n.transform(FSchemaField.meta.transform);
157
- n.dynamic = true; // to identify that this is a dynamically added field
183
+ n.dynamic = true;
158
184
  FModel.schema[FSchemaField.column] = n;
159
185
  models.set(FModel.table, FModel);
160
186
  }
161
187
  }
162
188
  }
163
189
 
164
- module.exports = ModelFormatter;
165
- //# sourceMappingURL=ModelFormatter.cjs.map
190
+ module.exports = ModelFactgory;
191
+ //# sourceMappingURL=ModelFactory.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ModelFactory.cjs","sources":["../../../src/core/classes/ModelFactory.ts"],"sourcesContent":["import xt from \"../../xt\";\nimport Model from \"../../model\";\nimport XqlSchema from \"../../xt/fields/Schema\";\nimport Xansql from \"../Xansql\";\nimport Foreign from \"./ForeignInfo\";\nimport XansqlError from \"../XansqlError\";\n\n/**\n * this class will format the models and assign relationships\n */\nclass ModelFactgory {\n private xansql: Xansql;\n private isFormated: boolean = false;\n private restricted_columns: string[] = [];\n readonly models: Map<string, Model> = new Map();\n\n constructor(xansql: Xansql) {\n this.xansql = xansql;\n }\n\n private restrictedColumn(column: string): boolean {\n return this.restricted_columns.includes(column.toUpperCase());\n }\n\n /**\n * Topological sort with cycle detection\n */\n private sortModelsByDependencies(models: Map<string, Model>): string[] {\n const graph = new Map<string, Set<string>>();\n const visiting = new Set<string>();\n const visited = new Set<string>();\n const result: string[] = [];\n\n // build dependency graph\n for (const [table, model] of models) {\n const deps = new Set<string>();\n for (const column in model.schema) {\n const field: any = model.schema[column];\n if (Foreign.isSchema(field)) {\n deps.add(field.table);\n }\n }\n graph.set(table, deps);\n }\n\n const visit = (table: string) => {\n if (visiting.has(table)) {\n throw new XansqlError({\n message: `Circular foreign key detected involving \"${table}\"`,\n model: table\n });\n }\n\n if (visited.has(table)) return;\n\n visiting.add(table);\n\n const deps = graph.get(table);\n if (deps) {\n for (const dep of deps) {\n if (!models.has(dep)) {\n throw new XansqlError({\n message: `Foreign model \"${dep}\" not found while sorting \"${table}\"`,\n model: table\n });\n }\n visit(dep);\n }\n }\n\n visiting.delete(table);\n visited.add(table);\n result.push(table);\n };\n\n for (const table of models.keys()) {\n visit(table);\n }\n\n return result;\n }\n\n format() {\n if (this.isFormated) {\n return this.models;\n }\n const models = this.models;\n\n // Proper, safe table sorting\n const sortedTables = this.sortModelsByDependencies(models);\n\n // rebuild model map in correct order\n const sortedModels = new Map<string, Model>();\n for (const table of sortedTables) {\n const model = models.get(table) as Model;\n sortedModels.set(table, model);\n }\n\n models.clear();\n for (const [table, model] of sortedModels) {\n models.set(table, model);\n }\n\n // relationship wiring\n for (const model of models.values()) {\n for (const column in model.schema) {\n if (this.restrictedColumn(column)) {\n throw new XansqlError({\n message: `Column name \"${column}\" in model \"${model.table}\" is restricted and cannot be used.`,\n model: model.table,\n column,\n });\n }\n\n const field: any = model.schema[column];\n\n if (Foreign.isSchema(field)) {\n this.formatIsSchema(model, column);\n } else if (Foreign.isArray(field)) {\n this.formatIsArray(model, column);\n }\n }\n }\n\n this.isFormated = true;\n return models;\n }\n\n private formatIsSchema(model: Model, column: string) {\n const models = this.models;\n const field: any = model.schema[column];\n\n const FModel = models.get(field.table);\n if (!FModel) {\n throw new XansqlError({\n message: `Foreign model \"${field.table}\" not found for ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n\n // ensure reciprocal field exists\n if (field.column in FModel.schema) {\n const foreignCol = FModel.schema[field.column];\n\n if (Foreign.isArray(foreignCol)) {\n const foreignType = (foreignCol as any).type as XqlSchema;\n if (foreignType.table !== model.table || foreignType.column !== column) {\n throw new XansqlError({\n message: `Foreign column ${field.table}.${field.column} does not reference back to ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n } else {\n throw new XansqlError({\n message: `Foreign column ${field.table}.${field.column} is not an array referencing back to ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n } else {\n const n = xt.schema(model.table, column).nullable();\n (n as any).dynamic = true;\n FModel.schema[field.column] = xt.array(n);\n models.set(FModel.table, FModel);\n }\n }\n\n private formatIsArray(model: Model, column: string) {\n const models = this.models;\n const field: any = model.schema[column];\n const FSchemaField = (field as any).type as XqlSchema;\n\n const FModel = models.get(FSchemaField.table);\n if (!FModel) {\n throw new XansqlError({\n message: `Foreign model \"${FSchemaField.table}\" not found for ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n\n if (FSchemaField.column in FModel.schema) {\n const foreignCol = FModel.schema[FSchemaField.column] as any;\n\n if (\n !Foreign.isSchema(foreignCol) ||\n foreignCol.table !== model.table ||\n foreignCol.column !== column\n ) {\n throw new XansqlError({\n message: `Foreign column ${FSchemaField.table}.${FSchemaField.column} does not reference back to ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n } else {\n const n = xt.schema(model.table, column);\n\n if (FSchemaField.meta?.nullable) n.nullable();\n if (FSchemaField.meta?.optional) n.optional();\n if (FSchemaField.meta?.default !== undefined) n.default(FSchemaField.meta.default);\n if (FSchemaField.meta?.transform) n.transform(FSchemaField.meta.transform);\n\n (n as any).dynamic = true;\n FModel.schema[FSchemaField.column] = n;\n models.set(FModel.table, FModel);\n }\n }\n}\n\nexport default ModelFactgory;\n"],"names":["Foreign","XansqlError","xt"],"mappings":"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"}
@@ -3,14 +3,19 @@ import Xansql from "../Xansql";
3
3
  /**
4
4
  * this class will format the models and assign relationships
5
5
  */
6
- declare class ModelFormatter {
6
+ declare class ModelFactgory {
7
7
  private xansql;
8
8
  private isFormated;
9
9
  private restricted_columns;
10
+ readonly models: Map<string, Model>;
10
11
  constructor(xansql: Xansql);
11
12
  private restrictedColumn;
13
+ /**
14
+ * Topological sort with cycle detection
15
+ */
16
+ private sortModelsByDependencies;
12
17
  format(): Map<string, Model>;
13
18
  private formatIsSchema;
14
19
  private formatIsArray;
15
20
  }
16
- export default ModelFormatter;
21
+ export default ModelFactgory;
@@ -5,65 +5,86 @@ import XansqlError from '../XansqlError.mjs';
5
5
  /**
6
6
  * this class will format the models and assign relationships
7
7
  */
8
- class ModelFormatter {
8
+ class ModelFactgory {
9
9
  constructor(xansql) {
10
10
  this.isFormated = false;
11
- this.restricted_columns = [
12
- // custom
13
- // "OPTIONAL", "NULLABLE", "META", "METAARRAY", "SCHEMA", "ARRAY",
14
- // "EQUALS", "NOT", "LT", "LTE", "GT", "GTE", "IN", "NOTIN", "BETWEEN", "NOTBETWEEN", "CONTAINS", "NOTCONTAINS", "STARTSWITH", "ENDSWITH", "ISNULL", "ISNOTNULL", "ISEMPTY", "ISNOTEMPTY", "ISTRUE", "ISFALSE",
15
- // "AGGREGATE",
16
- ];
11
+ this.restricted_columns = [];
12
+ this.models = new Map();
17
13
  this.xansql = xansql;
18
14
  }
19
15
  restrictedColumn(column) {
20
16
  return this.restricted_columns.includes(column.toUpperCase());
21
17
  }
22
- format() {
23
- if (this.isFormated)
24
- return this.xansql.ModelFactory;
25
- this.isFormated = true;
26
- const models = this.xansql.ModelFactory;
27
- // sort models by foreign key dependencies
28
- const sortedTables = [];
29
- for (let table of models.keys()) {
30
- const model = models.get(table);
31
- const schema = model.schema;
32
- for (let column in schema) {
33
- let field = schema[column];
18
+ /**
19
+ * Topological sort with cycle detection
20
+ */
21
+ sortModelsByDependencies(models) {
22
+ const graph = new Map();
23
+ const visiting = new Set();
24
+ const visited = new Set();
25
+ const result = [];
26
+ // build dependency graph
27
+ for (const [table, model] of models) {
28
+ const deps = new Set();
29
+ for (const column in model.schema) {
30
+ const field = model.schema[column];
34
31
  if (Foreign.isSchema(field)) {
35
- const foreignInfo = Foreign.get(model, column);
36
- const foreignTable = foreignInfo.table;
37
- const indexOfMainTable = sortedTables.indexOf(table);
38
- const indexOfForeignTable = sortedTables.indexOf(foreignTable);
39
- if (indexOfForeignTable === -1) {
40
- // foreign table not in sorted list, add it before main table
41
- sortedTables.splice(indexOfMainTable, 0, foreignTable);
42
- }
43
- else if (indexOfForeignTable > indexOfMainTable) {
44
- // foreign table is after main table, move it before
45
- sortedTables.splice(indexOfForeignTable, 1);
46
- sortedTables.splice(indexOfMainTable, 0, foreignTable);
47
- }
32
+ deps.add(field.table);
48
33
  }
49
34
  }
50
- if (!sortedTables.includes(table)) {
51
- sortedTables.push(table);
35
+ graph.set(table, deps);
36
+ }
37
+ const visit = (table) => {
38
+ if (visiting.has(table)) {
39
+ throw new XansqlError({
40
+ message: `Circular foreign key detected involving "${table}"`,
41
+ model: table
42
+ });
52
43
  }
44
+ if (visited.has(table))
45
+ return;
46
+ visiting.add(table);
47
+ const deps = graph.get(table);
48
+ if (deps) {
49
+ for (const dep of deps) {
50
+ if (!models.has(dep)) {
51
+ throw new XansqlError({
52
+ message: `Foreign model "${dep}" not found while sorting "${table}"`,
53
+ model: table
54
+ });
55
+ }
56
+ visit(dep);
57
+ }
58
+ }
59
+ visiting.delete(table);
60
+ visited.add(table);
61
+ result.push(table);
62
+ };
63
+ for (const table of models.keys()) {
64
+ visit(table);
53
65
  }
54
- // update models based with sorted tables
66
+ return result;
67
+ }
68
+ format() {
69
+ if (this.isFormated) {
70
+ return this.models;
71
+ }
72
+ const models = this.models;
73
+ // Proper, safe table sorting
74
+ const sortedTables = this.sortModelsByDependencies(models);
75
+ // rebuild model map in correct order
55
76
  const sortedModels = new Map();
56
- for (let table of sortedTables) {
77
+ for (const table of sortedTables) {
57
78
  const model = models.get(table);
58
79
  sortedModels.set(table, model);
59
80
  }
60
- // assign relationships
61
81
  models.clear();
62
- for (let [table, model] of sortedModels) {
82
+ for (const [table, model] of sortedModels) {
63
83
  models.set(table, model);
64
84
  }
65
- for (let model of models.values()) {
66
- for (let column in model.schema) {
85
+ // relationship wiring
86
+ for (const model of models.values()) {
87
+ for (const column in model.schema) {
67
88
  if (this.restrictedColumn(column)) {
68
89
  throw new XansqlError({
69
90
  message: `Column name "${column}" in model "${model.table}" is restricted and cannot be used.`,
@@ -71,7 +92,7 @@ class ModelFormatter {
71
92
  column,
72
93
  });
73
94
  }
74
- let field = model.schema[column];
95
+ const field = model.schema[column];
75
96
  if (Foreign.isSchema(field)) {
76
97
  this.formatIsSchema(model, column);
77
98
  }
@@ -80,19 +101,21 @@ class ModelFormatter {
80
101
  }
81
102
  }
82
103
  }
104
+ this.isFormated = true;
83
105
  return models;
84
106
  }
85
107
  formatIsSchema(model, column) {
86
- const models = this.xansql.ModelFactory;
87
- let field = model.schema[column];
108
+ const models = this.models;
109
+ const field = model.schema[column];
88
110
  const FModel = models.get(field.table);
89
111
  if (!FModel) {
90
112
  throw new XansqlError({
91
- message: `Foreign model ${field.table} not found for ${model.table}.${column}`,
113
+ message: `Foreign model "${field.table}" not found for ${model.table}.${column}`,
92
114
  model: model.table,
93
115
  column
94
116
  });
95
117
  }
118
+ // ensure reciprocal field exists
96
119
  if (field.column in FModel.schema) {
97
120
  const foreignCol = FModel.schema[field.column];
98
121
  if (Foreign.isArray(foreignCol)) {
@@ -115,26 +138,29 @@ class ModelFormatter {
115
138
  }
116
139
  else {
117
140
  const n = xt.schema(model.table, column).nullable();
118
- n.dynamic = true; // to identify that this is a dynamically added field
141
+ n.dynamic = true;
119
142
  FModel.schema[field.column] = xt.array(n);
120
143
  models.set(FModel.table, FModel);
121
144
  }
122
145
  }
123
146
  formatIsArray(model, column) {
124
- const models = this.xansql.ModelFactory;
125
- let field = model.schema[column];
147
+ var _a, _b, _c, _d;
148
+ const models = this.models;
149
+ const field = model.schema[column];
126
150
  const FSchemaField = field.type;
127
151
  const FModel = models.get(FSchemaField.table);
128
152
  if (!FModel) {
129
153
  throw new XansqlError({
130
- message: `Foreign model ${FSchemaField.table} not found for ${model.table}.${column}`,
154
+ message: `Foreign model "${FSchemaField.table}" not found for ${model.table}.${column}`,
131
155
  model: model.table,
132
156
  column
133
157
  });
134
158
  }
135
159
  if (FSchemaField.column in FModel.schema) {
136
160
  const foreignCol = FModel.schema[FSchemaField.column];
137
- if (!Foreign.isSchema(foreignCol) || foreignCol.table !== model.table || foreignCol.column !== column) {
161
+ if (!Foreign.isSchema(foreignCol) ||
162
+ foreignCol.table !== model.table ||
163
+ foreignCol.column !== column) {
138
164
  throw new XansqlError({
139
165
  message: `Foreign column ${FSchemaField.table}.${FSchemaField.column} does not reference back to ${model.table}.${column}`,
140
166
  model: model.table,
@@ -144,20 +170,20 @@ class ModelFormatter {
144
170
  }
145
171
  else {
146
172
  const n = xt.schema(model.table, column);
147
- if (FSchemaField.meta.nullable)
173
+ if ((_a = FSchemaField.meta) === null || _a === void 0 ? void 0 : _a.nullable)
148
174
  n.nullable();
149
- if (FSchemaField.meta.optional)
175
+ if ((_b = FSchemaField.meta) === null || _b === void 0 ? void 0 : _b.optional)
150
176
  n.optional();
151
- if (FSchemaField.meta.default !== undefined)
177
+ if (((_c = FSchemaField.meta) === null || _c === void 0 ? void 0 : _c.default) !== undefined)
152
178
  n.default(FSchemaField.meta.default);
153
- if (FSchemaField.meta.transform)
179
+ if ((_d = FSchemaField.meta) === null || _d === void 0 ? void 0 : _d.transform)
154
180
  n.transform(FSchemaField.meta.transform);
155
- n.dynamic = true; // to identify that this is a dynamically added field
181
+ n.dynamic = true;
156
182
  FModel.schema[FSchemaField.column] = n;
157
183
  models.set(FModel.table, FModel);
158
184
  }
159
185
  }
160
186
  }
161
187
 
162
- export { ModelFormatter as default };
163
- //# sourceMappingURL=ModelFormatter.mjs.map
188
+ export { ModelFactgory as default };
189
+ //# sourceMappingURL=ModelFactory.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ModelFactory.mjs","sources":["../../../src/core/classes/ModelFactory.ts"],"sourcesContent":["import xt from \"../../xt\";\nimport Model from \"../../model\";\nimport XqlSchema from \"../../xt/fields/Schema\";\nimport Xansql from \"../Xansql\";\nimport Foreign from \"./ForeignInfo\";\nimport XansqlError from \"../XansqlError\";\n\n/**\n * this class will format the models and assign relationships\n */\nclass ModelFactgory {\n private xansql: Xansql;\n private isFormated: boolean = false;\n private restricted_columns: string[] = [];\n readonly models: Map<string, Model> = new Map();\n\n constructor(xansql: Xansql) {\n this.xansql = xansql;\n }\n\n private restrictedColumn(column: string): boolean {\n return this.restricted_columns.includes(column.toUpperCase());\n }\n\n /**\n * Topological sort with cycle detection\n */\n private sortModelsByDependencies(models: Map<string, Model>): string[] {\n const graph = new Map<string, Set<string>>();\n const visiting = new Set<string>();\n const visited = new Set<string>();\n const result: string[] = [];\n\n // build dependency graph\n for (const [table, model] of models) {\n const deps = new Set<string>();\n for (const column in model.schema) {\n const field: any = model.schema[column];\n if (Foreign.isSchema(field)) {\n deps.add(field.table);\n }\n }\n graph.set(table, deps);\n }\n\n const visit = (table: string) => {\n if (visiting.has(table)) {\n throw new XansqlError({\n message: `Circular foreign key detected involving \"${table}\"`,\n model: table\n });\n }\n\n if (visited.has(table)) return;\n\n visiting.add(table);\n\n const deps = graph.get(table);\n if (deps) {\n for (const dep of deps) {\n if (!models.has(dep)) {\n throw new XansqlError({\n message: `Foreign model \"${dep}\" not found while sorting \"${table}\"`,\n model: table\n });\n }\n visit(dep);\n }\n }\n\n visiting.delete(table);\n visited.add(table);\n result.push(table);\n };\n\n for (const table of models.keys()) {\n visit(table);\n }\n\n return result;\n }\n\n format() {\n if (this.isFormated) {\n return this.models;\n }\n const models = this.models;\n\n // Proper, safe table sorting\n const sortedTables = this.sortModelsByDependencies(models);\n\n // rebuild model map in correct order\n const sortedModels = new Map<string, Model>();\n for (const table of sortedTables) {\n const model = models.get(table) as Model;\n sortedModels.set(table, model);\n }\n\n models.clear();\n for (const [table, model] of sortedModels) {\n models.set(table, model);\n }\n\n // relationship wiring\n for (const model of models.values()) {\n for (const column in model.schema) {\n if (this.restrictedColumn(column)) {\n throw new XansqlError({\n message: `Column name \"${column}\" in model \"${model.table}\" is restricted and cannot be used.`,\n model: model.table,\n column,\n });\n }\n\n const field: any = model.schema[column];\n\n if (Foreign.isSchema(field)) {\n this.formatIsSchema(model, column);\n } else if (Foreign.isArray(field)) {\n this.formatIsArray(model, column);\n }\n }\n }\n\n this.isFormated = true;\n return models;\n }\n\n private formatIsSchema(model: Model, column: string) {\n const models = this.models;\n const field: any = model.schema[column];\n\n const FModel = models.get(field.table);\n if (!FModel) {\n throw new XansqlError({\n message: `Foreign model \"${field.table}\" not found for ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n\n // ensure reciprocal field exists\n if (field.column in FModel.schema) {\n const foreignCol = FModel.schema[field.column];\n\n if (Foreign.isArray(foreignCol)) {\n const foreignType = (foreignCol as any).type as XqlSchema;\n if (foreignType.table !== model.table || foreignType.column !== column) {\n throw new XansqlError({\n message: `Foreign column ${field.table}.${field.column} does not reference back to ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n } else {\n throw new XansqlError({\n message: `Foreign column ${field.table}.${field.column} is not an array referencing back to ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n } else {\n const n = xt.schema(model.table, column).nullable();\n (n as any).dynamic = true;\n FModel.schema[field.column] = xt.array(n);\n models.set(FModel.table, FModel);\n }\n }\n\n private formatIsArray(model: Model, column: string) {\n const models = this.models;\n const field: any = model.schema[column];\n const FSchemaField = (field as any).type as XqlSchema;\n\n const FModel = models.get(FSchemaField.table);\n if (!FModel) {\n throw new XansqlError({\n message: `Foreign model \"${FSchemaField.table}\" not found for ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n\n if (FSchemaField.column in FModel.schema) {\n const foreignCol = FModel.schema[FSchemaField.column] as any;\n\n if (\n !Foreign.isSchema(foreignCol) ||\n foreignCol.table !== model.table ||\n foreignCol.column !== column\n ) {\n throw new XansqlError({\n message: `Foreign column ${FSchemaField.table}.${FSchemaField.column} does not reference back to ${model.table}.${column}`,\n model: model.table,\n column\n });\n }\n } else {\n const n = xt.schema(model.table, column);\n\n if (FSchemaField.meta?.nullable) n.nullable();\n if (FSchemaField.meta?.optional) n.optional();\n if (FSchemaField.meta?.default !== undefined) n.default(FSchemaField.meta.default);\n if (FSchemaField.meta?.transform) n.transform(FSchemaField.meta.transform);\n\n (n as any).dynamic = true;\n FModel.schema[FSchemaField.column] = n;\n models.set(FModel.table, FModel);\n }\n }\n}\n\nexport default ModelFactgory;\n"],"names":[],"mappings":"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"}
package/core/types.d.ts CHANGED
@@ -48,9 +48,9 @@ export type XansqlFileConfig = {
48
48
  };
49
49
  export type XansqlDialect = {
50
50
  engine: XansqlDialectEngine;
51
+ file?: XansqlFileConfig;
51
52
  execute: (sql: string, xansql: Xansql) => Promise<ExecuterResult | null>;
52
53
  getSchema: (xansql: Xansql) => Promise<XansqlDialectSchemaType | void>;
53
- file?: XansqlFileConfig;
54
54
  };
55
55
  export type XansqlSocket = {
56
56
  open: (socket: WebSocket) => Promise<void>;
@@ -1,14 +1,16 @@
1
1
  'use strict';
2
2
 
3
+ var tslib = require('tslib');
3
4
  var mysql = require('mysql2/promise');
4
5
 
5
- const MysqlDialect = (config) => {
6
+ const MysqlDialect = (_a) => {
7
+ var { file } = _a, config = tslib.__rest(_a, ["file"]);
6
8
  const pool = mysql.createPool(typeof config === 'string' ? { uri: config } : config);
7
- const execute = async (sql, params = []) => {
9
+ const execute = async (sql) => {
8
10
  var _a, _b;
9
11
  const conn = await pool.getConnection();
10
12
  try {
11
- const [rows] = await conn.query(sql, params);
13
+ const [rows] = await conn.query(sql);
12
14
  const result = rows;
13
15
  return {
14
16
  results: result,
@@ -66,7 +68,8 @@ const MysqlDialect = (config) => {
66
68
  return {
67
69
  engine: 'mysql',
68
70
  execute,
69
- getSchema
71
+ getSchema,
72
+ file
70
73
  };
71
74
  };
72
75
 
@@ -1 +1 @@
1
- {"version":3,"file":"MysqlDialect.cjs","sources":["../../src/dialect/MysqlDialect.ts"],"sourcesContent":["import { PoolOptions } from 'mysql2';\nimport mysql from 'mysql2/promise';\nimport { ExecuterResult } from '../core/types';\n\nconst MysqlDialect = (config: string | PoolOptions) => {\n const pool = mysql.createPool(\n typeof config === 'string' ? { uri: config } : config\n );\n\n const execute = async (sql: string, params: any[] = []): Promise<ExecuterResult> => {\n const conn = await pool.getConnection();\n try {\n const [rows] = await conn.query(sql, params);\n const result: any = rows;\n\n return {\n results: result,\n insertId: result?.insertId ?? 0,\n affectedRows: result?.affectedRows ?? 0\n };\n } finally {\n conn.release();\n }\n };\n\n const getSchema = async () => {\n const conn = await pool.getConnection();\n\n try {\n const [tables] = await conn.query<any[]>(\n `SELECT table_name as name\n FROM information_schema.tables \n WHERE table_schema = DATABASE();`\n );\n\n const schema: Record<string, any[]> = {};\n\n for (const t of tables) {\n const table = t.name;\n schema[table] = [];\n\n // Columns\n const [columns] = await conn.query<any[]>(\n `SELECT \n COLUMN_NAME as name,\n COLUMN_TYPE as type,\n IS_NULLABLE,\n COLUMN_DEFAULT,\n COLUMN_KEY\n FROM information_schema.columns\n WHERE table_schema = DATABASE()\n AND table_name = ?`,\n [table]\n );\n\n // Indexes\n const [indexes] = await conn.query<any[]>(\n `SHOW INDEX FROM \\`${table}\\``\n );\n\n for (const col of columns) {\n const colName = col.name;\n\n const isIndexed = indexes.some(i => i.Column_name === colName);\n const isUnique = indexes.some(i => i.Column_name === colName && i.Non_unique === 0);\n\n schema[table].push({\n name: colName,\n type: col.type,\n notnull: col.IS_NULLABLE === \"NO\",\n default_value: col.COLUMN_DEFAULT,\n pk: col.COLUMN_KEY === \"PRI\",\n index: isIndexed,\n unique: isUnique,\n });\n }\n }\n\n return schema;\n } finally {\n conn.release();\n }\n };\n\n return {\n engine: 'mysql' as const,\n execute,\n getSchema\n };\n};\n\nexport default MysqlDialect;\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"MysqlDialect.cjs","sources":["../../src/dialect/MysqlDialect.ts"],"sourcesContent":["import { PoolOptions } from 'mysql2';\nimport mysql from 'mysql2/promise';\nimport { ExecuterResult, XansqlDialectEngine, XansqlFileConfig } from '../core/types';\n\nconst MysqlDialect = ({ file, ...config }: PoolOptions & { file?: XansqlFileConfig }) => {\n const pool = mysql.createPool(typeof config === 'string' ? { uri: config } : config);\n\n const execute = async (sql: string): Promise<ExecuterResult> => {\n const conn = await pool.getConnection();\n try {\n const [rows] = await conn.query(sql);\n const result: any = rows;\n\n return {\n results: result,\n insertId: result?.insertId ?? 0,\n affectedRows: result?.affectedRows ?? 0\n };\n } finally {\n conn.release();\n }\n };\n\n const getSchema = async () => {\n const conn = await pool.getConnection();\n\n try {\n const [tables] = await conn.query<any[]>(\n `SELECT table_name as name\n FROM information_schema.tables \n WHERE table_schema = DATABASE();`\n );\n\n const schema: Record<string, any[]> = {};\n\n for (const t of tables) {\n const table = t.name;\n schema[table] = [];\n\n // Columns\n const [columns] = await conn.query<any[]>(\n `SELECT \n COLUMN_NAME as name,\n COLUMN_TYPE as type,\n IS_NULLABLE,\n COLUMN_DEFAULT,\n COLUMN_KEY\n FROM information_schema.columns\n WHERE table_schema = DATABASE()\n AND table_name = ?`,\n [table]\n );\n\n // Indexes\n const [indexes] = await conn.query<any[]>(\n `SHOW INDEX FROM \\`${table}\\``\n );\n\n for (const col of columns) {\n const colName = col.name;\n\n const isIndexed = indexes.some(i => i.Column_name === colName);\n const isUnique = indexes.some(i => i.Column_name === colName && i.Non_unique === 0);\n\n schema[table].push({\n name: colName,\n type: col.type,\n notnull: col.IS_NULLABLE === \"NO\",\n default_value: col.COLUMN_DEFAULT,\n pk: col.COLUMN_KEY === \"PRI\",\n index: isIndexed,\n unique: isUnique,\n });\n }\n }\n\n return schema;\n } finally {\n conn.release();\n }\n };\n\n return {\n engine: 'mysql' as XansqlDialectEngine,\n execute,\n getSchema,\n file\n };\n};\n\nexport default MysqlDialect;\n"],"names":["__rest"],"mappings":";;;;;AAIA,MAAM,YAAY,GAAG,CAAC,EAA8D,KAAI;AAAlE,IAAA,IAAA,EAAE,IAAI,EAAA,GAAA,EAAwD,EAAnD,MAAM,GAAAA,YAAA,CAAA,EAAA,EAAjB,QAAmB,CAAF;IACpC,MAAM,IAAI,GAAG,KAAK,CAAC,UAAU,CAAC,OAAO,MAAM,KAAK,QAAQ,GAAG,EAAE,GAAG,EAAE,MAAM,EAAE,GAAG,MAAM,CAAC;AAEpF,IAAA,MAAM,OAAO,GAAG,OAAO,GAAW,KAA6B;;AAC5D,QAAA,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,aAAa,EAAE;AACvC,QAAA,IAAI;YACD,MAAM,CAAC,IAAI,CAAC,GAAG,MAAM,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC;YACpC,MAAM,MAAM,GAAQ,IAAI;YAExB,OAAO;AACJ,gBAAA,OAAO,EAAE,MAAM;gBACf,QAAQ,EAAE,CAAA,EAAA,GAAA,MAAM,KAAA,IAAA,IAAN,MAAM,uBAAN,MAAM,CAAE,QAAQ,MAAA,IAAA,IAAA,EAAA,KAAA,KAAA,CAAA,GAAA,EAAA,GAAI,CAAC;gBAC/B,YAAY,EAAE,CAAA,EAAA,GAAA,MAAM,KAAA,IAAA,IAAN,MAAM,uBAAN,MAAM,CAAE,YAAY,MAAA,IAAA,IAAA,EAAA,KAAA,KAAA,CAAA,GAAA,EAAA,GAAI;aACxC;QACJ;gBAAU;YACP,IAAI,CAAC,OAAO,EAAE;QACjB;AACH,IAAA,CAAC;AAED,IAAA,MAAM,SAAS,GAAG,YAAW;AAC1B,QAAA,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,aAAa,EAAE;AAEvC,QAAA,IAAI;YACD,MAAM,CAAC,MAAM,CAAC,GAAG,MAAM,IAAI,CAAC,KAAK,CAC9B,CAAA;;AAEkC,6CAAA,CAAA,CACpC;YAED,MAAM,MAAM,GAA0B,EAAE;AAExC,YAAA,KAAK,MAAM,CAAC,IAAI,MAAM,EAAE;AACrB,gBAAA,MAAM,KAAK,GAAG,CAAC,CAAC,IAAI;AACpB,gBAAA,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE;;gBAGlB,MAAM,CAAC,OAAO,CAAC,GAAG,MAAM,IAAI,CAAC,KAAK,CAC/B,CAAA;;;;;;;;AAQsB,oCAAA,CAAA,EACtB,CAAC,KAAK,CAAC,CACT;;AAGD,gBAAA,MAAM,CAAC,OAAO,CAAC,GAAG,MAAM,IAAI,CAAC,KAAK,CAC/B,CAAA,kBAAA,EAAqB,KAAK,CAAA,EAAA,CAAI,CAChC;AAED,gBAAA,KAAK,MAAM,GAAG,IAAI,OAAO,EAAE;AACxB,oBAAA,MAAM,OAAO,GAAG,GAAG,CAAC,IAAI;AAExB,oBAAA,MAAM,SAAS,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC,WAAW,KAAK,OAAO,CAAC;oBAC9D,MAAM,QAAQ,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC,WAAW,KAAK,OAAO,IAAI,CAAC,CAAC,UAAU,KAAK,CAAC,CAAC;AAEnF,oBAAA,MAAM,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC;AAChB,wBAAA,IAAI,EAAE,OAAO;wBACb,IAAI,EAAE,GAAG,CAAC,IAAI;AACd,wBAAA,OAAO,EAAE,GAAG,CAAC,WAAW,KAAK,IAAI;wBACjC,aAAa,EAAE,GAAG,CAAC,cAAc;AACjC,wBAAA,EAAE,EAAE,GAAG,CAAC,UAAU,KAAK,KAAK;AAC5B,wBAAA,KAAK,EAAE,SAAS;AAChB,wBAAA,MAAM,EAAE,QAAQ;AAClB,qBAAA,CAAC;gBACL;YACH;AAEA,YAAA,OAAO,MAAM;QAChB;gBAAU;YACP,IAAI,CAAC,OAAO,EAAE;QACjB;AACH,IAAA,CAAC;IAED,OAAO;AACJ,QAAA,MAAM,EAAE,OAA8B;QACtC,OAAO;QACP,SAAS;QACT;KACF;AACJ;;;;"}
@@ -1,8 +1,11 @@
1
1
  import { PoolOptions } from 'mysql2';
2
- import { ExecuterResult } from '../core/types';
3
- declare const MysqlDialect: (config: string | PoolOptions) => {
4
- engine: "mysql";
5
- execute: (sql: string, params?: any[]) => Promise<ExecuterResult>;
2
+ import { ExecuterResult, XansqlDialectEngine, XansqlFileConfig } from '../core/types';
3
+ declare const MysqlDialect: ({ file, ...config }: PoolOptions & {
4
+ file?: XansqlFileConfig;
5
+ }) => {
6
+ engine: XansqlDialectEngine;
7
+ execute: (sql: string) => Promise<ExecuterResult>;
6
8
  getSchema: () => Promise<Record<string, any[]>>;
9
+ file: XansqlFileConfig;
7
10
  };
8
11
  export default MysqlDialect;
@@ -1,12 +1,14 @@
1
+ import { __rest } from 'tslib';
1
2
  import mysql from 'mysql2/promise';
2
3
 
3
- const MysqlDialect = (config) => {
4
+ const MysqlDialect = (_a) => {
5
+ var { file } = _a, config = __rest(_a, ["file"]);
4
6
  const pool = mysql.createPool(typeof config === 'string' ? { uri: config } : config);
5
- const execute = async (sql, params = []) => {
7
+ const execute = async (sql) => {
6
8
  var _a, _b;
7
9
  const conn = await pool.getConnection();
8
10
  try {
9
- const [rows] = await conn.query(sql, params);
11
+ const [rows] = await conn.query(sql);
10
12
  const result = rows;
11
13
  return {
12
14
  results: result,
@@ -64,7 +66,8 @@ const MysqlDialect = (config) => {
64
66
  return {
65
67
  engine: 'mysql',
66
68
  execute,
67
- getSchema
69
+ getSchema,
70
+ file
68
71
  };
69
72
  };
70
73