metal-orm 1.0.24 → 1.0.25

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/README.md CHANGED
@@ -117,6 +117,8 @@ You don’t have to use decorators, but when you do, you’re still on the same
117
117
  <a id="installation"></a>
118
118
  ## Installation 📦
119
119
 
120
+ **Requirements:** Node.js ≥ 20.0.0. For TypeScript projects, use TS 5.6+ to get the standard decorators API and typings.
121
+
120
122
  ```bash
121
123
  # npm
122
124
  npm install metal-orm
@@ -109,6 +109,28 @@ var buildTableDef = (meta) => {
109
109
  return table;
110
110
  };
111
111
 
112
+ // src/decorators/decorator-metadata.ts
113
+ var METADATA_KEY = "metal-orm:decorators";
114
+ var isStandardDecoratorContext = (value) => {
115
+ return typeof value === "object" && value !== null && "kind" in value;
116
+ };
117
+ var getOrCreateMetadataBag = (context) => {
118
+ const metadata = context.metadata || (context.metadata = {});
119
+ const existing = metadata[METADATA_KEY];
120
+ if (existing) {
121
+ return existing;
122
+ }
123
+ const bag = { columns: [], relations: [] };
124
+ metadata[METADATA_KEY] = bag;
125
+ return bag;
126
+ };
127
+ var readMetadataBag = (context) => {
128
+ return context.metadata?.[METADATA_KEY];
129
+ };
130
+ var registerInitializer = (context, initializer) => {
131
+ context.addInitializer?.(initializer);
132
+ };
133
+
112
134
  // src/decorators/entity.ts
113
135
  var toSnakeCase = (value) => {
114
136
  return value.replace(/([a-z0-9])([A-Z])/g, "$1_$2").replace(/[^a-z0-9_]+/gi, "_").replace(/__+/g, "_").replace(/^_|_$/g, "").toLowerCase();
@@ -129,7 +151,28 @@ function Entity(options = {}) {
129
151
  setEntityTableName(value, tableName, options.hooks);
130
152
  return value;
131
153
  };
132
- return decorator;
154
+ const decoratorWithContext = (value, context) => {
155
+ const ctor = value;
156
+ decorator(ctor);
157
+ if (context && isStandardDecoratorContext(context)) {
158
+ const bag = readMetadataBag(context);
159
+ if (bag) {
160
+ const meta = ensureEntityMetadata(ctor);
161
+ for (const entry of bag.columns) {
162
+ if (!meta.columns[entry.propertyName]) {
163
+ addColumnMetadata(ctor, entry.propertyName, { ...entry.column });
164
+ }
165
+ }
166
+ for (const entry of bag.relations) {
167
+ if (!meta.relations[entry.propertyName]) {
168
+ addRelationMetadata(ctor, entry.propertyName, entry.relation);
169
+ }
170
+ }
171
+ }
172
+ }
173
+ return ctor;
174
+ };
175
+ return decoratorWithContext;
133
176
  }
134
177
 
135
178
  // src/decorators/column.ts
@@ -176,11 +219,32 @@ var registerColumn = (ctor, propertyName, column) => {
176
219
  }
177
220
  addColumnMetadata(ctor, propertyName, column);
178
221
  };
222
+ var registerColumnFromContext = (context, column) => {
223
+ if (!context.name) {
224
+ throw new Error("Column decorator requires a property name");
225
+ }
226
+ const propertyName = normalizePropertyName(context.name);
227
+ const bag = getOrCreateMetadataBag(context);
228
+ if (!bag.columns.some((entry) => entry.propertyName === propertyName)) {
229
+ bag.columns.push({ propertyName, column: { ...column } });
230
+ }
231
+ registerInitializer(context, function() {
232
+ const ctor = resolveConstructor(this);
233
+ if (!ctor) {
234
+ return;
235
+ }
236
+ registerColumn(ctor, propertyName, column);
237
+ });
238
+ };
179
239
  function Column(definition) {
180
240
  const normalized = normalizeColumnInput(definition);
181
- const decorator = (target, propertyKey) => {
182
- const propertyName = normalizePropertyName(propertyKey);
183
- const ctor = resolveConstructor(target);
241
+ const decorator = (targetOrValue, propertyKeyOrContext) => {
242
+ if (isStandardDecoratorContext(propertyKeyOrContext)) {
243
+ registerColumnFromContext(propertyKeyOrContext, normalized);
244
+ return;
245
+ }
246
+ const propertyName = normalizePropertyName(propertyKeyOrContext);
247
+ const ctor = resolveConstructor(targetOrValue);
184
248
  if (!ctor) {
185
249
  throw new Error("Unable to resolve constructor when registering column metadata");
186
250
  }
@@ -259,9 +323,29 @@ var registerRelation = (ctor, propertyName, metadata) => {
259
323
  addRelationMetadata(ctor, propertyName, metadata);
260
324
  };
261
325
  var createFieldDecorator = (metadataFactory) => {
262
- const decorator = (target, propertyKey) => {
263
- const propertyName = normalizePropertyName2(propertyKey);
264
- const ctor = resolveConstructor2(target);
326
+ const decorator = (targetOrValue, propertyKeyOrContext) => {
327
+ if (isStandardDecoratorContext(propertyKeyOrContext)) {
328
+ const ctx = propertyKeyOrContext;
329
+ if (!ctx.name) {
330
+ throw new Error("Relation decorator requires a property name");
331
+ }
332
+ const propertyName2 = normalizePropertyName2(ctx.name);
333
+ const bag = getOrCreateMetadataBag(ctx);
334
+ const relationMetadata = metadataFactory(propertyName2);
335
+ if (!bag.relations.some((entry) => entry.propertyName === propertyName2)) {
336
+ bag.relations.push({ propertyName: propertyName2, relation: relationMetadata });
337
+ }
338
+ registerInitializer(ctx, function() {
339
+ const ctor2 = resolveConstructor2(this);
340
+ if (!ctor2) {
341
+ return;
342
+ }
343
+ registerRelation(ctor2, propertyName2, relationMetadata);
344
+ });
345
+ return;
346
+ }
347
+ const propertyName = normalizePropertyName2(propertyKeyOrContext);
348
+ const ctor = resolveConstructor2(targetOrValue);
265
349
  if (!ctor) {
266
350
  throw new Error("Unable to resolve constructor when registering relation metadata");
267
351
  }