{"record":{"id":"0f2471c060341219","repo":"temporalio/temporal","slug":"invalid-config-type-t-for-nexusoperation-callbac","errorCode":null,"errorMessage":"invalid config type: %T for nexusoperation.callback.endpoint.template, expected string","messagePattern":"invalid config type: %T for nexusoperation\\.callback\\.endpoint\\.template, expected string","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"chasm/lib/nexusoperation/config.go","lineNumber":166,"sourceCode":"\t\theaders.PrincipalNameHeaderName,\n\t},\n\t`Case insensitive list of disallowed header keys for Nexus Operations. ScheduleNexusOperation commands with a\n\"nexus_header\" field that contains any of these disallowed keys will be rejected.`,\n)\n\nvar MaxOperationScheduleToCloseTimeout = dynamicconfig.NewNamespaceDurationSetting(\n\t\"nexusoperation.limit.scheduleToCloseTimeout\",\n\t0,\n\t`Maximum allowed duration of a Nexus Operation. ScheduleOperation commands that specify no schedule-to-close timeout\nor a longer timeout than permitted will have their schedule-to-close timeout capped to this value. 0 implies no limit.`,\n)\n\nvar CallbackURLTemplate = dynamicconfig.NewGlobalTypedSettingWithConverter(\n\t\"nexusoperation.callback.endpoint.template\",\n\tfunc(in any) (*template.Template, error) {\n\t\ts, ok := in.(string)\n\t\tif !ok {\n\t\t\treturn nil, fmt.Errorf(\"invalid config type: %T for nexusoperation.callback.endpoint.template, expected string\", in)\n\t\t}\n\t\tif s == \"unset\" {\n\t\t\treturn nil, nil\n\t\t}\n\t\treturn template.New(\"NexusCallbackURL\").Parse(s)\n\t},\n\tnil,\n\t`Controls the template for generating callback URLs included in Nexus operation requests, which are used to deliver\nasynchronous completion for external endpoint targets. The template can be used to interpolate the {{.NamepaceName}}\nand {{.NamespaceID}} parameters to construct a publicly accessible URL.\nMust be set to call external endpoints.`,\n)\n\ntype RetryPolicyConfig struct {\n\tInitialInterval time.Duration\n\tMaxInterval     time.Duration\n}\n","sourceCodeStart":148,"sourceCodeEnd":184,"githubUrl":"https://github.com/temporalio/temporal/blob/bde624efd13fbd3843654058db6d9c716166318b/chasm/lib/nexusoperation/config.go#L148-L184","documentation":"The dynamicconfig global setting 'nexusoperation.callback.endpoint.template' is declared with a typed-converter that only accepts a string, which is parsed as a Go text/template used to build Nexus callback URLs. If the configured value is not a string, the converter fails with this error, breaking any code path that reads the setting.","triggerScenarios":"Setting nexusoperation.callback.endpoint.template in dynamic config (file, DB, or runtime) to a non-string value — e.g. a JSON/YAML number, boolean, object, or map — then any code reading the setting (e.g. during Nexus operation start) invokes the converter and gets this error.","commonSituations":"Config file has the value unquoted (YAML parses it as a non-string), or a runtime-config UI stores a non-string type. Also happens when someone configures the raw template in a structured config format that coerces types.","solutions":["Quote the value in dynamic config so it is a Go string, e.g. nexusoperation.callback.endpoint.template: \"http://localhost:7243/namespaces/{{.Namespace}}/nexus/callbacks\"","If dynamic config is a YAML/JSON file, ensure the entry is a scalar string, not a number/bool/nested object","Validate the template parses correctly (template.New(...).Parse) before deploying the config"],"exampleFix":"# before\nnexusoperation.callback.endpoint.template: {\"url\": \"http://host/cb\"}\n# after\nnexusoperation.callback.endpoint.template: \"http://host/cb\"","handlingStrategy":"validation","validationCode":"v, ok := cfg.Get(\"nexusoperation.callback.endpoint.template\")\nif _, ok := v.(string); !ok {\n    return fmt.Errorf(\"nexusoperation.callback.endpoint.template must be a string, got %T\", v)\n}\nif _, err := template.New(\"NexusCallbackURL\").Parse(v.(string)); err != nil {\n    return fmt.Errorf(\"template parse failed: %w\", err)\n}","typeGuard":"func isStringSetting(v any) (string, bool) {\n    s, ok := v.(string)\n    return s, ok\n}","tryCatchPattern":null,"preventionTips":["Quote template values in YAML/JSON dynamic config files","Validate config at deploy time by loading the setting with the same converter","Add a startup smoke test that reads the setting and parses the template","Avoid runtime config UIs that coerce types for string settings"],"tags":["dynamicconfig","nexus","configuration","template"],"backgroundTag":"invalid-config-type","analyzedSha":"bde624efd13fbd3843654058db6d9c716166318b","analyzedAt":"2026-09-01T07:18:39.080Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}