Skip to content
Open
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
12 changes: 0 additions & 12 deletions application-engine/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -270,18 +270,6 @@
<version>${junit-jupiter.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-api</artifactId>
<version>${junit-jupiter.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-engine</artifactId>
<version>${junit-jupiter.version}</version>
<scope>test</scope>
</dependency>
<!-- Groovy -->
<!-- https://mvnrepository.com/artifact/org.codehaus.groovy/groovy-all -->
<dependency>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,8 @@ public class DataService implements IDataService {

public static final int MONGO_ID_LENGTH = 24;

private static final Set<FieldType> setDataForbiddenFieldTypes = Set.of(FieldType.TASK_REF, FieldType.CASE_REF);

@Autowired
protected ApplicationEventPublisher publisher;

Expand Down Expand Up @@ -220,6 +222,22 @@ public SetDataEventOutcome setData(Task task, ObjectNode values) {

@Override
public SetDataEventOutcome setData(Task task, ObjectNode values, Map<String, String> params) {
return setData(task, values, params, false);
}

/**
* Updates the data field's attributes of the provided task.
*
* @param task the task object of which the data are updated
* @param values information about how to update the data fields
* @param params additional information to be injected to the action delegate context
* @param runStrict if set to true, additional validations are going to be applied when updating the data fields. If
* set to false, minimal restrictions are considered.
*
* @return outcome containing Case, Task and changes that have been made.
* */
@Override
public SetDataEventOutcome setData(Task task, ObjectNode values, Map<String, String> params, boolean runStrict) {
Case useCase = workflowService.findOne(task.getCaseId());
AbstractUser user = userService.getLoggedOrSystem();

Expand All @@ -231,8 +249,20 @@ public SetDataEventOutcome setData(Task task, ObjectNode values, Map<String, Str
SetDataEventOutcome outcome = new SetDataEventOutcome(useCase, task);
values.fields().forEachRemaining(entry -> {
String fieldId = entry.getKey();
if (runStrict) {
Field<?> field = useCase.getField(fieldId);
if (field == null) {
throw new IllegalArgumentException("Such field with id [" + fieldId + "] does not exist in petri net [" + useCase.getPetriNetId() + "]");
}
if (setDataForbiddenFieldTypes.contains(field.getType())) {
return;
}
}
DataField dataField = useCase.getDataSet().get(fieldId);
if (dataField != null) {
if (runStrict && !isDataFieldEditable(dataField, task.getTransitionId())) {
throw new IllegalArgumentException("Cannot edit data field [" + fieldId + "], which is not editable on transition [" + task.getTransitionId() + "].");
}
Field field = useCase.getPetriNet().getField(fieldId).get();
outcome.addOutcomes(resolveDataEvents(field, DataEventType.SET, EventPhase.PRE, useCase, task, params));
if (outcome.getMessage() == null) {
Expand Down Expand Up @@ -303,6 +333,15 @@ public SetDataEventOutcome setData(Task task, ObjectNode values, Map<String, Str
return outcome;
}

private boolean isDataFieldEditable(DataField dataField, String transId) {
Map<String, Set<FieldBehavior>> behaviorMap = dataField.getBehavior();
if (behaviorMap == null) {
return false;
}
Set<FieldBehavior> behaviorSet = behaviorMap.get(transId);
return behaviorSet != null && behaviorSet.contains(FieldBehavior.EDITABLE);
}

@Override
public GetDataGroupsEventOutcome getDataGroups(String taskId, Locale locale) {
return getDataGroups(taskId, locale, new HashSet<>(), 0, null);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -976,6 +976,9 @@ public SetDataEventOutcome getMainOutcome(Map<String, SetDataEventOutcome> outco
}
}
mainOutcome = outcomes.remove(key);
if (mainOutcome == null) {
return null;
}
mainOutcome.addOutcomes(new ArrayList<>(outcomes.values()));
return mainOutcome;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@ public interface IDataService {

SetDataEventOutcome setData(Task task, ObjectNode values, Map<String, String> params);

SetDataEventOutcome setData(Task task, ObjectNode values, Map<String, String> params, boolean runStrict);

FileFieldInputStream getFile(Case useCase, Task task, FileField field, boolean forPreview) throws FileNotFoundException;

FileFieldInputStream getFile(Case useCase, Task task, FileField field, boolean forPreview, Map<String, String> params) throws FileNotFoundException;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@
import com.netgrif.application.engine.elastic.service.interfaces.IElasticTaskService;
import com.netgrif.application.engine.elastic.web.requestbodies.singleaslist.SingleElasticTaskSearchRequestAsList;
import com.netgrif.application.engine.eventoutcomes.LocalisedEventOutcomeFactory;
import com.netgrif.application.engine.objects.petrinet.domain.dataset.FieldType;
import com.netgrif.application.engine.objects.petrinet.domain.dataset.localised.LocalisedField;
import com.netgrif.application.engine.workflow.web.responsebodies.LocalisedTaskResource;
import com.netgrif.application.engine.objects.petrinet.domain.throwable.TransitionNotExecutableException;
import com.netgrif.application.engine.workflow.domain.IllegalArgumentWithChangedFieldsException;
Expand All @@ -19,6 +21,7 @@
import com.netgrif.application.engine.workflow.service.FileFieldInputStream;
import com.netgrif.application.engine.workflow.service.interfaces.IDataService;
import com.netgrif.application.engine.workflow.service.interfaces.ITaskService;
import com.netgrif.application.engine.workflow.service.interfaces.IWorkflowService;
import com.netgrif.application.engine.workflow.web.requestbodies.file.FileFieldRequest;
import com.netgrif.application.engine.workflow.web.requestbodies.singleaslist.SingleTaskSearchRequestAsList;
import com.netgrif.application.engine.workflow.web.responsebodies.*;
Expand All @@ -41,10 +44,8 @@
import org.springframework.web.multipart.MultipartFile;

import java.io.FileNotFoundException;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.*;
import java.util.stream.Collectors;

public abstract class AbstractTaskController {

Expand All @@ -54,17 +55,21 @@ public abstract class AbstractTaskController {

private final IDataService dataService;

private final IWorkflowService workflowService;

private final IElasticTaskService searchService;

private final UserService userService;

public AbstractTaskController(ITaskService taskService,
IDataService dataService,
IElasticTaskService searchService,
IWorkflowService workflowService,
UserService userService) {
this.taskService = taskService;
this.dataService = dataService;
this.searchService = searchService;
this.workflowService = workflowService;
this.userService = userService;
}

Expand Down Expand Up @@ -216,9 +221,32 @@ public EntityModel<EventOutcomeWithMessage> getData(String taskId, Locale locale

public EntityModel<EventOutcomeWithMessage> setData(String taskId, ObjectNode dataBody, Locale locale) {
try {
List<com.netgrif.application.engine.objects.petrinet.domain.DataGroup> dataGroups = dataService.getDataGroups(taskId, locale).getData();
Set<String> referencedTaskIds = new HashSet<>();
referencedTaskIds.add(taskId);
for (com.netgrif.application.engine.objects.petrinet.domain.DataGroup dataGroup : dataGroups) {
Set<String> referencedTaskIdsByDataGroup = dataGroup.getFields().getContent().stream()
.filter(someField -> someField instanceof LocalisedField localisedField
&& localisedField.getType() == FieldType.TASK_REF
&& localisedField.getValue() instanceof List
&& !((List<?>) localisedField.getValue()).isEmpty())
.map(localisedField -> (List<String>) ((LocalisedField) localisedField).getValue())
.flatMap(List::stream)
.collect(Collectors.toSet());
referencedTaskIds.addAll(referencedTaskIdsByDataGroup);
}
Map<String, SetDataEventOutcome> outcomes = new HashMap<>();
dataBody.fields().forEachRemaining(it -> outcomes.put(it.getKey(), dataService.setData(it.getKey(), it.getValue().deepCopy())));
dataBody.fields().forEachRemaining(fieldChangesEntry -> {
String taskIdToChangeWith = fieldChangesEntry.getKey();
if (!referencedTaskIds.contains(taskIdToChangeWith)) {
return;
}
Task taskToChangeWith = taskService.findOne(taskIdToChangeWith);
outcomes.put(taskIdToChangeWith, dataService.setData(taskToChangeWith,
fieldChangesEntry.getValue().deepCopy(), new HashMap<>(), true));
});
SetDataEventOutcome mainOutcome = taskService.getMainOutcome(outcomes, taskId);
mainOutcome = handleMainSetDataEventOutcome(mainOutcome, taskId);
return EventOutcomeWithMessageResource.successMessage("Data field values have been successfully set",
LocalisedEventOutcomeFactory.from(mainOutcome, LocaleContextHolder.getLocale()));
} catch (IllegalArgumentWithChangedFieldsException e) {
Expand All @@ -236,6 +264,7 @@ public EntityModel<EventOutcomeWithMessage> saveFile(String taskId, MultipartFil
Map<String, SetDataEventOutcome> outcomes = new HashMap<>();
outcomes.put(dataBody.getParentTaskId(), dataService.saveFile(dataBody.getParentTaskId(), dataBody.getFieldId(), multipartFile));
SetDataEventOutcome mainOutcome = taskService.getMainOutcome(outcomes, taskId);
mainOutcome = handleMainSetDataEventOutcome(mainOutcome, taskId);
return EventOutcomeWithMessageResource.successMessage("Data field values have been successfully set",
LocalisedEventOutcomeFactory.from(mainOutcome, LocaleContextHolder.getLocale()));
} catch (IllegalArgumentWithChangedFieldsException e) {
Expand Down Expand Up @@ -268,15 +297,17 @@ public EntityModel<EventOutcomeWithMessage> deleteFile(String taskId, String fie
Map<String, SetDataEventOutcome> outcomes = new HashMap<>();
outcomes.put(taskId, dataService.deleteFile(taskId, fieldId));
SetDataEventOutcome mainOutcome = taskService.getMainOutcome(outcomes, taskId);
return EventOutcomeWithMessageResource.successMessage("Data field values have been sucessfully set",
mainOutcome = handleMainSetDataEventOutcome(mainOutcome, taskId);
return EventOutcomeWithMessageResource.successMessage("Data field values have been successfully set",
LocalisedEventOutcomeFactory.from(mainOutcome, LocaleContextHolder.getLocale()));
}

public EntityModel<EventOutcomeWithMessage> saveFiles(String taskId, MultipartFile[] multipartFiles, FileFieldRequest requestBody) {
Map<String, SetDataEventOutcome> outcomes = new HashMap<>();
outcomes.put(requestBody.getParentTaskId(), dataService.saveFiles(requestBody.getParentTaskId(), requestBody.getFieldId(), multipartFiles));
SetDataEventOutcome mainOutcome = taskService.getMainOutcome(outcomes, taskId);
return EventOutcomeWithMessageResource.successMessage("Data field values have been sucessfully set",
mainOutcome = handleMainSetDataEventOutcome(mainOutcome, taskId);
return EventOutcomeWithMessageResource.successMessage("Data field values have been successfully set",
LocalisedEventOutcomeFactory.from(mainOutcome, LocaleContextHolder.getLocale()));
}

Expand All @@ -300,7 +331,8 @@ public EntityModel<EventOutcomeWithMessage> deleteNamedFile(String taskId, Strin
Map<String, SetDataEventOutcome> outcomes = new HashMap<>();
outcomes.put(taskId, dataService.deleteFileByName(taskId, fieldId, name));
SetDataEventOutcome mainOutcome = taskService.getMainOutcome(outcomes, taskId);
return EventOutcomeWithMessageResource.successMessage("Data field values have been sucessfully set",
mainOutcome = handleMainSetDataEventOutcome(mainOutcome, taskId);
return EventOutcomeWithMessageResource.successMessage("Data field values have been successfully set",
LocalisedEventOutcomeFactory.from(mainOutcome, LocaleContextHolder.getLocale()));
}

Expand All @@ -316,4 +348,13 @@ public ResponseEntity<Resource> getFilePreview(String taskId, String fieldId) th
.headers(headers)
.body(fileFieldInputStream != null ? new InputStreamResource(fileFieldInputStream.getInputStream()) : null);
}

protected SetDataEventOutcome handleMainSetDataEventOutcome(SetDataEventOutcome mainOutcome, String taskId) {
if (mainOutcome == null) {
Task task = taskService.findOne(taskId);
return new SetDataEventOutcome(workflowService.findOne(task.getCaseId()), task);
} else {
return mainOutcome;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
import com.netgrif.application.engine.workflow.domain.eventoutcomes.response.EventOutcomeWithMessage;
import com.netgrif.application.engine.workflow.service.interfaces.IDataService;
import com.netgrif.application.engine.workflow.service.interfaces.ITaskService;
import com.netgrif.application.engine.workflow.service.interfaces.IWorkflowService;
import com.netgrif.application.engine.workflow.web.requestbodies.file.FileFieldRequest;
import com.netgrif.application.engine.workflow.web.requestbodies.singleaslist.SingleTaskSearchRequestAsList;
import com.netgrif.application.engine.workflow.web.responsebodies.LocalisedTaskResource;
Expand Down Expand Up @@ -54,8 +55,9 @@ public class PublicTaskController extends AbstractTaskController {

public PublicTaskController(ITaskService taskService,
IDataService dataService,
IWorkflowService workflowService,
UserService userService) {
super(taskService, dataService, null, userService);
super(taskService, dataService, null, workflowService, userService);
this.taskService = taskService;
this.dataService = dataService;
this.userService = userService;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
import com.netgrif.application.engine.workflow.domain.eventoutcomes.response.EventOutcomeWithMessage;
import com.netgrif.application.engine.workflow.service.interfaces.IDataService;
import com.netgrif.application.engine.workflow.service.interfaces.ITaskService;
import com.netgrif.application.engine.workflow.service.interfaces.IWorkflowService;
import com.netgrif.application.engine.workflow.web.requestbodies.file.FileFieldRequest;
import com.netgrif.application.engine.workflow.web.requestbodies.singleaslist.SingleTaskSearchRequestAsList;
import com.netgrif.application.engine.workflow.web.responsebodies.CountResponse;
Expand Down Expand Up @@ -55,8 +56,9 @@ public class TaskController extends AbstractTaskController {
public TaskController(ITaskService taskService,
IDataService dataService,
IElasticTaskService searchService,
IWorkflowService workflowService,
UserService userService) {
super(taskService, dataService, searchService, userService);
super(taskService, dataService, searchService, workflowService, userService);
}

@Override
Expand Down
Loading