temporalio/temporal · critical
<dynamic archival cluster state err>
Error message
<dynamic archival cluster state err>
What it means
NewArchivalConfig in common/archiver/archival_metadata.go parses the static cluster archival state string via getClusterArchivalState and panics on error. The message "<dynamic archival cluster state err>" wraps whatever the parser returned (e.g. an invalid state string). Because this is a constructor run at service startup, a bad value is treated as a fatal configuration error rather than a returned error.
Source
Thrown at common/archiver/archival_metadata.go:112
func (metadata *archivalMetadata) GetHistoryConfig() ArchivalConfig {
return metadata.historyConfig
}
func (metadata *archivalMetadata) GetVisibilityConfig() ArchivalConfig {
return metadata.visibilityConfig
}
// NewArchivalConfig constructs a new valid ArchivalConfig
func NewArchivalConfig(
staticClusterStateStr string,
dynamicClusterState dynamicconfig.StringPropertyFn,
enableRead dynamicconfig.BoolPropertyFn,
namespaceDefaultStateStr string,
namespaceDefaultURI string,
) ArchivalConfig {
staticClusterState, err := getClusterArchivalState(staticClusterStateStr)
if err != nil {
panic(err)
}
namespaceDefaultState, err := getNamespaceArchivalState(namespaceDefaultStateStr)
if err != nil {
panic(err)
}
return &archivalConfig{
staticClusterState: staticClusterState,
dynamicClusterState: dynamicClusterState,
enableRead: enableRead,
namespaceDefaultState: namespaceDefaultState,
namespaceDefaultURI: namespaceDefaultURI,
}
}
// NewDisabledArchvialConfig returns an ArchivalConfig where archival is disabled for both the cluster and the namespace
func NewDisabledArchvialConfig() ArchivalConfig {
return &archivalConfig{View on GitHub (pinned to bde624efd1)
Solutions
- Fix the archival state string in config to a valid value (enabled/disabled/paused)
- Log and print the wrapped err from getClusterArchivalState — the panic message carries the underlying parse error
- Validate config at deploy time (config schema check) before the service starts
- If you control the call site in tests, pass only values produced by the archiver package's own constants
Example fix
// before (config.yaml) archival: clusterState: "enable" // after (config.yaml) archival: clusterState: "enabled"
Defensive patterns
Strategy: validation
Validate before calling
staticState := cfg.ArchivalClusterState
if staticState != "" && staticState != "enabled" && staticState != "disabled" && staticState != "paused" {
return fmt.Errorf("invalid cluster archival state: %q", staticState)
} Type guard
func validArchivalState(s string) bool {
switch s {
case "", "enabled", "disabled", "paused":
return true
}
return false
} Prevention
- Use the archiver package's exported state constants in config generation
- Add config schema validation for archival keys before service startup
- Pin accepted values in config templates and lint them in CI
When it happens
Trigger: Calling NewArchivalConfig with a staticClusterStateStr that getClusterArchivalState cannot parse (not one of the valid archival state values: "enabled", "disabled", "paused", or the empty/unset meaning dynamic default).
Common situations: Typo in the cluster archival state in the service config YAML (e.g. "enable" instead of "enabled"); environment-specific config overriding the state with an unsupported string; upgrading Temporal where the accepted state vocabulary changed while old config lingers.
Related errors
- <dynamic namespace archival state err>
- Empty cluster information
- Master cluster name is empty
- Unexpected frontend service name
- missing current cluster metadata under clusterMetadata.Clust
AI-assisted analysis of temporalio/temporal@bde624efd1 (2026-09-01).
Data as JSON: /api/errors/83ef66cab9277b68.
Report an issue: GitHub.