conductor-oss / conductor-oss/conductor

[FEATURE]: Support system tasks other than the SubWorkflow task as parent of a Sub Workflow

Open
#386 0 comments 0 reactions 0 assignees View on GitHub
enhancement
Dominant language
Java
Stars
32.2k
Forks
1k
Avg merge
2d 3h
Merged PRs (30d)
37

Description

## Describe the Feature Request

I have been working on an custom system task that launches multiple SubWorkflows in a loop. However, I found there were a number of places with logic hardcoded to taskType that prevented this working.

There are hardcoded references to SUB_WORKFLOW in the following places methods:

1. `WorkflowExecutorOps.executeSubworkflowTaskAndSyncData` called from `updateParentWorkflowTask`

```
@VisibleForTesting
void updateParentWorkflowTask(WorkflowModel subWorkflow) {
TaskModel subWorkflowTask =
executionDAOFacade.getTaskModel(subWorkflow.getParentWorkflowTaskId());
executeSubworkflowTaskAndSyncData(subWorkflow, subWorkflowTask);
executionDAOFacade.updateTask(subWorkflowTask);
}

private void executeSubworkflowTaskAndSyncData(
WorkflowModel subWorkflow, TaskModel subWorkflowTask) {
WorkflowSystemTask subWorkflowSystemTask =
systemTaskRegistry.get(TaskType.TASK_TYPE_SUB_WORKFLOW);
subWorkflowSystemTask.execute(subWorkflow, subWorkflowTask, this);
}

```

2. `WorkflowExecutorOps.findChangedSubWorkflowTask`
- note the initial filtering here might be a bug assuming DYNAMIC_TASK could also run a SubWorkflow task

```
if (workflowDef.containsType(TaskType.TASK_TYPE_SUB_WORKFLOW)
|| workflow.getWorkflowDefinition()
.containsType(TaskType.TASK_TYPE_FORK_JOIN_DYNAMIC)) {
return workflow.getTasks().stream()
.filter(
t ->
t.getTaskType().equals(TaskType.TASK_TYPE_SUB_WORKFLOW)
&& t.isSubworkflowChanged()
&& !t.isRetried())
.findFirst();
}
```

3. `WorkflowExecutorOps.rerunWF` (line 1669 & 1772)

4. `WorkflowExecutorOps.findLastFailedSubWorkflowIfAny` (line 413)

5. `WorkflowRepairService.verifyAndRepairTask` (line 154)

## Describe Preferred Solution

1. Change the `WorkflowExecutorOps.executeSubworkflowTaskAndSyncData` to pass`subWorkflowTask.getTaskType()` to the `systemTaskRegistry`

```
private void executeSubworkflowTaskAndSyncData(
WorkflowModel subWorkflow, TaskModel subWorkflowTask) {
WorkflowSystemTask subWorkflowSystemTask =
systemTaskRegistry.get(subWorkflowTask.getTaskType()); // replace hard coding here
subWorkflowSystemTask.execute(subWorkflow, subWorkflowTask, this);
}
```

2. And the following method to `WorkflowSystemTask` interface and override to return true in `SubWorkflow` class:

```
public boolean isSubWorkflowParent() { return false; }
```

Add additional method to `SystemTaskRegistry`

```
public boolean isSubWorkflowParent(String taskType) {
return get(taskType).isSubWorkflowParent();
}
```

3. Replace logic that explicitly checks for hardcoding with checks on the SystemRegistry

``
systemTaskRegistry.isSubWorkflowParent(t.getTaskType())

```

## Describe Alternatives

I am not aware of other viable options, as the task type still needs to be unique

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.