{"record":{"id":"cb1722caef863516","repo":"flowable/flowable-engine","slug":"name-expression-does-not-resolve-to-a-string","errorCode":null,"errorMessage":"name expression does not resolve to a string: ","messagePattern":"name expression does not resolve to a string: ","errorType":"exception","errorClass":"FlowableIllegalArgumentException","httpStatus":null,"severity":"error","filePath":"modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/impl/behavior/impl/HumanTaskActivityBehavior.java","lineNumber":197,"sourceCode":"\n    protected void handleTaskName(PlanItemInstanceEntity planItemInstanceEntity, ExpressionManager expressionManager, \n                    TaskEntity taskEntity, CreateHumanTaskBeforeContext beforeContext, MigrationContext migrationContext) {\n        \n        String nameStringValue = null;\n        if (migrationContext != null && migrationContext.getName() != null) {\n            nameStringValue = migrationContext.getName();\n            \n        } else if (StringUtils.isNotEmpty(beforeContext.getName())) {\n            nameStringValue = beforeContext.getName();\n        }\n        \n        if (StringUtils.isNotEmpty(nameStringValue)) {\n            Object name = expressionManager.createExpression(nameStringValue).getValue(planItemInstanceEntity);\n            if (name != null) {\n                if (name instanceof String) {\n                    taskEntity.setName((String) name);\n                } else {\n                    throw new FlowableIllegalArgumentException(\"name expression does not resolve to a string: \" + beforeContext.getName());\n                }\n            }\n        }\n    }\n\n    protected void handleTaskDescription(PlanItemInstanceEntity planItemInstanceEntity, ExpressionManager expressionManager, \n                    TaskEntity taskEntity, CreateHumanTaskBeforeContext beforeContext) {\n        \n        if (StringUtils.isNotEmpty(beforeContext.getDescription())) {\n            Object description = expressionManager.createExpression(beforeContext.getDescription()).getValue(planItemInstanceEntity);\n            if (description != null) {\n                if (description instanceof String) {\n                    taskEntity.setDescription((String) description);\n                } else {\n                    throw new FlowableIllegalArgumentException(\"documentation expression does not resolve to a string: \" + beforeContext.getDescription());\n                }\n            }\n        }","sourceCodeStart":179,"sourceCodeEnd":215,"githubUrl":"https://github.com/flowable/flowable-engine/blob/d6d39ce1c69ff244f2d9dc6af756a9b95e865586/modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/impl/behavior/impl/HumanTaskActivityBehavior.java#L179-L215","documentation":"HumanTaskActivityBehavior resolves the task name from a name expression when configured. If the expression evaluates to a non-String, non-null object, the engine cannot safely assign it to the task name and throws FlowableIllegalArgumentException. Null values are tolerated (name stays unset), but wrong types are not.","triggerScenarios":"handleTaskName evaluates the name expression and the resulting value is neither null nor a String — e.g. an Integer, Boolean, Map, or JSON object.","commonSituations":"Case variable holding a number used directly as task name (e.g. ${caseCount}); data object fields returning parsed JSON objects; expressions returning collections; changes in variable type after a model update.","solutions":["Convert the value to a String inside the expression, e.g. ${someNumber.toString()} or ${'Task for ' + customerName}.","Store a String-typed variable for the task name and reference that instead.","If the value is a complex object, reference a specific string field, e.g. ${customer.name} instead of ${customer}.","Update the case model/form so the variable is declared and set as a string."],"exampleFix":"// before: numeric variable used directly -> Integer\n<humanTask nameExpression=\"${orderNumber}\"/>\n// after\n<humanTask nameExpression=\"${orderNumber.toString()}\"/> // or store a String variable","handlingStrategy":"type-guard","validationCode":"Object nameVal = caseVariables.get(\"taskNameVar\");\nif (nameVal != null && !(nameVal instanceof String)) {\n    throw new IllegalArgumentException(\"taskNameVar must be a String, got: \" + nameVal.getClass());\n}","typeGuard":"if (nameValue instanceof String s) {\n    taskEntity.setName(s); // safe assignment\n}","tryCatchPattern":"try {\n    caseRuntimeService.triggerPlanItemInstance(planItemId);\n} catch (FlowableIllegalArgumentException e) {\n    if (e.getMessage().startsWith(\"name expression does not resolve to a string\")) {\n        log.error(\"Task name expression returned non-string for case {}\", caseInstanceId);\n    }\n    throw e;\n}","preventionTips":["Declare task-name variables as strings in forms/data objects","Use .toString() or string concatenation inside expressions for non-string values","Reference specific string fields of complex objects, not the object itself"],"tags":["cmmn","human-task","expression","type-mismatch"],"backgroundTag":"type-mismatch","analyzedSha":"d6d39ce1c69ff244f2d9dc6af756a9b95e865586","analyzedAt":"2026-09-11T06:41:19.413Z","contentChangedAt":"2026-09-11T06:41:19.413Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}