mirror of https://github.com/astral-sh/ruff
refactor: Move ALL from RuleCodePrefix to RuleSelector
This commit is contained in:
parent
abc9810e2b
commit
28018442f6
|
|
@ -1188,13 +1188,13 @@
|
|||
"RuleSelector": {
|
||||
"type": "string",
|
||||
"enum": [
|
||||
"ALL",
|
||||
"A",
|
||||
"A0",
|
||||
"A00",
|
||||
"A001",
|
||||
"A002",
|
||||
"A003",
|
||||
"ALL",
|
||||
"ANN",
|
||||
"ANN0",
|
||||
"ANN00",
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ use proc_macro2::Span;
|
|||
use quote::quote;
|
||||
use syn::Ident;
|
||||
|
||||
const ALL: &str = "ALL";
|
||||
|
||||
/// A hash map from deprecated `RuleSelector` to latest
|
||||
/// `RuleSelector`.
|
||||
pub static PREFIX_REDIRECTS: Lazy<HashMap<&'static str, &'static str>> = Lazy::new(|| {
|
||||
|
|
@ -116,7 +114,6 @@ pub fn expand<'a>(
|
|||
all_codes.insert(code_str);
|
||||
}
|
||||
|
||||
prefix_to_codes.insert(ALL.to_string(), all_codes);
|
||||
prefix_to_codes.insert("PL".to_string(), pl_codes);
|
||||
|
||||
// Add any prefix aliases (e.g., "U" to "UP").
|
||||
|
|
@ -148,6 +145,7 @@ pub fn expand<'a>(
|
|||
|
||||
quote! {
|
||||
#[derive(
|
||||
::strum_macros::EnumIter,
|
||||
::strum_macros::EnumString,
|
||||
::strum_macros::AsRefStr,
|
||||
Debug,
|
||||
|
|
@ -158,7 +156,6 @@ pub fn expand<'a>(
|
|||
Clone,
|
||||
::serde::Serialize,
|
||||
::serde::Deserialize,
|
||||
::schemars::JsonSchema,
|
||||
)]
|
||||
pub enum #prefix_ident {
|
||||
#(#prefix_variants,)*
|
||||
|
|
@ -207,11 +204,6 @@ fn generate_impls<'a>(
|
|||
|
||||
let specificity_match_arms = prefix_to_codes.keys().map(|prefix_str| {
|
||||
let prefix = Ident::new(prefix_str, Span::call_site());
|
||||
if prefix_str == ALL {
|
||||
quote! {
|
||||
#prefix_ident::#prefix => Specificity::All,
|
||||
}
|
||||
} else {
|
||||
let mut num_numeric = prefix_str.chars().filter(|char| char.is_numeric()).count();
|
||||
if prefix_str != "PL" && prefix_str.starts_with("PL") {
|
||||
num_numeric += 1;
|
||||
|
|
@ -228,7 +220,6 @@ fn generate_impls<'a>(
|
|||
quote! {
|
||||
#prefix_ident::#prefix => #suffix_len,
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
quote! {
|
||||
|
|
|
|||
|
|
@ -1,33 +1,120 @@
|
|||
use std::str::FromStr;
|
||||
|
||||
use schemars::_serde_json::Value;
|
||||
use schemars::schema::{InstanceType, Schema, SchemaObject};
|
||||
use schemars::JsonSchema;
|
||||
use serde::de::{self, Visitor};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use strum::IntoEnumIterator;
|
||||
|
||||
use crate::registry::{Rule, RuleCodePrefix};
|
||||
use crate::registry::{Rule, RuleCodePrefix, RuleIter};
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Serialize, Deserialize)]
|
||||
pub struct RuleSelector(RuleCodePrefix);
|
||||
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord)]
|
||||
pub enum RuleSelector {
|
||||
/// All rules
|
||||
All,
|
||||
Prefix(RuleCodePrefix),
|
||||
}
|
||||
|
||||
impl FromStr for RuleSelector {
|
||||
type Err = strum::ParseError;
|
||||
type Err = ParseError;
|
||||
|
||||
fn from_str(s: &str) -> Result<Self, Self::Err> {
|
||||
Ok(Self(RuleCodePrefix::from_str(s)?))
|
||||
if s == "ALL" {
|
||||
Ok(Self::All)
|
||||
} else {
|
||||
Ok(Self::Prefix(
|
||||
RuleCodePrefix::from_str(s).map_err(|_| ParseError::Unknown(s.to_string()))?,
|
||||
))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, thiserror::Error)]
|
||||
pub enum ParseError {
|
||||
#[error("Unknown rule selector `{0}`")]
|
||||
// TODO(martin): tell the user how to discover rule codes via the CLI once such a command is
|
||||
// implemented (but that should of course be done only in ruff_cli and not here)
|
||||
Unknown(String),
|
||||
}
|
||||
|
||||
impl Serialize for RuleSelector {
|
||||
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
|
||||
where
|
||||
S: serde::Serializer,
|
||||
{
|
||||
match self {
|
||||
RuleSelector::All => serializer.serialize_str("ALL"),
|
||||
RuleSelector::Prefix(prefix) => prefix.serialize(serializer),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<'de> Deserialize<'de> for RuleSelector {
|
||||
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
|
||||
where
|
||||
D: serde::Deserializer<'de>,
|
||||
{
|
||||
// We are not simply doing:
|
||||
// let s: &str = Deserialize::deserialize(deserializer)?;
|
||||
// FromStr::from_str(s).map_err(de::Error::custom)
|
||||
// here because the toml crate apparently doesn't support that
|
||||
// (as of toml v0.6.0 running `cargo test` failed with the above two lines)
|
||||
deserializer.deserialize_str(SelectorVisitor)
|
||||
}
|
||||
}
|
||||
|
||||
struct SelectorVisitor;
|
||||
|
||||
impl Visitor<'_> for SelectorVisitor {
|
||||
type Value = RuleSelector;
|
||||
|
||||
fn expecting(&self, formatter: &mut std::fmt::Formatter) -> std::fmt::Result {
|
||||
formatter.write_str(
|
||||
"expected a string code identifying a linter or specific rule, or a partial rule code \
|
||||
or ALL to refer to all rules",
|
||||
)
|
||||
}
|
||||
|
||||
fn visit_str<E>(self, v: &str) -> Result<Self::Value, E>
|
||||
where
|
||||
E: de::Error,
|
||||
{
|
||||
FromStr::from_str(v).map_err(de::Error::custom)
|
||||
}
|
||||
}
|
||||
|
||||
impl From<RuleCodePrefix> for RuleSelector {
|
||||
fn from(prefix: RuleCodePrefix) -> Self {
|
||||
Self(prefix)
|
||||
Self::Prefix(prefix)
|
||||
}
|
||||
}
|
||||
|
||||
impl IntoIterator for &RuleSelector {
|
||||
type IntoIter = ::std::vec::IntoIter<Self::Item>;
|
||||
type IntoIter = RuleSelectorIter;
|
||||
type Item = Rule;
|
||||
|
||||
fn into_iter(self) -> Self::IntoIter {
|
||||
self.0.into_iter()
|
||||
match self {
|
||||
RuleSelector::All => RuleSelectorIter::All(Rule::iter()),
|
||||
RuleSelector::Prefix(prefix) => RuleSelectorIter::Prefix(prefix.into_iter()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub enum RuleSelectorIter {
|
||||
All(RuleIter),
|
||||
Prefix(std::vec::IntoIter<Rule>),
|
||||
}
|
||||
|
||||
impl Iterator for RuleSelectorIter {
|
||||
type Item = Rule;
|
||||
|
||||
fn next(&mut self) -> Option<Self::Item> {
|
||||
match self {
|
||||
RuleSelectorIter::All(iter) => iter.next(),
|
||||
RuleSelectorIter::Prefix(iter) => iter.next(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -37,7 +124,7 @@ impl IntoIterator for &RuleSelector {
|
|||
// RuleSelector` (see https://github.com/rust-lang/rust/issues/67792).
|
||||
// TODO(martin): Remove once RuleSelector is an enum with Linter & Rule variants
|
||||
pub(crate) const fn prefix_to_selector(prefix: RuleCodePrefix) -> RuleSelector {
|
||||
RuleSelector(prefix)
|
||||
RuleSelector::Prefix(prefix)
|
||||
}
|
||||
|
||||
impl JsonSchema for RuleSelector {
|
||||
|
|
@ -45,14 +132,26 @@ impl JsonSchema for RuleSelector {
|
|||
"RuleSelector".to_string()
|
||||
}
|
||||
|
||||
fn json_schema(gen: &mut schemars::gen::SchemaGenerator) -> schemars::schema::Schema {
|
||||
<RuleCodePrefix as JsonSchema>::json_schema(gen)
|
||||
fn json_schema(_gen: &mut schemars::gen::SchemaGenerator) -> schemars::schema::Schema {
|
||||
Schema::Object(SchemaObject {
|
||||
instance_type: Some(InstanceType::String.into()),
|
||||
enum_values: Some(
|
||||
std::iter::once("ALL".to_string())
|
||||
.chain(RuleCodePrefix::iter().map(|s| s.as_ref().to_string()))
|
||||
.map(Value::String)
|
||||
.collect(),
|
||||
),
|
||||
..SchemaObject::default()
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
impl RuleSelector {
|
||||
pub(crate) fn specificity(&self) -> Specificity {
|
||||
self.0.specificity()
|
||||
match self {
|
||||
RuleSelector::All => Specificity::All,
|
||||
RuleSelector::Prefix(prefix) => prefix.specificity(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -239,10 +239,7 @@ impl From<&Configuration> for RuleTable {
|
|||
let mut rules = RuleTable::empty();
|
||||
|
||||
let fixable = resolve_codes([RuleCodeSpec {
|
||||
select: config
|
||||
.fixable
|
||||
.as_deref()
|
||||
.unwrap_or(&[crate::registry::RuleCodePrefix::ALL.into()]),
|
||||
select: config.fixable.as_deref().unwrap_or(&[RuleSelector::All]),
|
||||
ignore: config.unfixable.as_deref().unwrap_or_default(),
|
||||
}]);
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue