{"record":{"id":"ffffed819aea7903","repo":"crowdsecurity/crowdsec","slug":"stream-arn-is-mandatory-when-use-enhanced-fanout-i","errorCode":null,"errorMessage":"stream_arn is mandatory when use_enhanced_fanout is true","messagePattern":"stream_arn is mandatory when use_enhanced_fanout is true","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/acquisition/modules/kinesis/config.go","lineNumber":81,"sourceCode":"\nfunc (s *Source) UnmarshalConfig(yamlConfig []byte) error {\n\tcfg, err := ConfigurationFromYAML(yamlConfig)\n\tif err != nil {\n\t\treturn err\n\t}\n\n\ts.Config = cfg\n\n\treturn nil\n}\n\nfunc (c *Configuration) Validate() error {\n\tif c.StreamName == \"\" && !c.UseEnhancedFanOut {\n\t\treturn errors.New(\"stream_name is mandatory when use_enhanced_fanout is false\")\n\t}\n\n\tif c.StreamARN == \"\" && c.UseEnhancedFanOut {\n\t\treturn errors.New(\"stream_arn is mandatory when use_enhanced_fanout is true\")\n\t}\n\n\tif c.ConsumerName == \"\" && c.UseEnhancedFanOut {\n\t\treturn errors.New(\"consumer_name is mandatory when use_enhanced_fanout is true\")\n\t}\n\n\tif c.StreamARN != \"\" && c.StreamName != \"\" {\n\t\treturn errors.New(\"stream_arn and stream_name are mutually exclusive\")\n\t}\n\n\treturn nil\n}\n\nfunc (s *Source) Configure(ctx context.Context, yamlConfig []byte, logger *log.Entry, metricsLevel metrics.AcquisitionMetricsLevel) error {\n\ts.logger = logger\n\ts.metricsLevel = metricsLevel\n\n\terr := s.UnmarshalConfig(yamlConfig)","sourceCodeStart":63,"sourceCodeEnd":99,"githubUrl":"https://github.com/crowdsecurity/crowdsec/blob/909b5157986a2b2c2163300fdaef5ed01289f7d2/pkg/acquisition/modules/kinesis/config.go#L63-L99","documentation":"In enhanced fan-out mode the Kinesis source registers a dedicated consumer identified by the stream ARN, so StreamARN must be set. Configuration.Validate() enforces that any config with use_enhanced_fanout: true also provides stream_arn. Stream name alone is not accepted because the fan-out subscribe API requires the full ARN.","triggerScenarios":"Calling Validate() on a kinesis Configuration where UseEnhancedFanOut is true and StreamARN is empty — e.g. a config with use_enhanced_fanout: true and only stream_name set.","commonSituations":"Users switch on enhanced fan-out but keep using stream_name (the shared-consumer style config), or copy a fan-out config template and leave stream_arn blank/placeholder.","solutions":["Set stream_arn to the full stream ARN (arn:aws:kinesis:<region>:<account>:stream/<name>) in the acquisition config.","Keep use_enhanced_fanout: true only if you have registered a consumer; otherwise drop the flag and use stream_name.","Also set consumer_name, which is required in the same mode."],"exampleFix":"// before (yaml)\nsource: kinesis\nuse_enhanced_fanout: true\nstream_name: logs\nconsumer_name: crowdsec\n\n// after (yaml)\nsource: kinesis\nuse_enhanced_fanout: true\nstream_arn: arn:aws:kinesis:us-east-1:123456789012:stream/logs\nconsumer_name: crowdsec","handlingStrategy":"validation","validationCode":"if cfg.UseEnhancedFanOut && cfg.StreamARN == \"\" {\n    return fmt.Errorf(\"kinesis: stream_arn is required when use_enhanced_fanout is true\")\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Copy the full ARN from `aws kinesis describe-stream-summary --stream-name <name>` rather than typing it.","Treat stream_arn as the canonical identifier whenever fan-out is enabled.","Validate the config in CI before rollout."],"tags":["aws","kinesis","config-validation","enhanced-fanout"],"backgroundTag":"missing-required-config-field","analyzedSha":"909b5157986a2b2c2163300fdaef5ed01289f7d2","analyzedAt":"2026-09-06T12:27:26.012Z","contentChangedAt":"2026-09-06T12:27:26.012Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}