dzql 0.5.31 → 0.5.32
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/package.json
CHANGED
|
@@ -52,7 +52,7 @@ export class GraphRulesCodegen {
|
|
|
52
52
|
|
|
53
53
|
const actionBlocks = [];
|
|
54
54
|
for (const action of actions) {
|
|
55
|
-
const actionSQL = this._generateAction(action, ruleName, description);
|
|
55
|
+
const actionSQL = this._generateAction(action, ruleName, description, operation);
|
|
56
56
|
if (actionSQL) {
|
|
57
57
|
actionBlocks.push(actionSQL);
|
|
58
58
|
}
|
|
@@ -99,29 +99,33 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
99
99
|
|
|
100
100
|
/**
|
|
101
101
|
* Generate SQL for a single action
|
|
102
|
+
* @param {Object} action - The action configuration
|
|
103
|
+
* @param {string} ruleName - The rule name
|
|
104
|
+
* @param {string} description - The rule description
|
|
105
|
+
* @param {string} operation - The operation context ('create', 'update', 'delete')
|
|
102
106
|
* @private
|
|
103
107
|
*/
|
|
104
|
-
_generateAction(action, ruleName, description) {
|
|
108
|
+
_generateAction(action, ruleName, description, operation) {
|
|
105
109
|
const comment = ` -- ${description}`;
|
|
106
110
|
|
|
107
111
|
switch (action.type) {
|
|
108
112
|
case 'create':
|
|
109
|
-
return this._generateCreateAction(action, comment);
|
|
113
|
+
return this._generateCreateAction(action, comment, operation);
|
|
110
114
|
|
|
111
115
|
case 'update':
|
|
112
|
-
return this._generateUpdateAction(action, comment);
|
|
116
|
+
return this._generateUpdateAction(action, comment, operation);
|
|
113
117
|
|
|
114
118
|
case 'delete':
|
|
115
|
-
return this._generateDeleteAction(action, comment);
|
|
119
|
+
return this._generateDeleteAction(action, comment, operation);
|
|
116
120
|
|
|
117
121
|
case 'validate':
|
|
118
|
-
return this._generateValidateAction(action, comment);
|
|
122
|
+
return this._generateValidateAction(action, comment, operation);
|
|
119
123
|
|
|
120
124
|
case 'execute':
|
|
121
|
-
return this._generateExecuteAction(action, comment);
|
|
125
|
+
return this._generateExecuteAction(action, comment, operation);
|
|
122
126
|
|
|
123
127
|
case 'notify':
|
|
124
|
-
return this._generateNotifyAction(action, comment);
|
|
128
|
+
return this._generateNotifyAction(action, comment, operation);
|
|
125
129
|
|
|
126
130
|
default:
|
|
127
131
|
console.warn('Unknown action type:', action.type);
|
|
@@ -133,7 +137,7 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
133
137
|
* Generate CREATE action
|
|
134
138
|
* @private
|
|
135
139
|
*/
|
|
136
|
-
_generateCreateAction(action, comment) {
|
|
140
|
+
_generateCreateAction(action, comment, operation) {
|
|
137
141
|
const entity = action.entity;
|
|
138
142
|
const data = action.data;
|
|
139
143
|
|
|
@@ -142,7 +146,7 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
142
146
|
|
|
143
147
|
for (const [field, value] of Object.entries(data)) {
|
|
144
148
|
fields.push(field);
|
|
145
|
-
values.push(this._resolveValue(value));
|
|
149
|
+
values.push(this._resolveValue(value, operation));
|
|
146
150
|
}
|
|
147
151
|
|
|
148
152
|
return `${comment}
|
|
@@ -154,19 +158,19 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
154
158
|
* Generate UPDATE action
|
|
155
159
|
* @private
|
|
156
160
|
*/
|
|
157
|
-
_generateUpdateAction(action, comment) {
|
|
161
|
+
_generateUpdateAction(action, comment, operation) {
|
|
158
162
|
const entity = action.entity;
|
|
159
163
|
const data = action.data;
|
|
160
164
|
const match = action.match;
|
|
161
165
|
|
|
162
166
|
const setClauses = [];
|
|
163
167
|
for (const [field, value] of Object.entries(data)) {
|
|
164
|
-
setClauses.push(`${field} = ${this._resolveValue(value)}`);
|
|
168
|
+
setClauses.push(`${field} = ${this._resolveValue(value, operation)}`);
|
|
165
169
|
}
|
|
166
170
|
|
|
167
171
|
const whereClauses = [];
|
|
168
172
|
for (const [field, value] of Object.entries(match)) {
|
|
169
|
-
whereClauses.push(`${field} = ${this._resolveValue(value)}`);
|
|
173
|
+
whereClauses.push(`${field} = ${this._resolveValue(value, operation)}`);
|
|
170
174
|
}
|
|
171
175
|
|
|
172
176
|
return `${comment}
|
|
@@ -179,13 +183,13 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
179
183
|
* Generate DELETE action
|
|
180
184
|
* @private
|
|
181
185
|
*/
|
|
182
|
-
_generateDeleteAction(action, comment) {
|
|
186
|
+
_generateDeleteAction(action, comment, operation) {
|
|
183
187
|
const entity = action.entity;
|
|
184
188
|
const match = action.match;
|
|
185
189
|
|
|
186
190
|
const whereClauses = [];
|
|
187
191
|
for (const [field, value] of Object.entries(match)) {
|
|
188
|
-
whereClauses.push(`${field} = ${this._resolveValue(value)}`);
|
|
192
|
+
whereClauses.push(`${field} = ${this._resolveValue(value, operation)}`);
|
|
189
193
|
}
|
|
190
194
|
|
|
191
195
|
return `${comment}
|
|
@@ -197,14 +201,14 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
197
201
|
* Generate VALIDATE action
|
|
198
202
|
* @private
|
|
199
203
|
*/
|
|
200
|
-
_generateValidateAction(action, comment) {
|
|
204
|
+
_generateValidateAction(action, comment, operation) {
|
|
201
205
|
const functionName = action.function;
|
|
202
206
|
const params = action.params || {};
|
|
203
207
|
const errorMessage = action.error_message || 'Validation failed';
|
|
204
208
|
|
|
205
209
|
const paramList = [];
|
|
206
210
|
for (const [key, value] of Object.entries(params)) {
|
|
207
|
-
paramList.push(`${key} => ${this._resolveValue(value)}`);
|
|
211
|
+
paramList.push(`${key} => ${this._resolveValue(value, operation)}`);
|
|
208
212
|
}
|
|
209
213
|
|
|
210
214
|
const paramSQL = paramList.length > 0 ? paramList.join(', ') : '';
|
|
@@ -219,13 +223,13 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
219
223
|
* Generate EXECUTE action
|
|
220
224
|
* @private
|
|
221
225
|
*/
|
|
222
|
-
_generateExecuteAction(action, comment) {
|
|
226
|
+
_generateExecuteAction(action, comment, operation) {
|
|
223
227
|
const functionName = action.function;
|
|
224
228
|
const params = action.params || {};
|
|
225
229
|
|
|
226
230
|
const paramList = [];
|
|
227
231
|
for (const [key, value] of Object.entries(params)) {
|
|
228
|
-
paramList.push(`${key} => ${this._resolveValue(value)}`);
|
|
232
|
+
paramList.push(`${key} => ${this._resolveValue(value, operation)}`);
|
|
229
233
|
}
|
|
230
234
|
|
|
231
235
|
const paramSQL = paramList.length > 0 ? paramList.join(', ') : '';
|
|
@@ -253,11 +257,16 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
253
257
|
* Creates an event that will be broadcast to specified users
|
|
254
258
|
* @private
|
|
255
259
|
*/
|
|
256
|
-
_generateNotifyAction(action, comment) {
|
|
260
|
+
_generateNotifyAction(action, comment, operation) {
|
|
257
261
|
const users = action.users || [];
|
|
258
262
|
const message = action.message || '';
|
|
259
263
|
const data = action.data || {};
|
|
260
264
|
|
|
265
|
+
// Determine the correct record variable based on operation
|
|
266
|
+
const recordVar = operation === 'delete' ? 'p_old_record'
|
|
267
|
+
: operation === 'update' ? 'p_new_record'
|
|
268
|
+
: 'p_record';
|
|
269
|
+
|
|
261
270
|
// Build user ID array resolution
|
|
262
271
|
let userIdSQL = 'ARRAY[]::INT[]';
|
|
263
272
|
|
|
@@ -269,10 +278,10 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
269
278
|
if (userPath.startsWith('@') && !userPath.includes('->')) {
|
|
270
279
|
// Simple field reference: @author_id
|
|
271
280
|
const fieldName = userPath.substring(1);
|
|
272
|
-
userPaths.push(`(
|
|
281
|
+
userPaths.push(`(${recordVar}->>'${fieldName}')::int`);
|
|
273
282
|
} else if (userPath.startsWith('@') && userPath.includes('->')) {
|
|
274
283
|
// Complex path: @post_id->posts.author_id - use runtime resolver
|
|
275
|
-
userPaths.push(`dzql.resolve_notification_path('${this.tableName}',
|
|
284
|
+
userPaths.push(`dzql.resolve_notification_path('${this.tableName}', ${recordVar}, '${userPath}')`);
|
|
276
285
|
} else {
|
|
277
286
|
// Literal user ID
|
|
278
287
|
userPaths.push(`${userPath}`);
|
|
@@ -301,19 +310,19 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
301
310
|
dataFields.push(`'table', '${this.tableName}'`);
|
|
302
311
|
|
|
303
312
|
if (message) {
|
|
304
|
-
dataFields.push(`'message', ${this._resolveValue(message)}`);
|
|
313
|
+
dataFields.push(`'message', ${this._resolveValue(message, operation)}`);
|
|
305
314
|
}
|
|
306
315
|
|
|
307
316
|
// Add custom data fields
|
|
308
317
|
for (const [key, value] of Object.entries(data)) {
|
|
309
|
-
dataFields.push(`'${key}', ${this._resolveValue(value)}`);
|
|
318
|
+
dataFields.push(`'${key}', ${this._resolveValue(value, operation)}`);
|
|
310
319
|
}
|
|
311
320
|
|
|
312
321
|
const dataSQL = dataFields.length > 0
|
|
313
322
|
? `jsonb_build_object(${dataFields.join(', ')})`
|
|
314
323
|
: "'{}'::jsonb";
|
|
315
324
|
|
|
316
|
-
const pkBuildObject = this._generatePKBuildObject(
|
|
325
|
+
const pkBuildObject = this._generatePKBuildObject(recordVar);
|
|
317
326
|
|
|
318
327
|
return `${comment}
|
|
319
328
|
-- Create notification event
|
|
@@ -386,9 +395,11 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
386
395
|
|
|
387
396
|
/**
|
|
388
397
|
* Resolve a value (variable reference or literal)
|
|
398
|
+
* @param {string|number} value - The value to resolve
|
|
399
|
+
* @param {string} operation - The operation context ('create', 'update', 'delete')
|
|
389
400
|
* @private
|
|
390
401
|
*/
|
|
391
|
-
_resolveValue(value) {
|
|
402
|
+
_resolveValue(value, operation = 'create') {
|
|
392
403
|
if (typeof value !== 'string') {
|
|
393
404
|
// Number or other type
|
|
394
405
|
return value;
|
|
@@ -410,8 +421,14 @@ $$ LANGUAGE plpgsql SECURITY DEFINER;`;
|
|
|
410
421
|
return 'NOW()';
|
|
411
422
|
|
|
412
423
|
default:
|
|
413
|
-
// Field reference from record
|
|
414
|
-
|
|
424
|
+
// Field reference from record - use correct variable based on operation
|
|
425
|
+
if (operation === 'delete') {
|
|
426
|
+
return `(p_old_record->>'${varName}')`;
|
|
427
|
+
} else if (operation === 'update') {
|
|
428
|
+
return `(p_new_record->>'${varName}')`;
|
|
429
|
+
} else {
|
|
430
|
+
return `(p_record->>'${varName}')`;
|
|
431
|
+
}
|
|
415
432
|
}
|
|
416
433
|
}
|
|
417
434
|
|