Remove repeated and erroneous scoped settings headers in docs (#8670)

Closes https://github.com/astral-sh/ruff/issues/8505.
This commit is contained in:
Charlie Marsh 2023-11-13 21:44:30 -08:00 committed by GitHub
parent bf2cc3f520
commit f7d249ae06
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 75 additions and 22 deletions

View file

@ -129,12 +129,12 @@ fn emit_field(output: &mut String, name: &str, field: &OptionField, parent_set:
output.push_str("**Example usage**:\n\n");
output.push_str(&format_tab(
"pyproject.toml",
&format_header(parent_set, ConfigurationFile::PyprojectToml),
&format_header(field.scope, parent_set, ConfigurationFile::PyprojectToml),
field.example,
));
output.push_str(&format_tab(
"ruff.toml",
&format_header(parent_set, ConfigurationFile::RuffToml),
&format_header(field.scope, parent_set, ConfigurationFile::RuffToml),
field.example,
));
output.push('\n');
@ -149,23 +149,53 @@ fn format_tab(tab_name: &str, header: &str, content: &str) -> String {
)
}
fn format_header(parent_set: &Set, configuration: ConfigurationFile) -> String {
let fmt = if let Some(set_name) = parent_set.name() {
if set_name == "format" {
String::from(".format")
} else {
format!(".lint.{set_name}")
}
} else {
String::new()
};
/// Format the TOML header for the example usage for a given option.
///
/// For example: `[tool.ruff.format]` or `[tool.ruff.lint.isort]`.
fn format_header(
scope: Option<&str>,
parent_set: &Set,
configuration: ConfigurationFile,
) -> String {
match configuration {
ConfigurationFile::PyprojectToml => format!("[tool.ruff{fmt}]"),
ConfigurationFile::PyprojectToml => {
let mut header = if let Some(set_name) = parent_set.name() {
if set_name == "format" {
String::from("tool.ruff.format")
} else {
format!("tool.ruff.lint.{set_name}")
}
} else {
"tool.ruff".to_string()
};
if let Some(scope) = scope {
if !header.is_empty() {
header.push('.');
}
header.push_str(scope);
}
format!("[{header}]")
}
ConfigurationFile::RuffToml => {
if fmt.is_empty() {
let mut header = if let Some(set_name) = parent_set.name() {
if set_name == "format" {
String::from("format")
} else {
format!("lint.{set_name}")
}
} else {
String::new()
};
if let Some(scope) = scope {
if !header.is_empty() {
header.push('.');
}
header.push_str(scope);
}
if header.is_empty() {
String::new()
} else {
format!("[{}]", fmt.strip_prefix('.').unwrap())
format!("[{header}]")
}
}
}

View file

@ -190,9 +190,16 @@ fn handle_option(field: &Field, attr: &Attribute) -> syn::Result<proc_macro2::To
default,
value_type,
example,
scope,
} = parse_field_attributes(attr)?;
let kebab_name = LitStr::new(&ident.to_string().replace('_', "-"), ident.span());
let scope = if let Some(scope) = scope {
quote!(Some(#scope))
} else {
quote!(None)
};
let deprecated = if let Some(deprecated) = field
.attrs
.iter()
@ -221,6 +228,7 @@ fn handle_option(field: &Field, attr: &Attribute) -> syn::Result<proc_macro2::To
default: &#default,
value_type: &#value_type,
example: &#example,
scope: #scope,
deprecated: #deprecated
})
}
@ -232,18 +240,22 @@ struct FieldAttributes {
default: String,
value_type: String,
example: String,
scope: Option<String>,
}
fn parse_field_attributes(attribute: &Attribute) -> syn::Result<FieldAttributes> {
let mut default = None;
let mut value_type = None;
let mut example = None;
let mut scope = None;
attribute.parse_nested_meta(|meta| {
if meta.path.is_ident("default") {
default = Some(get_string_literal(&meta, "default", "option")?.value());
} else if meta.path.is_ident("value_type") {
value_type = Some(get_string_literal(&meta, "value_type", "option")?.value());
} else if meta.path.is_ident("scope") {
scope = Some(get_string_literal(&meta, "scope", "option")?.value());
} else if meta.path.is_ident("example") {
let example_text = get_string_literal(&meta, "value_type", "option")?.value();
example = Some(dedent(&example_text).trim_matches('\n').to_string());
@ -276,6 +288,7 @@ fn parse_field_attributes(attribute: &Attribute) -> syn::Result<FieldAttributes>
default,
value_type,
example,
scope,
})
}

View file

@ -834,9 +834,9 @@ pub struct LintCommonOptions {
#[option(
default = "{}",
value_type = "dict[str, list[RuleSelector]]",
scope = "per-file-ignores",
example = r#"
# Ignore `E402` (import violations) in all `__init__.py` files, and in `path/to/file.py`.
[tool.ruff.lint.per-file-ignores]
"__init__.py" = ["E402"]
"path/to/file.py" = ["E402"]
"#
@ -848,9 +848,9 @@ pub struct LintCommonOptions {
#[option(
default = "{}",
value_type = "dict[str, list[RuleSelector]]",
scope = "extend-per-file-ignores",
example = r#"
# Also ignore `E402` in all `__init__.py` files.
[tool.ruff.lint.extend-per-file-ignores]
"__init__.py" = ["E402"]
"#
)]
@ -1205,8 +1205,8 @@ pub struct Flake8ImportConventionsOptions {
#[option(
default = r#"{"altair": "alt", "matplotlib": "mpl", "matplotlib.pyplot": "plt", "numpy": "np", "pandas": "pd", "seaborn": "sns", "tensorflow": "tf", "tkinter": "tk", "holoviews": "hv", "panel": "pn", "plotly.express": "px", "polars": "pl", "pyarrow": "pa"}"#,
value_type = "dict[str, str]",
scope = "aliases",
example = r#"
[tool.ruff.lint.flake8-import-conventions.aliases]
# Declare the default aliases.
altair = "alt"
"matplotlib.pyplot" = "plt"
@ -1223,8 +1223,8 @@ pub struct Flake8ImportConventionsOptions {
#[option(
default = r#"{}"#,
value_type = "dict[str, str]",
scope = "extend-aliases",
example = r#"
[tool.ruff.lint.flake8-import-conventions.extend-aliases]
# Declare a custom alias for the `matplotlib` module.
"dask.dataframe" = "dd"
"#
@ -1235,8 +1235,8 @@ pub struct Flake8ImportConventionsOptions {
#[option(
default = r#"{}"#,
value_type = "dict[str, list[str]]",
scope = "banned-aliases",
example = r#"
[tool.ruff.lint.flake8-import-conventions.banned-aliases]
# Declare the banned aliases.
"tensorflow.keras.backend" = ["K"]
"#
@ -1548,8 +1548,8 @@ pub struct Flake8TidyImportsOptions {
#[option(
default = r#"{}"#,
value_type = r#"dict[str, { "msg": str }]"#,
scope = "banned-api",
example = r#"
[tool.ruff.lint.flake8-tidy-imports.banned-api]
"cgi".msg = "The cgi module is deprecated, see https://peps.python.org/pep-0594/#cgi."
"typing.TypedDict".msg = "Use typing_extensions.TypedDict instead."
"#
@ -2000,9 +2000,9 @@ pub struct IsortOptions {
#[option(
default = "{}",
value_type = "dict[str, list[str]]",
scope = "sections",
example = r#"
# Group all Django imports into a separate section.
[tool.ruff.lint.isort.sections]
"django" = ["django"]
"#
)]

View file

@ -100,6 +100,7 @@ impl OptionSet {
/// default: "false",
/// value_type: "bool",
/// example: "",
/// scope: None,
/// deprecated: None,
/// });
/// }
@ -122,6 +123,7 @@ impl OptionSet {
/// default: "false",
/// value_type: "bool",
/// example: "",
/// scope: None,
/// deprecated: None
/// });
///
@ -138,6 +140,7 @@ impl OptionSet {
/// default: "false",
/// value_type: "bool",
/// example: "",
/// scope: None,
/// deprecated: None
/// });
/// }
@ -169,6 +172,7 @@ impl OptionSet {
/// default: "false",
/// value_type: "bool",
/// example: "",
/// scope: None,
/// deprecated: None
/// };
///
@ -191,6 +195,7 @@ impl OptionSet {
/// default: "false",
/// value_type: "bool",
/// example: "",
/// scope: None,
/// deprecated: None
/// };
///
@ -203,6 +208,7 @@ impl OptionSet {
/// default: "false",
/// value_type: "bool",
/// example: "",
/// scope: None,
/// deprecated: None
/// });
///
@ -319,8 +325,12 @@ impl Debug for OptionSet {
#[derive(Debug, Eq, PartialEq, Clone)]
pub struct OptionField {
pub doc: &'static str,
/// Ex) `"false"`
pub default: &'static str,
/// Ex) `"bool"`
pub value_type: &'static str,
/// Ex) `"per-file-ignores"`
pub scope: Option<&'static str>,
pub example: &'static str,
pub deprecated: Option<Deprecated>,
}