Skip to content

Commit

Permalink
feat: add zeebe:taskDefinition binding
Browse files Browse the repository at this point in the history
This allows to template any properties of `zeebe:taskDefinition`,
including both currently supported `type` and `retries`.

Related to camunda/camunda-modeler#2936
  • Loading branch information
barmac committed Oct 30, 2023
1 parent 6f7d0d7 commit 1622a1c
Show file tree
Hide file tree
Showing 16 changed files with 266 additions and 68 deletions.
8 changes: 3 additions & 5 deletions src/cloud-element-templates/CreateHelper.js
Original file line number Diff line number Diff line change
Expand Up @@ -70,15 +70,13 @@ export function createTaskHeader(binding, value, bpmnFactory) {
/**
* Create a task definition representing the given value.
*
* @param {String} value
* @param {object} attrs
* @param {BpmnFactory} bpmnFactory
*
* @return {ModdleElement}
*/
export function createTaskDefinitionWithType(value, bpmnFactory) {
return bpmnFactory.create('zeebe:TaskDefinition', {
type: value
});
export function createTaskDefinition(attrs = {}, bpmnFactory) {
return bpmnFactory.create('zeebe:TaskDefinition', attrs);
}

/**
Expand Down
28 changes: 25 additions & 3 deletions src/cloud-element-templates/ElementTemplatesConditionChecker.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import { isObject } from 'min-dash';
import CommandInterceptor from 'diagram-js/lib/command/CommandInterceptor';

import { setPropertyValue, unsetProperty } from './util/propertyUtil';
import { MESSAGE_BINDING_TYPES } from './util/bindingTypes';
import { MESSAGE_BINDING_TYPES, ZEEBE_TASK_DEFINITION, ZEEBE_TASK_DEFINITION_TYPE_TYPE } from './util/bindingTypes';
import { removeMessage } from './util/rootElementUtil';

/**
Expand Down Expand Up @@ -104,14 +104,14 @@ function getMissingProperties(sourceTemplate, targetTemplate) {

function compareProps(sourceProp, targetProp) {
return (
equals(sourceProp.binding, targetProp.binding) &&
areBindingsEqual(sourceProp.binding, targetProp.binding) &&
equals(sourceProp.condition, targetProp.condition)
);
}

function findPropertyWithBinding(template, prop1) {
return template.properties.some(
prop2 => equals(prop1.binding, prop2.binding)
prop2 => areBindingsEqual(prop1.binding, prop2.binding)
);
}

Expand Down Expand Up @@ -140,6 +140,28 @@ function normalizeReplacer(key, value) {
return value;
}

function areBindingsEqual(binding1, binding2) {
binding1 = normalizeBinding(binding1);
binding2 = normalizeBinding(binding2);

return equals(binding1, binding2);
}

/**
* Convert deprecated binding type to new type.
*/
function normalizeBinding(binding) {
if (binding.type === ZEEBE_TASK_DEFINITION_TYPE_TYPE) {
return {
...binding,
type: ZEEBE_TASK_DEFINITION,
property: 'type'
};
}

return binding;
}

function equals(a, b) {
return JSON.stringify(a, normalizeReplacer) === JSON.stringify(b, normalizeReplacer);
}
Expand Down
53 changes: 24 additions & 29 deletions src/cloud-element-templates/cmd/ChangeElementTemplateHandler.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import {
import {
createInputParameter,
createOutputParameter,
createTaskDefinitionWithType,
createTaskDefinition,
createTaskHeader,
createZeebeProperty,
shouldUpdate
Expand All @@ -29,9 +29,14 @@ import { applyConditions } from '../Condition';

import {
MESSAGE_PROPERTY_TYPE,
MESSAGE_ZEEBE_SUBSCRIPTION_PROPERTY_TYPE
MESSAGE_ZEEBE_SUBSCRIPTION_PROPERTY_TYPE,
TASK_DEFINITION_TYPES
} from '../util/bindingTypes';

import {
getTaskDefinitionPropertyName
} from '../util/taskDefinition';

import {
createElement,
getRoot
Expand Down Expand Up @@ -201,7 +206,7 @@ export default class ChangeElementTemplateHandler {
const newBinding = newProperty.binding,
newBindingType = newBinding.type;

return newBindingType === 'zeebe:taskDefinition:type';
return TASK_DEFINITION_TYPES.includes(newBindingType);
});

// (1) do not override old task definition if no new properties specified
Expand All @@ -213,27 +218,18 @@ export default class ChangeElementTemplateHandler {

newProperties.forEach((newProperty) => {
const oldProperty = findOldProperty(oldTemplate, newProperty),
oldBinding = oldProperty && oldProperty.binding,
oldBindingType = oldBinding && oldBinding.type,
oldTaskDefinition = findBusinessObject(businessObject, newProperty),
newPropertyValue = getDefaultValue(newProperty),
newBinding = newProperty.binding,
newBindingType = newBinding.type;
propertyName = getTaskDefinitionPropertyName(newBinding);

// (2) update old task definition
if (oldTaskDefinition) {

if (!shouldKeepValue(oldTaskDefinition, oldProperty, newProperty)) {

// TODO(pinussilvestrus): for now we only support <type>
// this needs to be adjusted once we support more
let properties = {};

if (oldBindingType === 'zeebe:taskDefinition:type' || !oldBindingType) {
properties = {
type: newPropertyValue
};
}
const properties = {
[propertyName]: newPropertyValue
};

commandStack.execute('element.updateModdleProperties', {
element,
Expand All @@ -245,13 +241,11 @@ export default class ChangeElementTemplateHandler {

// (3) add new task definition
else {
let newTaskDefinition;
const properties = {
[propertyName]: newPropertyValue
};

// TODO(pinussilvestrus): for now we only support <type>
// this needs to be adjusted once we support more
if (newBindingType === 'zeebe:taskDefinition:type') {
newTaskDefinition = createTaskDefinitionWithType(newPropertyValue, bpmnFactory);
}
const newTaskDefinition = createTaskDefinition(properties, bpmnFactory);

newTaskDefinition.$parent = businessObject;

Expand Down Expand Up @@ -827,7 +821,7 @@ function findBusinessObject(element, property) {
const binding = property.binding,
bindingType = binding.type;

if (bindingType === 'zeebe:taskDefinition:type') {
if (TASK_DEFINITION_TYPES.includes(bindingType)) {
return findExtension(businessObject, 'zeebe:TaskDefinition');
}

Expand Down Expand Up @@ -904,12 +898,13 @@ export function findOldProperty(oldTemplate, newProperty) {
});
}

if (newBindingType === 'zeebe:taskDefinition:type') {
if (TASK_DEFINITION_TYPES.includes(newBindingType)) {
return find(oldProperties, function(oldProperty) {
const oldBinding = oldProperty.binding,
oldBindingType = oldBinding.type;
oldPropertyName = getTaskDefinitionPropertyName(oldBinding),
newPropertyName = getTaskDefinitionPropertyName(newBinding);

return oldBindingType === 'zeebe:taskDefinition:type';
return oldPropertyName === newPropertyName;
});
}

Expand Down Expand Up @@ -1059,8 +1054,8 @@ function getPropertyValue(element, property) {
return businessObject.get(bindingName);
}

if (bindingType === 'zeebe:taskDefinition:type') {
return businessObject.get('zeebe:type');
if (TASK_DEFINITION_TYPES.includes(bindingType)) {
return businessObject.get(getTaskDefinitionPropertyName(binding));
}

if (bindingType === 'zeebe:input') {
Expand Down Expand Up @@ -1098,4 +1093,4 @@ function remove(array, item) {
array.splice(index, 1);

return array;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,10 @@ import {
} from '../CreateHelper';
import { getDefaultValue } from '../Helper';

import {
getTaskDefinitionPropertyName
} from '../util/taskDefinition';


export default class TaskDefinitionTypeBindingProvider {
static create(element, options) {
Expand All @@ -12,8 +16,9 @@ export default class TaskDefinitionTypeBindingProvider {
} = options;

const value = getDefaultValue(property);
const propertyName = getTaskDefinitionPropertyName(property.binding);

const taskDefinition = ensureExtension(element, 'zeebe:TaskDefinition', bpmnFactory);
taskDefinition.set('type', value);
taskDefinition.set(propertyName, value);
}
}
}
6 changes: 4 additions & 2 deletions src/cloud-element-templates/create/TemplateElementFactory.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import {
import { find } from 'min-dash';

import PropertyBindingProvider from './PropertyBindingProvider';
import TaskDefinitionTypeBindingProvider from './TaskDefinitionTypeBindingProvider';
import TaskDefinitionBindingProvider from './TaskDefinitionBindingProvider';
import InputBindingProvider from './InputBindingProvider';
import OutputBindingProvider from './OutputBindingProvider';
import TaskHeaderBindingProvider from './TaskHeaderBindingProvider';
Expand All @@ -18,6 +18,7 @@ import {
MESSAGE_ZEEBE_SUBSCRIPTION_PROPERTY_TYPE,
PROPERTY_TYPE,
ZEEBE_TASK_DEFINITION_TYPE_TYPE,
ZEEBE_TASK_DEFINITION,
ZEBBE_INPUT_TYPE,
ZEEBE_OUTPUT_TYPE,
ZEEBE_TASK_HEADER_TYPE,
Expand All @@ -36,7 +37,8 @@ export default class TemplateElementFactory {

this._providers = {
[PROPERTY_TYPE]: PropertyBindingProvider,
[ZEEBE_TASK_DEFINITION_TYPE_TYPE]: TaskDefinitionTypeBindingProvider,
[ZEEBE_TASK_DEFINITION_TYPE_TYPE]: TaskDefinitionBindingProvider,
[ZEEBE_TASK_DEFINITION]: TaskDefinitionBindingProvider,
[ZEBBE_PROPERTY_TYPE]: ZeebePropertiesProvider,
[ZEBBE_INPUT_TYPE]: InputBindingProvider,
[ZEEBE_OUTPUT_TYPE]: OutputBindingProvider,
Expand Down
2 changes: 2 additions & 0 deletions src/cloud-element-templates/properties/CustomProperties.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import {
import {
PROPERTY_TYPE,
ZEEBE_TASK_DEFINITION_TYPE_TYPE,
ZEEBE_TASK_DEFINITION,
ZEBBE_INPUT_TYPE,
ZEEBE_OUTPUT_TYPE,
ZEEBE_PROPERTY_TYPE,
Expand Down Expand Up @@ -195,6 +196,7 @@ function getDefaultType(property) {
if ([
PROPERTY_TYPE,
ZEEBE_TASK_DEFINITION_TYPE_TYPE,
ZEEBE_TASK_DEFINITION,
ZEBBE_INPUT_TYPE,
ZEEBE_OUTPUT_TYPE,
ZEEBE_PROPERTY_TYPE,
Expand Down
5 changes: 4 additions & 1 deletion src/cloud-element-templates/util/bindingTypes.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ export const ZEBBE_INPUT_TYPE = 'zeebe:input';
export const ZEEBE_OUTPUT_TYPE = 'zeebe:output';
export const ZEEBE_PROPERTY_TYPE = 'zeebe:property';
export const ZEEBE_TASK_DEFINITION_TYPE_TYPE = 'zeebe:taskDefinition:type';
export const ZEEBE_TASK_DEFINITION = 'zeebe:taskDefinition';
export const ZEEBE_TASK_HEADER_TYPE = 'zeebe:taskHeader';
export const MESSAGE_PROPERTY_TYPE = 'bpmn:Message#property';
export const MESSAGE_ZEEBE_SUBSCRIPTION_PROPERTY_TYPE = 'bpmn:Message#zeebe:subscription#property';
Expand All @@ -15,11 +16,13 @@ export const EXTENSION_BINDING_TYPES = [
ZEEBE_OUTPUT_TYPE,
ZEEBE_PROPERTY_TYPE,
ZEEBE_TASK_DEFINITION_TYPE_TYPE,
ZEEBE_TASK_DEFINITION,
ZEEBE_TASK_HEADER_TYPE
];

export const TASK_DEFINITION_TYPES = [
ZEEBE_TASK_DEFINITION_TYPE_TYPE
ZEEBE_TASK_DEFINITION_TYPE_TYPE,
ZEEBE_TASK_DEFINITION
];

export const IO_BINDING_TYPES = [
Expand Down
Loading

0 comments on commit 1622a1c

Please sign in to comment.