Skip to content

Commit

Permalink
wip: synchronize on converging gateway
Browse files Browse the repository at this point in the history
  • Loading branch information
barmac committed Feb 6, 2022
1 parent f97594c commit cd10989
Showing 1 changed file with 73 additions and 3 deletions.
76 changes: 73 additions & 3 deletions lib/simulator/behaviors/InclusiveGatewayBehavior.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {
filterSequenceFlows
filterSequenceFlows, isSequenceFlow
} from '../util/ModelUtil';


Expand All @@ -14,7 +14,30 @@ export default function InclusiveGatewayBehavior(
}

InclusiveGatewayBehavior.prototype.enter = function(context) {
this._simulator.exit(context);
const {
scope,
element
} = context;

const incomingSequenceFlows = filterSequenceFlows(element.incoming);

if (incomingSequenceFlows.length === 1) {
return this._simulator.exit(context);
}

const {
parent: parentScope
} = scope;

const sameParentScopes = this._simulator.findScopes(scope => (
scope.parent === parentScope && scope.element !== element));

// There are still some tokens to wait for.
if (this._canReachAnyScope(sameParentScopes, element)) {
return;
}

this._join(context);
};

InclusiveGatewayBehavior.prototype.exit = function(context) {
Expand Down Expand Up @@ -52,7 +75,54 @@ InclusiveGatewayBehavior.prototype.exit = function(context) {
}
};

InclusiveGatewayBehavior.prototype._join = function(context) {
const elementScopes = this._simulator.findScopes({
parent: context.parent,
element: context.element
});

for (const childScope of elementScopes) {

if (childScope !== context.scope) {

// complete joining child scope
this._simulator.destroyScope(childScope.complete(), context.scope);
}
}

this._simulator.exit(context);
};

InclusiveGatewayBehavior.prototype._canReachAnyScope = function(scopes, currentElement, traversed = new Set()) {
if (traversed.has(currentElement)) {
return false;
}

if (anyScopeIsOnElement(scopes, currentElement)) {
return true;
}

if (isSequenceFlow(currentElement)) {
return this._canReachAnyScope(scopes, currentElement.source, traversed);
}


const incomingFlows = filterSequenceFlows(currentElement.incoming);

for (const flow of incomingFlows) {
if (this._canReachAnyScope(scopes, flow, traversed)) {
return true;
}
}

return false;
};

InclusiveGatewayBehavior.$inject = [
'simulator',
'activityBehavior'
];
];

function anyScopeIsOnElement(scopes, element) {
return scopes.some(scope => scope.element === element);
}

0 comments on commit cd10989

Please sign in to comment.