Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

refactor: use the new flow/flownode links from the bpmn semantic in the predictions demo #515

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions demo/predictions/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
<script defer src="https://cdn.jsdelivr.net/npm/[email protected]/dist/bpmn-visualization.min.js"></script>
<script defer src="../../examples/static/js/diagram/bpmn-diagram-bpmn-spec-pizza.js"></script>
<script defer src="../static/js/use-case.js"></script>
<script defer src="./js/path.js"></script>
<script defer src="./js/data.js"></script>
<script defer src="./js/style.js"></script>
<script defer src="./js/prediction-use-case.js"></script>
Expand Down
133 changes: 52 additions & 81 deletions demo/predictions/js/data.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,65 +6,34 @@ class ExecutionData {

_vendorWhereIsMyPizzaId = '_6-674';

#runningElementsWithoutPrediction = [this._vendorWhereIsMyPizzaId, this._customerEvtBasedGwId];
_commonExecutedElements;

_commonExecutedElements = [
// customer
'_6-61', // start event
'_6-125', // sequence flow between 'start event' and 'select pizza'
'_6-74', // select a pizza
'_6-178', // sequence flow between 'select a pizza' and 'order a pizza'
'_6-127', // order a pizza
'_6-420', // sequence flow between 'order a pizza' and 'event-based gateway' (running element)

'_6-638', // message flow

// vendor
'_6-450', // order received
'_6-630', // sequence flow between 'order received' and 'parallel gateway'
'_6-652', // parallel gateway
'_6-693', // sequence flow between 'parallel gateway' and 'Bake the pizza'
'_6-691', // sequence flow between 'parallel gateway' and 'where is my pizza'
];
_executedElements;

get executedElements() {
return [];
}
_runningElementWithPrediction;

get runningElementWithPrediction() {
return null;
}
_predictedPaths;

get predictedPaths() {
return null;
}
#runningElementsWithoutPrediction = [this._vendorWhereIsMyPizzaId, this._customerEvtBasedGwId];

get runningElementsWithoutPrediction() {
return this.#runningElementsWithoutPrediction;
}
}
_pathResolver;

class PredicatedLateExecutionData extends ExecutionData {
constructor(pathResolver) {
this._pathResolver = pathResolver;
this._commonExecutedElements = pathResolver.getVisitedEdges([
// customer
'_6-61', // start event
'_6-74', // select a pizza
'_6-127', // order a pizza

_runningElementWithPrediction = this._vendorBakeThePizzaId;

_predictedPaths = [
// customer elements
this._customerEvtBasedGwId,
'_6-424', // sequence flow between 'event-based gateway' (running element) and timer event
'_6-219', // timer event
'_6-426', // sequence flow between 'timer event' and 'Ask for the pizza'
'_6-236', // 'Ask for the pizza'
// message flow
'_6-642',
// vendor elements
this._vendorWhereIsMyPizzaId,
'_6-748', // sequence flow between 'where is my pizza' and 'Calm customer'
'_6-695', // 'Calm customer'
];
// vendor
'_6-450', // order received
'_6-652', // parallel gateway
]);
}

get executedElements() {
return this._commonExecutedElements;
return this._executedElements;
}

get runningElementWithPrediction() {
Expand All @@ -75,43 +44,45 @@ class PredicatedLateExecutionData extends ExecutionData {
return this._predictedPaths;
}

get runningElementsWithoutPrediction() {
return this.#runningElementsWithoutPrediction;
}
}

class PredictedOnTimeExecutionData extends ExecutionData {

// vendor 'Deliver the pizza'
_runningElementWithPrediction = '_6-514';

_predictedPaths = [
// customer elements
this._customerEvtBasedGwId,
'_6-422', // sequence flow between 'event-based gateway' (running element) and msg event
'_6-202', // msg event 'Pizza received'
'_6-428', // sequence flow between 'msg event' and 'Pay the pizza'
'_6-304', // 'Pay the pizza'
// message flow
'_6-640', // from vendor 'Deliver the pizza' to customer 'msg event'
// vendor elements
'_6-634', // sequence flow between 'Deliver the pizza' and 'Receive payment'
'_6-565', // 'Receive payment'
];

_executedElements = [...this._commonExecutedElements,
// vendor
this._vendorBakeThePizzaId,
'_6-632', // sequence flow between 'Bake the pizza' and 'Deliver the pizza'
];
class PredicatedLateExecutionData extends ExecutionData {

get executedElements() {
return this._executedElements;
constructor(pathResolver) {
super(pathResolver)

this._executedElements = this._commonExecutedElements;
this._runningElementWithPrediction = this._vendorBakeThePizzaId;
this._predictedPaths = pathResolver.getVisitedEdges([
// customer elements
this._customerEvtBasedGwId,
'_6-219', // timer event
'_6-236', // 'Ask for the pizza'
// vendor elements
this._vendorWhereIsMyPizzaId,
'_6-695', // 'Calm customer'
]);
}
}

get runningElementWithPrediction() {
return this._runningElementWithPrediction;
}
class PredictedOnTimeExecutionData extends ExecutionData {

get predictedPaths() {
return this._predictedPaths;
constructor(pathResolver) {
super(pathResolver)

this._executedElements = pathResolver.getVisitedEdges([...this._commonExecutedElements, this._vendorBakeThePizzaId ]);
this._runningElementWithPrediction = '_6-514'; // vendor 'Deliver the pizza'
this._predictedPaths = pathResolver.getVisitedEdges([
// customer elements
this._customerEvtBasedGwId,
'_6-202', // msg event 'Pizza received'
'_6-304', // 'Pay the pizza'
// vendor elements
'_6-565', // 'Receive payment'
]);
}

}
43 changes: 43 additions & 0 deletions demo/predictions/js/path.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
// From Bonita Day 2023 Demo
class PathResolver {
Copy link
Member

@tbouffard tbouffard Jun 27, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

issue: we cannot duplicate the code from the demo.
We already know it requires refactoring at least for process-analytics/bonita-day-demo-2023#52. There are also a lot of extra validation of the incoming/outgoing (verification that a related edge id exists in the model) whereas this should be guarantee by bpmn-visualization.
In addition, we plan to extract PathResolver from the bonita day demo process-analytics/bonita-day-demo-2023#36. If we duplicate the implementation here, we must track it and plan to use the shared code here. And this may not possible out of the box depending on the way we package the shared code. In particular, we are not sure to to provide an IIFE bundle for the shared lib.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To replace in another PR. See #260

_bpmnVisualization;

constructor(bpmnVisualization) {
this._bpmnVisualization = bpmnVisualization;
}

getVisitedEdges(shapeIds) {
const edgeIds = new Set();
for (const shapeId of shapeIds) {
const shapeElt = this._bpmnVisualization.bpmnElementsRegistry.getElementsByIds(shapeId)[0];
if (!shapeElt) {
continue;
}

const bpmnSemantic = shapeElt.bpmnSemantic;
const incomingEdges = bpmnSemantic.incomingIds;
if (incomingEdges) {
for (const edgeId of incomingEdges) {
const edgeElement = this._bpmnVisualization.bpmnElementsRegistry.getElementsByIds(edgeId)[0];
const sourceRef = edgeElement.bpmnSemantic.sourceRefId;
if (shapeIds.includes(sourceRef)) {
edgeIds.add(edgeId);
}
}
}

const outgoingEdges = bpmnSemantic.outgoingIds;
if (outgoingEdges) {
for (const edgeId of outgoingEdges) {
const edgeElement = this._bpmnVisualization.bpmnElementsRegistry.getElementsByIds(edgeId)[0];
const targetRef = edgeElement.bpmnSemantic.targetRefId;
if (shapeIds.includes(targetRef)) {
edgeIds.add(edgeId);
}
}
}
}

return Array.from(edgeIds);
}
}
16 changes: 7 additions & 9 deletions demo/predictions/js/prediction-use-case.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,20 +5,21 @@ class PredicatedLateUseCase extends UseCase {

constructor(type) {
super(type, () => pizzaDiagram(), true, {fit: {type: 'Center', margin: 20}});
this._executionData = new PredicatedLateExecutionData();
}

_postLoadDiagram() {
this._initManager();
this._initManagers();

this._style.reduceVisibilityOfExecutedElements(this._executionData.executedElements);
this._style.highlightRunningElementsWithPrediction(this._executionData.runningElementWithPrediction);
this._style.toggleHighlightRunningElementsWithoutPrediction(this._executionData.runningElementsWithoutPrediction);
this._registerInteractions(this._executionData.predictedPaths, this._executionData.runningElementsWithoutPrediction, this._executionData.runningElementWithPrediction);
}

_initManager() {
_initManagers() {
this._style = new PredicatedLateStyle(this._bpmnVisualization.bpmnElementsRegistry);
const pathResolver = new PathResolver(this._bpmnVisualization);
this._executionData = new PredicatedLateExecutionData(pathResolver);
}

_registerInteractions(predictedPath, runningElementsWithoutPrediction, runningElementWithPrediction) {
Expand All @@ -37,12 +38,9 @@ class PredicatedLateUseCase extends UseCase {


class PredictedOnTimeUseCase extends PredicatedLateUseCase {
constructor(type) {
super(type);
this._executionData = new PredictedOnTimeExecutionData();
}

_initManager() {
_initManagers() {
this._style = new PredictedOnTimeStyle(this._bpmnVisualization.bpmnElementsRegistry);
const pathResolver = new PathResolver(this._bpmnVisualization);
this._executionData = new PredictedOnTimeExecutionData(pathResolver);
}
}