{"record":{"id":"4d7d80116005c056","repo":"sipeed/picoclaw","slug":"deltachat-email-is-required-next-step-choose-on","errorCode":null,"errorMessage":"deltachat: email is required.\nNext step: choose one of the chatmail servers below and set channel_list.deltachat.settings.email to %q, or use the same @server form with another chatmail relay. Run `picoclaw g` again; PicoClaw will create the account, print the generated full email address, and stop so you can save that address in the config.\nAvailable chatmail servers:\n%s","messagePattern":"deltachat: email is required\\.\nNext step: choose one of the chatmail servers below and set channel_list\\.deltachat\\.settings\\.email to %q, or use the same @server form with another chatmail relay\\. Run `picoclaw g` again; PicoClaw will create the account, print the generated full email address, and stop so you can save that address in the config\\.\nAvailable chatmail servers:\n(.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/channels/deltachat/deltachat.go","lineNumber":163,"sourceCode":"\t*channels.BaseChannel\n\tbc     *config.Channel\n\tconfig *config.DeltaChatSettings\n\n\tserverPath string\n\tdataDir    string\n\n\trpc       *rpcClient\n\taccountID int64\n\tselfAddr  string\n\n\tctx    context.Context\n\tcancel context.CancelFunc\n}\n\nfunc parseDeltaChatEmailSetting(value string) (string, bool, error) {\n\temail := strings.TrimSpace(value)\n\tif email == \"\" {\n\t\treturn \"\", false, fmt.Errorf(\n\t\t\t\"deltachat: email is required.\\nNext step: choose one of the chatmail servers below and set channel_list.deltachat.settings.email to %q, or use the same @server form with another chatmail relay. Run `picoclaw g` again; PicoClaw will create the account, print the generated full email address, and stop so you can save that address in the config.\\nAvailable chatmail servers:\\n%s\",\n\t\t\t\"@\"+defaultChatmailRelays[0].Domain,\n\t\t\tformatChatmailRelayList(),\n\t\t)\n\t}\n\tif !strings.HasPrefix(email, \"@\") {\n\t\treturn email, false, nil\n\t}\n\tdomain := strings.ToLower(strings.TrimSpace(strings.TrimPrefix(email, \"@\")))\n\tif domain == \"\" {\n\t\treturn \"\", false, fmt.Errorf(\"deltachat: email %q is missing a chatmail server. Use %q or one of:\\n%s\",\n\t\t\temail, \"@\"+defaultChatmailRelays[0].Domain, formatChatmailRelayList())\n\t}\n\tif strings.Contains(domain, \"@\") || strings.ContainsAny(domain, \"/\\\\ \\t\\r\\n\") {\n\t\treturn \"\", false, fmt.Errorf(\"deltachat: invalid chatmail server marker %q; use settings.email like %q\",\n\t\t\temail, \"@\"+defaultChatmailRelays[0].Domain)\n\t}\n\treturn domain, true, nil","sourceCodeStart":145,"sourceCodeEnd":181,"githubUrl":"https://github.com/sipeed/picoclaw/blob/49183d7e8daed0dba89ddbb6fcb60089401d9680/pkg/channels/deltachat/deltachat.go#L145-L181","documentation":"The Delta Chat channel was constructed with an empty channel_list.deltachat.settings.email, which parseDeltaChatEmailSetting rejects. The error text embeds the next steps: pick a chatmail server from the built-in relay list, set email to `@server` (PicoClaw then creates the account on next `picoclaw g`) or set a full address. This fires at channel construction time (NewDeltaChatChannel), before anything starts.","triggerScenarios":"NewDeltaChatChannel (or `picoclaw g` / manager init) with config.ChannelDeltaChatSettings.Email unset, whitespace-only, or the deltachat block missing the settings.email key entirely.","commonSituations":"First-time setup where the user enabled the deltachat channel but skipped email; YAML indentation putting email at the wrong level so it never unmarshals; copying a sample config that comments out email; trimming the config down and accidentally removing the key.","solutions":["Set channel_list.deltachat.settings.email to `@<chatmail-server>` (e.g. @nine.testrun.org) and run `picoclaw g`; PicoClaw creates the account, prints the full generated address, and stops so you can save it back into the config.","Alternatively set email to a full existing address if you already have a chatmail/Delta Chat account.","Check YAML indentation: settings must be a map under the deltachat channel with email as a key, not a sibling string.","Re-run the generator and follow the printed relay list in the error message."],"exampleFix":"# before\nchannel_list:\n  deltachat:\n    settings: {}\n\n# after\nchannel_list:\n  deltachat:\n    settings:\n      email: \"@nine.testrun.org\"","handlingStrategy":"validation","validationCode":"// Mirror the library check before constructing the channel\nif strings.TrimSpace(cfg.Email) == \"\" {\n    return fmt.Errorf(\"deltachat settings.email is empty; set it to '@server' or a full address\")\n}","typeGuard":"func hasDeltaChatEmail(cfg *config.DeltaChatSettings) bool {\n    return cfg != nil && strings.TrimSpace(cfg.Email) != \"\"\n}","tryCatchPattern":"ch, err := deltachat.NewDeltaChatChannel(bc, cfg, bus)\nif err != nil {\n    if strings.Contains(err.Error(), \"deltachat: email is required\") {\n        // follow the printed relay list, set settings.email, re-run picoclaw g\n    }\n    return err\n}","preventionTips":["Treat the deltachat block as requiring settings.email in config templates.","Validate config at load time, not at channel construction.","Use the @server form for first-time account creation; persist the generated full address back into the config."],"tags":["deltachat","go","config","chatmail","validation"],"backgroundTag":null,"analyzedSha":"49183d7e8daed0dba89ddbb6fcb60089401d9680","analyzedAt":"2026-08-15T21:55:41.315Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}