diff --git a/lib/zeebe/util/VariableContext.js b/lib/zeebe/util/VariableContext.js index 5d37dcf..cc12e10 100644 --- a/lib/zeebe/util/VariableContext.js +++ b/lib/zeebe/util/VariableContext.js @@ -4,6 +4,7 @@ export class EntriesContext extends VariableContext { constructor(value = { entries: {} }) { super(value); + this.value.id = this.value.id || crypto.randomUUID(); this.value.entries = this.value.entries || {}; const context = this.value; @@ -72,6 +73,7 @@ export class EntriesContext extends VariableContext { const { entries = {}, + used = [], ...rest } = unwrap(context); @@ -81,7 +83,11 @@ export class EntriesContext extends VariableContext { entries: { ...merged.entries, ...entries - } + }, + used: [ + ...(merged.used || []), + ...used + ] }; }, {}); diff --git a/lib/zeebe/util/feelUtility.js b/lib/zeebe/util/feelUtility.js index 75f4096..55a5137 100644 --- a/lib/zeebe/util/feelUtility.js +++ b/lib/zeebe/util/feelUtility.js @@ -80,8 +80,16 @@ function resolveReferences(variablesToResolve, allVariables) { sortedVariables.forEach(({ variable, expression }) => { const resultContext = getResultContext(expression, filterForScope(rootContext, variable)); + findUnresolvedVariables(resultContext, true); + + // console.log('annotated', annotateUsedVariables(resultContext)); + addUsedInfo(rootContext, resultContext, variable.origin[0]); + debugger; + let computedResult = resultContext.computedValue(); + console.log('computedResult', resultContext, computedResult, rootContext); + // Wrap primitive values in an EntriesContext if (!(computedResult instanceof EntriesContext)) { computedResult = EntriesContext.of(computedResult); @@ -114,6 +122,49 @@ function resolveReferences(variablesToResolve, allVariables) { return result; } +function findUsageNode(name, variables) { + console.log('findUsageNode', name, variables); + if (!variables) { + return []; + } + + return (variables.children || []).flatMap(child => { + console.log(name, child); + + if (child.context.value.name === name) { + return child; + } + + return findUsageNode(name, child); + }).filter(i => i); +} + +function addUsedInfo(rootContext, variables, scope) { + + // iterate over the result context and find used names + const context = variables.context; + const usedNames = context.value.used; // .map(variableName => { + // return context.value.entries[variableName]?.value?.id + // }).filter(i => i); + + // Add usage info to root context + const rootContextValues = Object.values(rootContext.entries); + rootContextValues.filter(v => usedNames.includes(v.name)).forEach( + v => { + v.usedIn = v.usedIn || []; + v.usedIn.push(scope); + + // Recursively find places the variable was used + console.log(findUsageNode(v.name, variables)); + findUsageNode(v.name, variables).forEach(node => { + addUsedInfo(v, node, scope); + console.log('node', node); + }); + + // Find recursive used variables + } + ); +} // helpers ////////////////////// @@ -135,6 +186,9 @@ export function getResultContext(expression, variables = {}) { start: contextTracker.start, reduce(...args) { const result = contextTracker.reduce(...args); + + console.log('reduce', result, ...args); + latestVariables = result; return result; } @@ -186,7 +240,9 @@ function getExpressionDetails(variable, origin) { const result = getResultContext(expression); - const unresolved = findUnresolvedVariables(result) ; + const unresolved = findUnresolvedVariables(result); + + // console.log('unresolved', unresolved); return { expression, unresolved }; } @@ -197,10 +253,14 @@ function getExpressionDetails(variable, origin) { * @param {Object} node * @returns {Array} */ -function findUnresolvedVariables(node) { +function findUnresolvedVariables(node, log) { const results = []; - results.push(...(node.children.flatMap(findUnresolvedVariables))); + results.push(...(node.children.flatMap(v => findUnresolvedVariables(v, log)))); + + // if (log && node.name === 'VariableName') { + // console.log('node', node); + // } if (node.name === 'VariableName' && !node.value) { results.push(node.raw); @@ -210,6 +270,20 @@ function findUnresolvedVariables(node) { } +function annotateUsedVariables(node) { + node.children.forEach(v => annotateUsedVariables(v)); + + // console.log('node', node); + + if (node.name === 'VariableName') { + node.context.value.usedIn = node.context.value.used || []; + node.context.value.usedIn.push(node.raw); + } + + return node; +} + + /** * Transforms the entries of a variable from an array to an object. * This allows faster lookup times during parsing. diff --git a/lib/zeebe/util/variable-resolver.code-workspace b/lib/zeebe/util/variable-resolver.code-workspace new file mode 100644 index 0000000..bafaec9 --- /dev/null +++ b/lib/zeebe/util/variable-resolver.code-workspace @@ -0,0 +1,32 @@ +{ + "folders": [ + { + "path": "../../.." + }, + { + "path": "../../../../lezer-feel" + } + ], + "settings": { + "workbench.colorCustomizations": { + "activityBar.activeBackground": "#7586eb", + "activityBar.background": "#7586eb", + "activityBar.foreground": "#15202b", + "activityBar.inactiveForeground": "#15202b99", + "activityBarBadge.background": "#f7c7ce", + "activityBarBadge.foreground": "#15202b", + "commandCenter.border": "#e7e7e799", + "sash.hoverBorder": "#7586eb", + "statusBar.background": "#485fe5", + "statusBar.foreground": "#e7e7e7", + "statusBarItem.hoverBackground": "#7586eb", + "statusBarItem.remoteBackground": "#485fe5", + "statusBarItem.remoteForeground": "#e7e7e7", + "titleBar.activeBackground": "#485fe5", + "titleBar.activeForeground": "#e7e7e7", + "titleBar.inactiveBackground": "#485fe599", + "titleBar.inactiveForeground": "#e7e7e799" + }, + "peacock.remoteColor": "#485fe5" + } +} \ No newline at end of file diff --git a/test/fixtures/zeebe/complex.bpmn b/test/fixtures/zeebe/complex.bpmn index 1100a7d..710cc23 100644 --- a/test/fixtures/zeebe/complex.bpmn +++ b/test/fixtures/zeebe/complex.bpmn @@ -1,50 +1,295 @@ - - - + + + + - + + - - + Flow_174qkz1 + Flow_0pb9aeq + + + + + + + + + + + + + + + + + Flow_0pb9aeq + Flow_0cvkyib + + + + + + + + + Flow_1texudu + + + + + + + + Flow_0cvkyib + Flow_1eo9wnw + + + + + + + + + + + + + + + + + Flow_1eo9wnw + Flow_0yfc5wr + - - - + - - - - - - + + + + Flow_03lf7dj + Flow_1e9afuk + + + + - - + + + + + + + + + + + Flow_1951zff + Flow_1xw334v + + + + + + Flow_1px4tat + Flow_1951zff + + + + + + Flow_0yfc5wr + Flow_1px4tat + Flow_11pl8ni + + + + Flow_1e9afuk + Flow_0r4lyiy + Flow_1texudu + + + + + + + + + + + + + + + + + + + + + Flow_11pl8ni + Flow_0r4lyiy + + + + + + + + + + + + + + + + + + Flow_1xw334v + Flow_03lf7dj + + + + + + + + + Flow_174qkz1 + + 0 0 8 * * MON + + + + TODO + + - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - + + + - - + + + - - + + + + + - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +