{"record":{"id":"6c7b080dc24c2629","repo":"crowdsecurity/crowdsec","slug":"invalid-dsn-s-for-journalctl-source-must-start-w","errorCode":null,"errorMessage":"invalid DSN %s for journalctl source, must start with journalctl://","messagePattern":"invalid DSN (.+?) for journalctl source, must start with journalctl://","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/acquisition/modules/journalctl/config.go","lineNumber":86,"sourceCode":"\tif err := s.UnmarshalConfig(yamlConfig); err != nil {\n\t\treturn err\n\t}\n\n\ts.setLogger(logger, 0, s.src)\n\ts.metricsLevel = metricsLevel\n\treturn nil\n}\n\nfunc (s *Source) ConfigureByDSN(_ context.Context, dsn string, labels map[string]string, logger *log.Entry, uuid string) error {\n\tvar (\n\t\tfilters  []string\n\t\tsince    string\n\t\tlogLevel log.Level\n\t)\n\n\t// format for the DSN is : journalctl://filters=FILTER1&filters=FILTER2\n\tif !strings.HasPrefix(dsn, \"journalctl://\") {\n\t\treturn fmt.Errorf(\"invalid DSN %s for journalctl source, must start with journalctl://\", dsn)\n\t}\n\n\tqs := strings.TrimPrefix(dsn, \"journalctl://\")\n\tif qs == \"\" {\n\t\treturn errors.New(\"empty journalctl:// DSN\")\n\t}\n\n\tparams, err := url.ParseQuery(qs)\n\tif err != nil {\n\t\treturn fmt.Errorf(\"could not parse journalctl DSN: %w\", err)\n\t}\n\n\tfor key, value := range params {\n\t\tswitch key {\n\t\tcase \"filters\":\n\t\t\tfilters = append(filters, value...)\n\t\tcase \"log_level\":\n\t\t\tif len(value) != 1 {","sourceCodeStart":68,"sourceCodeEnd":104,"githubUrl":"https://github.com/crowdsecurity/crowdsec/blob/909b5157986a2b2c2163300fdaef5ed01289f7d2/pkg/acquisition/modules/journalctl/config.go#L68-L104","documentation":"ConfigureByDSN expects a data-source string that begins with the 'journalctl://' scheme. Any DSN passed to the journalctl source with a different or missing prefix is rejected with this error. It is a fast guard before query-string parsing is attempted.","triggerScenarios":"Calling Source.ConfigureByDSN with a DSN like 'journalctl:filters=...' (single slash), 'file://...', or a bare filter expression without the scheme prefix.","commonSituations":"Hand-written acquis entries missing the '://'; copy-pasting a DSN from another source type (file://, syslog://); shell quoting stripping a slash.","solutions":["Prefix the DSN exactly with 'journalctl://', e.g. journalctl://filters=_SYSTEMD_UNIT=sshd.service.","Verify the source type in acquis.yaml is journalctl so the DSN is routed to this ConfigureByDSN.","Check for shell/CLI escaping that may have eaten characters from the DSN string."],"exampleFix":"// before\ns.ConfigureByDSN(\"journalctl:filters=_SYSTEMD_UNIT=sshd.service\")\n// after\ns.ConfigureByDSN(\"journalctl://filters=_SYSTEMD_UNIT=sshd.service\")","handlingStrategy":"validation","validationCode":"if !strings.HasPrefix(dsn, \"journalctl://\") || len(dsn) <= len(\"journalctl://\") {\n    return errors.New(\"DSN must be journalctl://<querystring> with a non-empty query\")\n}","typeGuard":null,"tryCatchPattern":"if err := src.ConfigureByDSN(dsn); err != nil {\n    if strings.Contains(err.Error(), \"invalid DSN\") {\n        // fix scheme prefix and retry\n    }\n}","preventionTips":["Always build DSNs with the full journalctl:// prefix including both slashes","Keep DSN strings in quoted YAML values to avoid shell-style mangling","Copy DSN examples verbatim from the docs rather than retyping"],"tags":["go","dsn","configuration","journalctl"],"backgroundTag":"invalid-url-format","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"}