Conversation
There was a problem hiding this comment.
Pull request overview
This pull request implements functionality to extract and track variables used in FEEL expressions within BPMN process definitions. The feature analyzes input mappings and script task expressions to identify which variables are required as inputs, creating "input requirement" entries that track dependencies between variables.
Changes:
- Added FEEL expression analysis using
@bpmn-io/feel-analyzerto extract input variables from expressions - Introduced
usedByproperty on ProcessVariable objects to track which target variables depend on each input - Added
getInputRequirementsForElementAPI method to retrieve input requirements for specific elements
Reviewed changes
Copilot reviewed 8 out of 9 changed files in this pull request and generated no comments.
Show a summary per file
| File | Description |
|---|---|
| package.json | Added dependencies for @bpmn-io/feel-analyzer and @camunda/feel-builtins to enable FEEL expression analysis |
| package-lock.json | Updated dependency tree with new packages and peer dependency resolutions |
| lib/zeebe/util/feelUtility.js | Core implementation: analyzes expressions with FeelAnalyzer, builds input requirements with deduplication and entry merging, filters scoped variables |
| lib/zeebe/VariableResolver.js | Integrates input requirements into the variable resolution pipeline |
| lib/base/VariableResolver.js | Adds getInputRequirementsForElement method, updates scope filtering to exclude input requirements, fixes async return type documentation |
| test/spec/zeebe/Mappings.spec.js | Comprehensive tests for input requirement extraction covering simple/nested expressions, deduplication, merging, scoping, and script tasks |
| test/fixtures/zeebe/mappings/input-requirements.bpmn | Test fixture with various input mapping scenarios |
| test/fixtures/zeebe/mappings/script-task-inputs.bpmn | Test fixture for script task input extraction |
| test/fixtures/zeebe/mappings/script-task-with-input-mappings.bpmn | Test fixture combining script tasks with input mappings |
Comments suppressed due to low confidence (3)
lib/base/VariableResolver.js:320
- The new public method
getInputRequirementsForElementhas no test coverage. Consider adding tests to verify that it correctly filters input requirements by element and handles edge cases like elements with no input requirements, multiple input requirements, and both diagram-js elements and moddle elements as parameters.
async getInputRequirementsForElement(element) {
const allVariablesByRoot = await this.getVariables()
.catch(() => {
return {};
});
const allVariables = Object.values(allVariablesByRoot).flat();
return allVariables.filter(v =>
v.usedBy && v.usedBy.length > 0
&& v.origin.length === 1 && v.origin[0].id === element.id
);
}
lib/base/VariableResolver.js:305
- The parameter type annotation for
elementshould be{ModdleElement}to be consistent with other methods in this class likegetProcessVariablesandgetVariablesForElementwhich use the same parameter type.
* @param {Object} element
lib/base/VariableResolver.js:318
- The method compares
v.origin[0].idwithelement.iddirectly, but the method might be called with a diagram-js element (which has a.businessObjectproperty) or a moddle element directly. Consider usinggetBusinessObject(element)likegetVariablesForElementdoes on line 256 to handle both cases correctly.
&& v.origin.length === 1 && v.origin[0].id === element.id
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
|
@barmac I've adjusted the behavior to follow the input mapping chain |
Hmm it looks that we still remove the variable which is required for the execution: Screen.Recording.2026-02-20.at.14.07.03.mov |
|
Sorry I didn't update the task testing PR yet. you need to test with (updated description) Screen.Recording.2026-02-20.at.14.20.03.mov |
|
Variables ordering in script:
So the script can use the inputs contrary to what the screenshot indicates. |
|
ATM it only looks at io mappings and script expressions. I can either just include all feel expressions (in the sense of any value starting with |
|
Gotcha. In that case, I think it's fine to move the complete support to a separate issue, but let's either fix or remove the script part. |
|
We don't want to check all of the values starting with |
ccce04e to
3120e8a
Compare
There was a problem hiding this comment.
Let's discuss the things mentioned:
- Performance - are we now "fast enough" with all built-ins used?
- Parsing - we parse the AST twice (this library, and
feel-analyzer) - does it matter, if so, how? inputRequrements, is that the name we want to use?- output mappings may establish dependencies
f4de807 to
7ff271b
Compare
test/spec/zeebe/Mappings.spec.js
Outdated
| const variables = await variableResolver.getConsumedVariablesForElement(task); | ||
|
|
||
| // then | ||
| const a = variables.find(v => v.name === 'a'); |
There was a problem hiding this comment.
We should use our existing helpers here:
expect(variables).to.variableInclude({
name: 'a',
usedBy: [ 'sum' ]
});
nikku
left a comment
There was a problem hiding this comment.
@Buckwich Could you update the PR description - to be clear on how the introduction of used variables as proposed changes the API surface?
- We have an existing API - will that contain used variables, or not?
- Especially as we have variable-outline in place, if that would want to show the variables for an element that are "used" - how would it do that, today?
➡️ Let's ensure both PR description and README updates clearly reflect the change in scope of this library - instead of "just looking at written variables" the library now gives you comprehensive intelligence on both written and consumed variables.
|
@Buckwich Can we have an environment (i.e. variable-int-up) to validate the changes E2E? I'd love to measure the end-user effect on typical diagrams. |
|
@barinali I'd like to summon you into the discussion - we will have |
Integration in desktop modeler: prefill-integration |
Thanks!
Eventually, yes. The question right now would be about how we want to proceed.
Variables exposed via
Agreed, but I'm unsure if we just want "variables related to this element" filter straight like that. I was thinking around the idea of giving the flexibility of individually filtering for;
I understand all three cases produce different narrowed down list of variables (compared to accessible variables) and provides different set of value. I think in case of debugging/inspection, all three filter modes may be valuable. |
I already did some experiments for that, but yeah currently waiting for the main changes in variables outline to be completed to avoid merge conflicts and we need to decide what to show. cf |
I'd start with the combined view, because less is more and await user feedback if they need more. |
So @barinali we should expose all variables via Perfect, this is what I needed. |
No, currently the main interface stays the same. but of course can be adjusted, but after the discussion in https://camunda.slack.com/archives/GP70M0J6M/p1772456953844339 I thought we agreed on this one Note:
|
|
I and @Buckwich have had a huddle about this. We both are on the same page about introducing The topic about changing the
|
|
Update from discussion:
|
|
Via #74 (review) I wanted us to show the E2E scope of this change - ensuring we add "used variables" in an integrated way. I went ahead and sketched how that integration could look like in this document. SummaryTo summarize the main takeaways:
Proposed addition to existing API// return only read variables, excluding local ones
const consumedVariables = variableResolver.getVariablesForElement(element, { read: true, local: false });
// return all written variables
const allWrittenVariables = variableResolver.getVariablesForElement(element, { written: true });
// return all variables (default)
const allVariables = variableResolver.getVariablesForElement(element); |
d873ddf to
dd46c34
Compare




Related to camunda/camunda-modeler#5639
Proposed Changes
runs feel-analyzer on every input "feel" expression (input mapping starting with
=and scripts) and adds them to raw variables without scopenew function
getInputRequirementsForElementcan be used by consumers to get those variablesvariables without scope are filtered out of the normal
getVariablesProbably best to try out in task testing demo:
Checklist
Ensure you provide everything we need to review your contribution:
Closes {LINK_TO_ISSUE}orRelated to {LINK_TO_ISSUE}@bpmn-io/srtool