Using Form Field's enum values in an external form

Hello Everybody…

According to the documentation, when using and external Form (with AngularJS) you could use the directive “cam-variable-name” to bind fields. You could also use “cam-choices” to bind an enumeration to the options, like the example bellow.

<select cam-variable-name="PRODUCT_TYPE"
        cam-variable-type="String"
        cam-choices="AVAILABLE_PRODUCT_TYPES">
</select>

However, it’s not clear where should I configure this enumeration (in the example, AVAILABLE_PRODUCT_TYPES).

When I’m creating the fields, in Modeler, I can define the enum values/labels but I tried using the field name in cam-choices and it doesn’t work.
What value should I pass to cam-choices to bind it to the field’s enum values?

Hi @fcordova

Are the values static? Than you could do the following:

<select cam-variable-name="PRODUCT_TYPE"
        cam-variable-type="String">
  <option>drink</option>
  <option>food</option>
</select> 

If you want to use cam-choices the variable should be a map or a list stored by the engine for the current instance. Take a look at that page. You can’t use the enum values defined in the modeler -> that are options for the generated forms.

You could load your enum values before the User Task is started by an execution listener.
There you could do something like that:

Map<String, String> productTypes = new HashMap<String, String>();
productTypes.put("001", "Notebook");
productTypes.put("002", "Server");
productTypes.put("003", "Workstation");

execution.setVariable("AVAILABLE_PRODUCT_TYPES",  
  objectValue(productTypes)
    .serializationDataFormat(SerializationDataFormats.JSON)
    .create());

regards,
Dominik

Hi Dominik, thanks for your reply…

The values are static although they may change when process evolves.
Since I could have different forms used in different activities (external ou generated), wouldn’t it make sense to bind the options directly to the values defined in the modeler for that field, so all these forms would reflect the current values?

Setting these values as a process’s variable could work but still feels like it’s more complicated than it should be, isn’t it ?
Maybe the directive could use the field’s definition by default, if no value is defined, like this:

<select cam-variable-name="PRODUCT_TYPE"
        cam-variable-type="String"
        cam-choices>
</select>

Hi,

but how can you define them in the modeler if the values you can choose are changing?

In my point of view generated forms are for prototyping. I think it doesn’t make sense to mix that up with embedded forms. However you could write a “dynamic” execution listener that checks the extension elements of your user tasks for enums and then adds the values to a map that is serialized to JSON. Here is some line of code that would do that: (Had problems with the serialization)

public void setEnumValues(DelegateExecution execution) {

    		CamundaFormData formData = execution.getBpmnModelElementInstance().getExtensionElements().getElementsQuery()
				.filterByType(CamundaFormData.class).singleResult();
		Collection<CamundaFormField> fields = formData.getCamundaFormFields();
		for (CamundaFormField field : fields) {
			if (field.getCamundaType().equals("enum")) {
				Map<String, String> enumValues = new HashMap<String, String>();
				String id = field.getCamundaId();
				Collection<CamundaValue> values = field.getCamundaValues();
				for (CamundaValue value : values) {
					enumValues.put(value.getCamundaId(), value.getCamundaName());
				}
			
				//Before that Serialize the enumValues to JSON
				execution.setVariable(id, enumValues);
			}
		}
	}

Wouldn’t recommend to do that but have a try :slight_smile:

regards,
Dominik

Hi @dominikh, thanks for your reply…

Consider the kind of information that is not dynamic enough to “deserve” a CRUD but is also not so static to be hardcoded in the form.

You’re probably right but that’s not the main point here. It’s not about what kind of form is more suitable (even because it’s more a matter of personal preferences, time or technical skills :smile:) but to have the process consistent along all activities…

If my business user (who has modeled the process) has defined an enum to a field, it should be consistently used everywhere in the process, no matter if I use generated, embedded or external forms.
So, the developer (who has created the form) should not be able to override that definition. If the process has different views (forms) in different activities and each one defines its own options (not in sync with the model), there is a high risk to the process to be inconsistent.

I understand it could be solved with a bit of code but I believe the whole intent of a bpm engine is to empower business users to model their process by themselves and every time we ask them to add code to make things to work, a little fairy dies somewhere… :smile:
Don’t get me wrong, I really know the engine won’t be so magical that you’ll never need to code again but it should work in the simplest cases.

But that’s more a philosophical issue and, as far as I could understand, it’s a feature request, right ?
Where could I open a ticket for that ? GitHub?

Hi @fcordova

So first you want to reuse enums (maybe with a select field) created in the model for Task1 in Task2 and second you want to use that enums for external/embedded forms that had to be created because the generated forms where not suitable enough right?

So what has to be done is:

  1. Before starting a Task with a Form, check the extension elements if there is an external/embedded form and than load the enums into the instance variables.
  2. Modify the modeler so that you have some kind of repository of current used enums.
    right?

You could create a global Execution Listener that is used for every single task for the 1. issue :wink:

I understand your idea of the behavior but I don’t know if that is a common use case.

Maybe someone from @camunda can help?

regards,
Dominik

Hi @fcordova,

Modeling yes, but automating the processes by the business users themselves fails most of the times. That’s where software development comes on the stage. Embedded Forms are much more powerful than generated forms and they can serve in the core processes of an enterprise.

You can open a JIRA ticket for your feature request, and if you like also contribute a solution with a pull request on github.

Cheers, Ingo

1 Like