@ronin/compiler 0.18.2 → 0.18.3-invalid-json-experimental-441

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/index.d.ts CHANGED
@@ -21,14 +21,12 @@ declare const QUERY_SYMBOLS: {
21
21
  readonly EXPRESSION: "__RONIN_EXPRESSION";
22
22
  readonly FIELD: "__RONIN_FIELD_";
23
23
  readonly FIELD_PARENT: "__RONIN_FIELD_PARENT_";
24
- readonly FIELD_PARENT_OLD: "__RONIN_FIELD_PARENT_OLD_";
25
- readonly FIELD_PARENT_NEW: "__RONIN_FIELD_PARENT_NEW_";
26
24
  readonly VALUE: "__RONIN_VALUE";
27
25
  };
28
26
 
29
27
  type QueryTypeEnum = (typeof DML_QUERY_TYPES)[number];
30
28
  type ModelQueryTypeEnum = (typeof DDL_QUERY_TYPES)[number];
31
- type ModelEntityEnum = 'field' | 'index' | 'trigger' | 'preset';
29
+ type ModelEntityEnum = 'field' | 'index' | 'preset';
32
30
  type FieldValue = string | number | boolean | null | unknown;
33
31
  type FieldSelector = Record<string, FieldValue | StoredObject>;
34
32
  type StoredObject = {
@@ -126,11 +124,10 @@ type CreateQuery = {
126
124
  };
127
125
  type AlterQuery = {
128
126
  model: string;
129
- to?: Partial<Omit<PublicModel, 'fields' | 'indexes' | 'triggers' | 'presets' | 'idPrefix'>>;
127
+ to?: Partial<Omit<PublicModel, 'fields' | 'indexes' | 'presets' | 'idPrefix'>>;
130
128
  create?: {
131
129
  field?: Omit<ModelField, 'system'>;
132
130
  index?: Omit<ModelIndex, 'system'>;
133
- trigger?: Omit<ModelTrigger, 'system'>;
134
131
  preset?: Omit<ModelPreset, 'system'>;
135
132
  };
136
133
  alter?: {
@@ -139,9 +136,6 @@ type AlterQuery = {
139
136
  } | {
140
137
  index?: string;
141
138
  to?: Partial<Omit<ModelIndex, 'system'>>;
142
- } | {
143
- trigger?: string;
144
- to?: Omit<ModelTrigger, 'system'>;
145
139
  } | {
146
140
  preset?: string;
147
141
  to?: Omit<ModelPreset, 'system'>;
@@ -298,30 +292,6 @@ type ModelIndex<T extends ModelEntityList<ModelField> = ModelEntityList<ModelFie
298
292
  */
299
293
  filter?: WithInstruction;
300
294
  };
301
- type ModelTriggerField<T extends ModelEntityList<ModelField> = ModelEntityList<ModelField>> = {
302
- /**
303
- * The slug of the field that should cause the trigger to fire if the value of the
304
- * field has changed.
305
- */
306
- slug: keyof T;
307
- };
308
- type ModelTrigger<T extends ModelEntityList<ModelField> = ModelEntityList<ModelField>> = {
309
- /** The identifier of the trigger. */
310
- slug: string;
311
- /** The type of query for which the trigger should fire. */
312
- action: 'INSERT' | 'UPDATE' | 'DELETE';
313
- /** When the trigger should fire in the case that a matching query is executed. */
314
- when: 'BEFORE' | 'DURING' | 'AFTER';
315
- /** A list of queries that should be executed when the trigger fires. */
316
- effects: Array<Record<typeof QUERY_SYMBOLS.QUERY, Query>>;
317
- /** A list of field slugs for which the trigger should fire. */
318
- fields?: Array<ModelTriggerField<T>>;
319
- /**
320
- * An object containing query instructions used to determine whether the trigger should
321
- * fire, or not.
322
- */
323
- filter?: WithInstruction;
324
- };
325
295
  type ModelPreset = {
326
296
  /** The visual display name of the preset. */
327
297
  name?: string;
@@ -369,7 +339,6 @@ interface Model<T extends ModelEntityList<ModelField> = ModelEntityList<ModelFie
369
339
  };
370
340
  fields: T;
371
341
  indexes?: ModelEntityList<ModelIndex<T>>;
372
- triggers?: ModelEntityList<ModelTrigger<T>>;
373
342
  presets?: ModelEntityList<ModelPreset>;
374
343
  }
375
344
  type PublicModel<T extends ModelEntityList<ModelField> = ModelEntityList<ModelField>> = Omit<Partial<Model<T>>, 'slug' | 'identifiers' | 'system' | 'tableAlias'> & {
@@ -423,7 +392,7 @@ type ExpandedResult<T = ResultRecord> = {
423
392
  };
424
393
  type Result<T = ResultRecord> = RegularResult<T> | ExpandedResult<T>;
425
394
 
426
- type RoninErrorCode = 'MODEL_NOT_FOUND' | 'FIELD_NOT_FOUND' | 'INDEX_NOT_FOUND' | 'TRIGGER_NOT_FOUND' | 'PRESET_NOT_FOUND' | 'INVALID_WITH_VALUE' | 'INVALID_TO_VALUE' | 'INVALID_INCLUDING_VALUE' | 'INVALID_FOR_VALUE' | 'INVALID_BEFORE_OR_AFTER_INSTRUCTION' | 'INVALID_MODEL_VALUE' | 'EXISTING_MODEL_ENTITY' | 'REQUIRED_MODEL_ENTITY' | 'MUTUALLY_EXCLUSIVE_INSTRUCTIONS' | 'MISSING_INSTRUCTION' | 'MISSING_FIELD';
395
+ type RoninErrorCode = 'MODEL_NOT_FOUND' | 'FIELD_NOT_FOUND' | 'INDEX_NOT_FOUND' | 'TRIGGER_NOT_FOUND' | 'PRESET_NOT_FOUND' | 'INVALID_WITH_VALUE' | 'INVALID_TO_VALUE' | 'INVALID_INCLUDING_VALUE' | 'INVALID_FOR_VALUE' | 'INVALID_BEFORE_OR_AFTER_INSTRUCTION' | 'INVALID_MODEL_VALUE' | 'INVALID_FIELD_VALUE' | 'EXISTING_MODEL_ENTITY' | 'REQUIRED_MODEL_ENTITY' | 'MUTUALLY_EXCLUSIVE_INSTRUCTIONS' | 'MISSING_INSTRUCTION' | 'MISSING_FIELD';
427
396
  interface Issue {
428
397
  message: string;
429
398
  path: Array<string | number>;
@@ -499,4 +468,4 @@ declare class Transaction {
499
468
 
500
469
  declare const CLEAN_ROOT_MODEL: PublicModel;
501
470
 
502
- export { type AddInstructions, type AddQuery, type AddInstructions as AddQueryInstructions, type AlterQuery, type CombinedInstructions, type CountInstructions, type CountQuery, type CountInstructions as CountQueryInstructions, type CreateQuery, DDL_QUERY_TYPES, DML_QUERY_TYPES, DML_QUERY_TYPES_READ, DML_QUERY_TYPES_WRITE, type DropQuery, type ExpandedResult, type GetInstructions, type GetQuery, type GetInstructions as GetQueryInstructions, type ListQuery, type PublicModel as Model, type ModelField, type ModelIndex, type ModelPreset, type ModelTrigger, QUERY_SYMBOLS, QUERY_TYPES, type Query, type QueryInstructionType as QueryInstruction, type QuerySchemaType, type QueryType, CLEAN_ROOT_MODEL as ROOT_MODEL, type RegularResult, type RemoveInstructions, type RemoveQuery, type RemoveInstructions as RemoveQueryInstructions, type Result, type ResultRecord, type ResultRecordBase, RoninError, type SetInstructions, type SetQuery, type SetInstructions as SetQueryInstructions, type Statement, type StoredObject, Transaction, type WithInstruction, getQuerySymbol };
471
+ export { type AddInstructions, type AddQuery, type AddInstructions as AddQueryInstructions, type AlterQuery, type CombinedInstructions, type CountInstructions, type CountQuery, type CountInstructions as CountQueryInstructions, type CreateQuery, DDL_QUERY_TYPES, DML_QUERY_TYPES, DML_QUERY_TYPES_READ, DML_QUERY_TYPES_WRITE, type DropQuery, type ExpandedResult, type GetInstructions, type GetQuery, type GetInstructions as GetQueryInstructions, type ListQuery, type PublicModel as Model, type ModelField, type ModelIndex, type ModelPreset, QUERY_SYMBOLS, QUERY_TYPES, type Query, type QueryInstructionType as QueryInstruction, type QuerySchemaType, type QueryType, CLEAN_ROOT_MODEL as ROOT_MODEL, type RegularResult, type RemoveInstructions, type RemoveQuery, type RemoveInstructions as RemoveQueryInstructions, type Result, type ResultRecord, type ResultRecordBase, RoninError, type SetInstructions, type SetQuery, type SetInstructions as SetQueryInstructions, type Statement, type StoredObject, Transaction, type WithInstruction, getQuerySymbol };
package/dist/index.js CHANGED
@@ -16,10 +16,6 @@ var QUERY_SYMBOLS = {
16
16
  FIELD: "__RONIN_FIELD_",
17
17
  // Represents the value of a field in the model of a parent query.
18
18
  FIELD_PARENT: "__RONIN_FIELD_PARENT_",
19
- // Represents the old value of a field in the parent model. Used for triggers.
20
- FIELD_PARENT_OLD: "__RONIN_FIELD_PARENT_OLD_",
21
- // Represents the new value of a field in the parent model. Used for triggers.
22
- FIELD_PARENT_NEW: "__RONIN_FIELD_PARENT_NEW_",
23
19
  // Represents a value provided to a query preset.
24
20
  VALUE: "__RONIN_VALUE"
25
21
  };
@@ -46,7 +42,6 @@ var composeMountingPath = (single, key, mountingPath) => {
46
42
  var MODEL_ENTITY_ERROR_CODES = {
47
43
  field: "FIELD_NOT_FOUND",
48
44
  index: "INDEX_NOT_FOUND",
49
- trigger: "TRIGGER_NOT_FOUND",
50
45
  preset: "PRESET_NOT_FOUND"
51
46
  };
52
47
  var RoninError = class extends Error {
@@ -1318,11 +1313,6 @@ var parseFieldExpression = (model, instructionName, expression, parentModel) =>
1318
1313
  if (match.startsWith(QUERY_SYMBOLS.FIELD_PARENT)) {
1319
1314
  rootModel = parentModel;
1320
1315
  toReplace = QUERY_SYMBOLS.FIELD_PARENT;
1321
- if (match.startsWith(QUERY_SYMBOLS.FIELD_PARENT_OLD)) {
1322
- rootModel.tableAlias = toReplace = QUERY_SYMBOLS.FIELD_PARENT_OLD;
1323
- } else if (match.startsWith(QUERY_SYMBOLS.FIELD_PARENT_NEW)) {
1324
- rootModel.tableAlias = toReplace = QUERY_SYMBOLS.FIELD_PARENT_NEW;
1325
- }
1326
1316
  }
1327
1317
  const fieldSlug = match.replace(toReplace, "");
1328
1318
  const field = getFieldFromModel(rootModel, fieldSlug, { instructionName });
@@ -1381,8 +1371,17 @@ var composeConditions = (models, model, statementParams, instructionName, value,
1381
1371
  instructionName
1382
1372
  });
1383
1373
  const { field: modelField } = fieldDetails || {};
1384
- const consumeJSON = (modelField?.type === "json" || modelField?.type === "blob") && instructionName === "to";
1385
- if (modelField && !(isObject(value) || Array.isArray(value)) || getQuerySymbol(value) || consumeJSON) {
1374
+ const fieldIsJSON = (modelField?.type === "json" || modelField?.type === "blob") && instructionName === "to";
1375
+ const valueIsJSON = isObject(value) || (modelField?.type === "blob" ? null : Array.isArray(value));
1376
+ if (!valueIsJSON || getQuerySymbol(value) || fieldIsJSON) {
1377
+ if (modelField && fieldIsJSON && !valueIsJSON) {
1378
+ const message = modelField.type === "json" ? "The provided field value is not valid JSON. Only objects and arrays should be provided. Other types of values should be stored in their respective primitive field types." : "The provided field value is not a valid Blob reference.";
1379
+ throw new RoninError({
1380
+ message,
1381
+ field: modelField?.slug,
1382
+ code: "INVALID_FIELD_VALUE"
1383
+ });
1384
+ }
1386
1385
  return composeFieldValues(
1387
1386
  models,
1388
1387
  model,
@@ -1622,7 +1621,6 @@ var ROOT_MODEL = {
1622
1621
  // which makes the statement shorter.
1623
1622
  fields: { type: "json", defaultValue: {} },
1624
1623
  indexes: { type: "json", defaultValue: {} },
1625
- triggers: { type: "json", defaultValue: {} },
1626
1624
  presets: { type: "json", defaultValue: {} }
1627
1625
  }
1628
1626
  };
@@ -1709,11 +1707,11 @@ var getFieldStatement = (models, model, field) => {
1709
1707
  const modelList = models.some((item) => item.slug === model.slug) ? models : [...models, model];
1710
1708
  const targetTable = getModelBySlug(modelList, field.target).table;
1711
1709
  statement += ` REFERENCES ${targetTable}("id")`;
1712
- for (const trigger in actions) {
1713
- if (!Object.hasOwn(actions, trigger)) continue;
1714
- const triggerName = trigger.toUpperCase().slice(2);
1715
- const action = actions[trigger];
1716
- statement += ` ON ${triggerName} ${action}`;
1710
+ for (const cause in actions) {
1711
+ if (!Object.hasOwn(actions, cause)) continue;
1712
+ const causeName = cause.toUpperCase().slice(2);
1713
+ const action = actions[cause];
1714
+ statement += ` ON ${causeName} ${action}`;
1717
1715
  }
1718
1716
  }
1719
1717
  return statement;
@@ -1721,7 +1719,6 @@ var getFieldStatement = (models, model, field) => {
1721
1719
  var PLURAL_MODEL_ENTITIES = {
1722
1720
  field: "fields",
1723
1721
  index: "indexes",
1724
- trigger: "triggers",
1725
1722
  preset: "presets"
1726
1723
  };
1727
1724
  var PLURAL_MODEL_ENTITIES_VALUES = Object.values(PLURAL_MODEL_ENTITIES);
@@ -1854,29 +1851,23 @@ var transformMetaQuery = (models, dependencyStatements, statementParams, query,
1854
1851
  statement: `CREATE TABLE "${modelWithPresets.table}" (${columns.join(", ")})`,
1855
1852
  params: []
1856
1853
  });
1857
- for (const [modelEntity, pluralModelEntity] of [
1858
- ["index", "indexes"],
1859
- ["trigger", "triggers"]
1860
- ]) {
1861
- const entityList = modelWithPresets[pluralModelEntity];
1862
- if (!entityList) continue;
1863
- for (const [itemSlug, item] of Object.entries(entityList)) {
1864
- const query2 = {
1865
- alter: {
1866
- model: modelWithPresets.slug,
1867
- create: {
1868
- [modelEntity]: { slug: itemSlug, ...item }
1869
- }
1854
+ const entityList = modelWithPresets.indexes;
1855
+ for (const [itemSlug, item] of Object.entries(entityList || {})) {
1856
+ const query2 = {
1857
+ alter: {
1858
+ model: modelWithPresets.slug,
1859
+ create: {
1860
+ index: { slug: itemSlug, ...item }
1870
1861
  }
1871
- };
1872
- const tempModels = [
1873
- ...models.filter((model2) => model2.slug !== modelWithPresets.slug),
1874
- { ...modelWithPresets, indexes: {}, triggers: {} }
1875
- ];
1876
- transformMetaQuery(tempModels, dependencyStatements, null, query2, {
1877
- inlineDefaults: options.inlineDefaults
1878
- });
1879
- }
1862
+ }
1863
+ };
1864
+ const tempModels = [
1865
+ ...models.filter((model2) => model2.slug !== modelWithPresets.slug),
1866
+ { ...modelWithPresets, indexes: {} }
1867
+ ];
1868
+ transformMetaQuery(tempModels, dependencyStatements, null, query2, {
1869
+ inlineDefaults: options.inlineDefaults
1870
+ });
1880
1871
  }
1881
1872
  queryTypeDetails = { with: modelWithPresets };
1882
1873
  getSystemModels(models, modelWithPresets).map((systemModel) => {
@@ -2034,56 +2025,6 @@ var transformMetaQuery = (models, dependencyStatements, statementParams, query,
2034
2025
  }
2035
2026
  dependencyStatements.push({ statement, params: [] });
2036
2027
  }
2037
- if (entity === "trigger") {
2038
- const triggerName = convertToSnakeCase(slug);
2039
- let statement = `${statementAction} TRIGGER "${triggerName}"`;
2040
- if (action === "create") {
2041
- const trigger = jsonValue;
2042
- const statementParts = [`${trigger.when} ${trigger.action}`];
2043
- if (trigger.fields) {
2044
- if (trigger.action !== "UPDATE") {
2045
- throw new RoninError({
2046
- message: `When ${actionReadable} ${PLURAL_MODEL_ENTITIES[entity]}, targeting specific fields requires the \`UPDATE\` action.`,
2047
- code: "INVALID_MODEL_VALUE",
2048
- fields: ["action"]
2049
- });
2050
- }
2051
- const fieldSelectors = trigger.fields.map((field2) => {
2052
- return getFieldFromModel(existingModel, field2.slug, {
2053
- modelEntityType: "trigger",
2054
- modelEntityName: triggerName
2055
- }).fieldSelector;
2056
- });
2057
- statementParts.push(`OF (${fieldSelectors.join(", ")})`);
2058
- }
2059
- statementParts.push("ON", `"${existingModel.table}"`);
2060
- if (trigger.filter || trigger.effects.some((query2) => findInObject(query2, QUERY_SYMBOLS.FIELD))) {
2061
- statementParts.push("FOR EACH ROW");
2062
- }
2063
- if (trigger.filter) {
2064
- const tableAlias = trigger.action === "DELETE" ? QUERY_SYMBOLS.FIELD_PARENT_OLD : QUERY_SYMBOLS.FIELD_PARENT_NEW;
2065
- const withStatement = handleWith(
2066
- models,
2067
- { ...existingModel, tableAlias },
2068
- null,
2069
- trigger.filter
2070
- );
2071
- statementParts.push("WHEN", `(${withStatement})`);
2072
- }
2073
- const effectStatements = trigger.effects.map((effectQuery) => {
2074
- return compileQueryInput(effectQuery[QUERY_SYMBOLS.QUERY], models, null, {
2075
- returning: false,
2076
- parentModel: existingModel,
2077
- inlineDefaults: options.inlineDefaults
2078
- }).main.statement;
2079
- });
2080
- statementParts.push("BEGIN");
2081
- statementParts.push(`${effectStatements.join("; ")};`);
2082
- statementParts.push("END");
2083
- statement += ` ${statementParts.join(" ")}`;
2084
- }
2085
- dependencyStatements.push({ statement, params: [] });
2086
- }
2087
2028
  const field = `${QUERY_SYMBOLS.FIELD}${pluralType}`;
2088
2029
  let json;
2089
2030
  switch (action) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ronin/compiler",
3
- "version": "0.18.2",
3
+ "version": "0.18.3-invalid-json-experimental-441",
4
4
  "type": "module",
5
5
  "description": "Compiles RONIN queries to SQL statements.",
6
6
  "publishConfig": {