{"record":{"id":"694bcc73d5e863d8","repo":"flowable/flowable-engine","slug":"no-smtp-host-is-configured-for-the-mail-server-for","errorCode":null,"errorMessage":"no SMTP host is configured for the mail server for tenant {tenantId}","messagePattern":"no SMTP host is configured for the mail server for tenant (.+?)","errorType":"exception","errorClass":"FlowableException","httpStatus":null,"severity":"error","filePath":"modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/CmmnEngineConfiguration.java","lineNumber":982,"sourceCode":"\n        Collection<String> tenantIds = new HashSet<>(mailSessionsJndi.keySet());\n        tenantIds.addAll(mailServers.keySet());\n\n        if (!tenantIds.isEmpty()) {\n            Map<String, FlowableMailClient> mailClients = defaultMailClientProvider.getMailClients();\n            MailServerInfo defaultMailServer = getDefaultMailServer();\n            for (String tenantId : tenantIds) {\n                if (mailClients.containsKey(tenantId)) {\n                    continue;\n                }\n                String sessionJndi = mailSessionsJndi.get(tenantId);\n                MailServerInfo tenantMailServer = mailServers.get(tenantId);\n                if (sessionJndi != null) {\n                    mailClients.put(tenantId, FlowableMailClientCreator.createSessionClient(sessionJndi, tenantMailServer, defaultMailServer));\n                } else if (tenantMailServer != null) {\n                    String host = tenantMailServer.getMailServerHost();\n                    if (host == null) {\n                        throw new FlowableException(\"no SMTP host is configured for the mail server for tenant \" + tenantId);\n                    }\n                    mailClients.put(tenantId, FlowableMailClientCreator.createHostClient(host, tenantMailServer, defaultMailServer));\n                }\n            }\n        }\n    }\n    public void initCmmnEngineAgendaFactory() {\n        if (cmmnEngineAgendaFactory == null) {\n            cmmnEngineAgendaFactory = new DefaultCmmnEngineAgendaFactory();\n        }\n    }\n\n    @Override\n    public void initCommandInvoker() {\n        if (this.commandInvoker == null) {\n            this.commandInvoker = new CmmnCommandInvoker(agendaOperationRunner, agendaOperationExecutionListeners);\n        }\n    }","sourceCodeStart":964,"sourceCodeEnd":1000,"githubUrl":"https://github.com/flowable/flowable-engine/blob/d6d39ce1c69ff244f2d9dc6af756a9b95e865586/modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/CmmnEngineConfiguration.java#L964-L1000","documentation":"Thrown during CmmnEngineConfiguration mail client initialization when a tenant-specific mail server entry exists but its SMTP host is null. Per-tenant mail sessions are built at startup and each configured tenant must have a resolvable host (unless a JNDI session is used).","triggerScenarios":"mailServers map contains an entry for tenantId with MailServerInfo.mailServerHost == null and no mailSessionsJndi entry for that tenant — e.g. setMailServers(Map) called with a partially filled MailServerInfo.","commonSituations":"Multi-tenant setup where one tenant's SMTP host property is missing or empty; programmatic setMailServers with a default-constructed MailServerInfo; tenant config loaded from DB/table with an empty host column.","solutions":["Set the host for the tenant's MailServerInfo before engine start (setMailServerHost on the info or in the tenant config source)","Configure a JNDI mail session for that tenant via mailSessionsJndi so host lookup is bypassed","Remove the empty tenant entry if that tenant should fall back to the default mail server","Validate tenant mail config at application startup (fail fast before CmmnEngineConfiguration.init)"],"exampleFix":"// before\nMailServerInfo info = new MailServerInfo();\ninfo.setMailServerUser(\"noreply\");\nmailServers.put(\"tenantA\", info);\n\n// after\nMailServerInfo info = new MailServerInfo();\ninfo.setMailServerHost(\"smtp.tenantA.example.com\");\ninfo.setMailServerPort(587);\nmailServers.put(\"tenantA\", info);","handlingStrategy":"validation","validationCode":"for (Map.Entry<String, MailServerInfo> e : tenantMailServers.entrySet()) {\n    if (e.getValue() == null || e.getValue().getMailServerHost() == null) {\n        throw new IllegalStateException(\"Missing SMTP host for tenant \" + e.getKey());\n    }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Validate every tenant's MailServerInfo has host+port before engine init","Source tenant mail config from one validated store with NOT NULL constraints","Use JNDI sessions for tenants without direct SMTP access","Cover multi-tenant startup in integration tests"],"tags":["cmmn","mail","smtp","multi-tenancy","configuration"],"backgroundTag":"missing-required-config-field","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"}