{"record":{"id":"1a153f1230c7cb09","repo":"rust-lang/cargo","slug":"lints-tool-name-is-not-valid-lint-name-try","errorCode":null,"errorMessage":"`lints.{tool}.{name}` is not valid lint name; try `lints.{prefix}.{suffix}`","messagePattern":"`lints\\.(.+?)\\.(.+?)` is not valid lint name; try `lints\\.(.+?)\\.(.+?)`","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/workspace/parser/mod.rs","lineNumber":2737,"sourceCode":"        for (name, config) in lints {\n            let normalized = name.replace('-', \"_\");\n            if name.contains('-') {\n                warnings.push(format!(\n                    \"`lints.{tool}.{name}` is deprecated in favor of \\\n                     `lints.{tool}.{normalized}` and will not work in a \\\n                     future edition\"\n                ));\n            }\n            if let Some(existing) = seen_normalized.get(&normalized) {\n                warnings.push(format!(\n                    \"duplicate lint `{existing}` in `[lints.{tool}]`, \\\n                     conflicts with `{name}` and will not work in a future edition\"\n                ));\n            }\n            seen_normalized.insert(normalized.clone(), name.to_string());\n            if let Some((prefix, suffix)) = name.split_once(\"::\") {\n                if tool == prefix {\n                    anyhow::bail!(\n                        \"`lints.{tool}.{name}` is not valid lint name; try `lints.{prefix}.{suffix}`\"\n                    )\n                } else if tool == \"rust\" && supported.contains(&prefix) {\n                    anyhow::bail!(\n                        \"`lints.{tool}.{name}` is not valid lint name; try `lints.{prefix}.{suffix}`\"\n                    )\n                } else {\n                    anyhow::bail!(\"`lints.{tool}.{name}` is not a valid lint name\")\n                }\n            } else if let Some(config) = config.config() {\n                for config_name in config.keys() {\n                    // manually report unused manifest key warning since we collect all the \"extra\"\n                    // keys and values inside the config table\n                    let expected = EXPECTED_LINT_CONFIG.contains(&(tool, name, config_name));\n                    if !expected {\n                        let message =\n                            format!(\"unused manifest key: `lints.{tool}.{name}.{config_name}`\");\n                        warnings.push(message);","sourceCodeStart":2719,"sourceCodeEnd":2755,"githubUrl":"https://github.com/rust-lang/cargo/blob/98a09e7e7d62850f14e5b6132101fc1edd19a16f/src/workspace/parser/mod.rs#L2719-L2755","documentation":"Thrown during [lints] validation when a lint name contains '::' and the segment before '::' equals the tool name. For example [lints.rust] with a key 'rust::dead_code' repeats the tool namespace. The correct form drops the redundant prefix: lints.rust.dead_code. The message suggests lints.{prefix}.{suffix} but here prefix equals tool, so the fix is to use just lints.{tool}.{suffix}.","triggerScenarios":"Writing [lints.rust] section with a key like 'rust::dead_code'. The split_once(\"::\") yields (prefix='rust', suffix='dead_code'), and the branch tool == prefix fires.","commonSituations":"A developer copies a lint name from a compiler message that includes the tool prefix (e.g. 'rust dead_code') and writes it verbatim. Confusion about whether the [lints] table key should include the tool namespace.","solutions":["Remove the redundant tool prefix from the lint key: use 'dead_code' not 'rust::dead_code' under [lints.rust].","Consult the lint's documentation for its bare name within the tool's namespace."],"exampleFix":"# before\n[lints.rust]\n\"rust::dead_code\" = \"warn\"\n\n# after\n[lints.rust]\ndead_code = \"warn\"","handlingStrategy":"validation","validationCode":"fn lint_name_no_redundant_tool_prefix(tool: &str, name: &str) -> Result<(), String> {\n    if let Some((prefix, _)) = name.split_once(\"::\") {\n        if prefix == tool {\n            return Err(format!(\"remove redundant `{tool}::` from lint `{name}`\"));\n        }\n    }\n    Ok(())\n}","typeGuard":"fn is_bare_lint_name(name: &str) -> bool { !name.contains(\"::\") }","tryCatchPattern":null,"preventionTips":["Use bare lint names (e.g. dead_code) inside the matching [lints.<tool>] table.","Never repeat the tool namespace in the lint key.","Cross-check lint names against the tool's documentation."],"tags":["cargo","lints","manifest","naming","parser"],"backgroundTag":null,"analyzedSha":"98a09e7e7d62850f14e5b6132101fc1edd19a16f","analyzedAt":"2026-08-11T17:42:36.556Z","contentChangedAt":"2026-08-11T17:42:36.556Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}