{"record":{"id":"b67f2b676a9c4096","repo":"conductor-oss/conductor","slug":"s-b67f2b","errorCode":null,"errorMessage":"%s","messagePattern":"%s","errorType":"exception","errorClass":"TerminateWorkflowException","httpStatus":null,"severity":"error","filePath":"core/src/main/java/com/netflix/conductor/core/execution/DeciderService.java","lineNumber":1041,"sourceCode":"    private int applyMaxRetryDelayCap(int delaySeconds, TaskDef taskDef) {\n        int cap = taskDef.getMaxRetryDelaySeconds();\n        return (cap > 0 && delaySeconds > cap) ? cap : delaySeconds;\n    }\n\n    private boolean isTaskSkipped(WorkflowTask taskToSchedule, WorkflowModel workflow) {\n        try {\n            boolean isTaskSkipped = false;\n            if (taskToSchedule != null) {\n                TaskModel t = workflow.getTaskByRefName(taskToSchedule.getTaskReferenceName());\n                if (t == null) {\n                    isTaskSkipped = false;\n                } else if (t.getStatus().equals(SKIPPED)) {\n                    isTaskSkipped = true;\n                }\n            }\n            return isTaskSkipped;\n        } catch (Exception e) {\n            throw new TerminateWorkflowException(e.getMessage());\n        }\n    }\n\n    private boolean isAyncCompleteSystemTask(TaskModel task) {\n        return systemTaskRegistry.isSystemTask(task.getTaskType())\n                && systemTaskRegistry.get(task.getTaskType()).isAsyncComplete(task);\n    }\n\n    public static class DeciderOutcome {\n\n        List<TaskModel> tasksToBeScheduled = new LinkedList<>();\n        List<TaskModel> tasksToBeUpdated = new LinkedList<>();\n        boolean isComplete;\n        TaskModel terminateTask;\n\n        private DeciderOutcome() {}\n    }\n}","sourceCodeStart":1023,"sourceCodeEnd":1059,"githubUrl":"https://github.com/conductor-oss/conductor/blob/cf7c3e4a8adfb158be778ab1ec525323c363cd3a/core/src/main/java/com/netflix/conductor/core/execution/DeciderService.java#L1023-L1059","documentation":"isTaskSkipped wraps its entire body in try/catch(Exception) and rethrows any exception's message as a TerminateWorkflowException with no cause and no structured status. The %s is just the inner exception's getMessage(). This obscures the real error type and makes the failure look like a workflow-termination when it may be a data-resolution bug (e.g. getTaskByRefName failing).","triggerScenarios":"workflow.getTaskByRefName(refName) throws inside isTaskSkipped during startWorkflow's skip-loop — e.g. duplicate reference names, corrupt task data, or a null WorkflowTask reference name.","commonSituations":"Two WorkflowTasks share the same taskReferenceName; a workflow model with corrupted task list; a null taskReferenceName on the task to schedule.","solutions":["Search server logs for the full stack trace of the wrapped exception (the message alone is insufficient).","Validate that all WorkflowTask.taskReferenceName values in the definition are unique and non-null.","Reproduce with the same workflow definition and inspect getTaskByRefName behavior.","Consider improving the catch to preserve the cause — file an issue, since the current swallow loses diagnosability."],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"// Validate unique, non-null taskReferenceNames at definition time.\nSet<String> refs = new HashSet<>();\nfor (WorkflowTask t : def.getTasks()) {\n    if (t.getTaskReferenceName() == null || !refs.add(t.getTaskReferenceName())) {\n        throw new IllegalArgumentException(\"Duplicate/null taskReferenceName in \" + def.getName());\n    }\n}","typeGuard":null,"tryCatchPattern":"try {\n    deciderService.decide(workflow);\n} catch (TerminateWorkflowException e) {\n    // message is opaque; pull full stack trace from server logs\n    LOGGER.error(\"isTaskSkipped wrapped exception: {}\", e.getMessage());\n}","preventionTips":["Ensure all WorkflowTask.taskReferenceName values are unique and non-null.","Pull the full server stack trace — the wrapped message alone is insufficient.","Consider preserving the cause (file an issue) to improve diagnosability."],"tags":["conductor","workflow","decider","opaque-error","task-reference","terminate-workflow"],"backgroundTag":null,"analyzedSha":"cf7c3e4a8adfb158be778ab1ec525323c363cd3a","analyzedAt":"2026-08-14T03:33:19.897Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}