mirror of https://github.com/astral-sh/ruff
[ty] remove the `visitor` parameter in the `recursive_type_normalized_impl` method (#21701)
This commit is contained in:
parent
846df40a6e
commit
a6cbc138d2
|
|
@ -52,6 +52,10 @@ def f(x: A):
|
||||||
|
|
||||||
JSONPrimitive = Union[str, int, float, bool, None]
|
JSONPrimitive = Union[str, int, float, bool, None]
|
||||||
JSONValue = TypeAliasType("JSONValue", 'Union[JSONPrimitive, Sequence["JSONValue"], Mapping[str, "JSONValue"]]')
|
JSONValue = TypeAliasType("JSONValue", 'Union[JSONPrimitive, Sequence["JSONValue"], Mapping[str, "JSONValue"]]')
|
||||||
|
|
||||||
|
def _(x: JSONValue):
|
||||||
|
# TODO: should be `JSONValue`
|
||||||
|
reveal_type(x) # revealed: Divergent
|
||||||
```
|
```
|
||||||
|
|
||||||
## Self-referential legacy type variables
|
## Self-referential legacy type variables
|
||||||
|
|
|
||||||
|
|
@ -573,20 +573,19 @@ impl<'db> PropertyInstanceType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
let getter = match self.getter(db) {
|
let getter = match self.getter(db) {
|
||||||
Some(ty) if nested => Some(ty.recursive_type_normalized_impl(db, div, true, visitor)?),
|
Some(ty) if nested => Some(ty.recursive_type_normalized_impl(db, div, true)?),
|
||||||
Some(ty) => Some(
|
Some(ty) => Some(
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
None => None,
|
None => None,
|
||||||
};
|
};
|
||||||
let setter = match self.setter(db) {
|
let setter = match self.setter(db) {
|
||||||
Some(ty) if nested => Some(ty.recursive_type_normalized_impl(db, div, true, visitor)?),
|
Some(ty) if nested => Some(ty.recursive_type_normalized_impl(db, div, true)?),
|
||||||
Some(ty) => Some(
|
Some(ty) => Some(
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
None => None,
|
None => None,
|
||||||
|
|
@ -1553,15 +1552,14 @@ impl<'db> Type<'db> {
|
||||||
#[must_use]
|
#[must_use]
|
||||||
pub(crate) fn recursive_type_normalized(self, db: &'db dyn Db, cycle: &salsa::Cycle) -> Self {
|
pub(crate) fn recursive_type_normalized(self, db: &'db dyn Db, cycle: &salsa::Cycle) -> Self {
|
||||||
cycle.head_ids().fold(self, |ty, id| {
|
cycle.head_ids().fold(self, |ty, id| {
|
||||||
let visitor = NormalizedVisitor::new(Type::divergent(id));
|
ty.recursive_type_normalized_impl(db, Type::divergent(id), false)
|
||||||
ty.recursive_type_normalized_impl(db, Type::divergent(id), false, &visitor)
|
|
||||||
.unwrap_or(Type::divergent(id))
|
.unwrap_or(Type::divergent(id))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Normalizes types including divergent types (recursive types), which is necessary for convergence of fixed-point iteration.
|
/// Normalizes types including divergent types (recursive types), which is necessary for convergence of fixed-point iteration.
|
||||||
/// When nested is true, propagate `None`. That is, if the type contains a `Divergent` type, the return value of this method is `None`.
|
/// When `nested` is true, propagate `None`. That is, if the type contains a `Divergent` type, the return value of this method is `None` (so we can use the `?` operator).
|
||||||
/// When nested is false, create a type containing `Divergent` types instead of propagating `None`.
|
/// When `nested` is false, create a type containing `Divergent` types instead of propagating `None` (we should use `unwrap_or(Divergent)`).
|
||||||
/// This is to preserve the structure of the non-divergent parts of the type instead of completely collapsing the type containing a `Divergent` type into a `Divergent` type.
|
/// This is to preserve the structure of the non-divergent parts of the type instead of completely collapsing the type containing a `Divergent` type into a `Divergent` type.
|
||||||
/// ```python
|
/// ```python
|
||||||
/// tuple[tuple[Divergent, Literal[1]], Literal[1]].recursive_type_normalized(nested: false)
|
/// tuple[tuple[Divergent, Literal[1]], Literal[1]].recursive_type_normalized(nested: false)
|
||||||
|
|
@ -1580,102 +1578,73 @@ impl<'db> Type<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
if nested && self == div {
|
if nested && self == div {
|
||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
match self {
|
match self {
|
||||||
Type::Union(union) => visitor.try_visit(self, || {
|
Type::Union(union) => union.recursive_type_normalized_impl(db, div, nested),
|
||||||
union.recursive_type_normalized_impl(db, div, nested, visitor)
|
Type::Intersection(intersection) => intersection
|
||||||
}),
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
Type::Intersection(intersection) => visitor.try_visit(self, || {
|
.map(Type::Intersection),
|
||||||
intersection
|
Type::Callable(callable) => callable
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.map(Type::Intersection)
|
.map(Type::Callable),
|
||||||
}),
|
Type::ProtocolInstance(protocol) => protocol
|
||||||
Type::Callable(callable) => visitor.try_visit(self, || {
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
callable
|
.map(Type::ProtocolInstance),
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
Type::NominalInstance(instance) => instance
|
||||||
.map(Type::Callable)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
}),
|
.map(Type::NominalInstance),
|
||||||
Type::ProtocolInstance(protocol) => visitor.try_visit(self, || {
|
Type::FunctionLiteral(function) => function
|
||||||
protocol
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.map(Type::FunctionLiteral),
|
||||||
.map(Type::ProtocolInstance)
|
Type::PropertyInstance(property) => property
|
||||||
}),
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
Type::NominalInstance(instance) => visitor.try_visit(self, || {
|
.map(Type::PropertyInstance),
|
||||||
instance
|
Type::KnownBoundMethod(method_kind) => method_kind
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.map(Type::NominalInstance)
|
.map(Type::KnownBoundMethod),
|
||||||
}),
|
Type::BoundMethod(method) => method
|
||||||
Type::FunctionLiteral(function) => visitor.try_visit(self, || {
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
function
|
.map(Type::BoundMethod),
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
Type::BoundSuper(bound_super) => bound_super
|
||||||
.map(Type::FunctionLiteral)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
}),
|
.map(Type::BoundSuper),
|
||||||
Type::PropertyInstance(property) => visitor.try_visit(self, || {
|
Type::GenericAlias(generic) => generic
|
||||||
property
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.map(Type::GenericAlias),
|
||||||
.map(Type::PropertyInstance)
|
Type::SubclassOf(subclass_of) => subclass_of
|
||||||
}),
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
Type::KnownBoundMethod(method_kind) => visitor.try_visit(self, || {
|
.map(Type::SubclassOf),
|
||||||
method_kind
|
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
|
||||||
.map(Type::KnownBoundMethod)
|
|
||||||
}),
|
|
||||||
Type::BoundMethod(method) => visitor.try_visit(self, || {
|
|
||||||
method
|
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
|
||||||
.map(Type::BoundMethod)
|
|
||||||
}),
|
|
||||||
Type::BoundSuper(bound_super) => visitor.try_visit(self, || {
|
|
||||||
bound_super
|
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
|
||||||
.map(Type::BoundSuper)
|
|
||||||
}),
|
|
||||||
Type::GenericAlias(generic) => visitor.try_visit(self, || {
|
|
||||||
generic
|
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
|
||||||
.map(Type::GenericAlias)
|
|
||||||
}),
|
|
||||||
Type::SubclassOf(subclass_of) => visitor.try_visit(self, || {
|
|
||||||
subclass_of
|
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
|
||||||
.map(Type::SubclassOf)
|
|
||||||
}),
|
|
||||||
Type::TypeVar(_) => Some(self),
|
Type::TypeVar(_) => Some(self),
|
||||||
Type::KnownInstance(known_instance) => visitor.try_visit(self, || {
|
Type::KnownInstance(known_instance) => known_instance
|
||||||
known_instance
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.map(Type::KnownInstance),
|
||||||
.map(Type::KnownInstance)
|
Type::TypeIs(type_is) => {
|
||||||
}),
|
|
||||||
Type::TypeIs(type_is) => visitor.try_visit(self, || {
|
|
||||||
let ty = if nested {
|
let ty = if nested {
|
||||||
type_is
|
type_is
|
||||||
.return_type(db)
|
.return_type(db)
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)?
|
.recursive_type_normalized_impl(db, div, true)?
|
||||||
} else {
|
} else {
|
||||||
type_is
|
type_is
|
||||||
.return_type(db)
|
.return_type(db)
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
};
|
};
|
||||||
Some(type_is.with_type(db, ty))
|
Some(type_is.with_type(db, ty))
|
||||||
}),
|
}
|
||||||
Type::Dynamic(dynamic) => Some(Type::Dynamic(dynamic.recursive_type_normalized())),
|
Type::Dynamic(dynamic) => Some(Type::Dynamic(dynamic.recursive_type_normalized())),
|
||||||
Type::TypedDict(_) => {
|
Type::TypedDict(_) => {
|
||||||
// TODO: Normalize TypedDicts
|
// TODO: Normalize TypedDicts
|
||||||
Some(self)
|
Some(self)
|
||||||
}
|
}
|
||||||
Type::TypeAlias(_) => Some(self),
|
Type::TypeAlias(_) => Some(self),
|
||||||
Type::NewTypeInstance(newtype) => visitor.try_visit(self, || {
|
Type::NewTypeInstance(newtype) => newtype
|
||||||
newtype
|
|
||||||
.try_map_base_class_type(db, |class_type| {
|
.try_map_base_class_type(db, |class_type| {
|
||||||
class_type.recursive_type_normalized_impl(db, div, nested, visitor)
|
class_type.recursive_type_normalized_impl(db, div, nested)
|
||||||
})
|
})
|
||||||
.map(Type::NewTypeInstance)
|
.map(Type::NewTypeInstance),
|
||||||
}),
|
|
||||||
Type::LiteralString
|
Type::LiteralString
|
||||||
| Type::AlwaysFalsy
|
| Type::AlwaysFalsy
|
||||||
| Type::AlwaysTruthy
|
| Type::AlwaysTruthy
|
||||||
|
|
@ -8702,7 +8671,6 @@ impl<'db> KnownInstanceType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self {
|
match self {
|
||||||
// Nothing to normalize
|
// Nothing to normalize
|
||||||
|
|
@ -8712,37 +8680,37 @@ impl<'db> KnownInstanceType<'db> {
|
||||||
Self::ConstraintSet(set) => Some(Self::ConstraintSet(set)),
|
Self::ConstraintSet(set) => Some(Self::ConstraintSet(set)),
|
||||||
Self::TypeVar(typevar) => Some(Self::TypeVar(typevar)),
|
Self::TypeVar(typevar) => Some(Self::TypeVar(typevar)),
|
||||||
Self::TypeAliasType(type_alias) => type_alias
|
Self::TypeAliasType(type_alias) => type_alias
|
||||||
.recursive_type_normalized_impl(db, div, visitor)
|
.recursive_type_normalized_impl(db, div)
|
||||||
.map(Self::TypeAliasType),
|
.map(Self::TypeAliasType),
|
||||||
Self::Field(field) => field
|
Self::Field(field) => field
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.map(Self::Field),
|
.map(Self::Field),
|
||||||
Self::UnionType(union_type) => union_type
|
Self::UnionType(union_type) => union_type
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.map(Self::UnionType),
|
.map(Self::UnionType),
|
||||||
Self::Literal(ty) => ty
|
Self::Literal(ty) => ty
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.map(Self::Literal),
|
.map(Self::Literal),
|
||||||
Self::Annotated(ty) => ty
|
Self::Annotated(ty) => ty
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.map(Self::Annotated),
|
.map(Self::Annotated),
|
||||||
Self::TypeGenericAlias(ty) => ty
|
Self::TypeGenericAlias(ty) => ty
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.map(Self::TypeGenericAlias),
|
.map(Self::TypeGenericAlias),
|
||||||
Self::LiteralStringAlias(ty) => ty
|
Self::LiteralStringAlias(ty) => ty
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.map(Self::LiteralStringAlias),
|
.map(Self::LiteralStringAlias),
|
||||||
Self::Callable(callable) => callable
|
Self::Callable(callable) => callable
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.map(Self::Callable),
|
.map(Self::Callable),
|
||||||
Self::NewType(newtype) => newtype
|
Self::NewType(newtype) => newtype
|
||||||
.try_map_base_class_type(db, |class_type| {
|
.try_map_base_class_type(db, |class_type| {
|
||||||
class_type.recursive_type_normalized_impl(db, div, true, visitor)
|
class_type.recursive_type_normalized_impl(db, div, true)
|
||||||
})
|
})
|
||||||
.map(Self::NewType),
|
.map(Self::NewType),
|
||||||
Self::GenericContext(generic) => Some(Self::GenericContext(generic)),
|
Self::GenericContext(generic) => Some(Self::GenericContext(generic)),
|
||||||
Self::Specialization(specialization) => specialization
|
Self::Specialization(specialization) => specialization
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.map(Self::Specialization),
|
.map(Self::Specialization),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -9231,15 +9199,12 @@ impl<'db> FieldInstance<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
let default_type = match self.default_type(db) {
|
let default_type = match self.default_type(db) {
|
||||||
Some(default) if nested => {
|
Some(default) if nested => Some(default.recursive_type_normalized_impl(db, div, true)?),
|
||||||
Some(default.recursive_type_normalized_impl(db, div, true, visitor)?)
|
|
||||||
}
|
|
||||||
Some(default) => Some(
|
Some(default) => Some(
|
||||||
default
|
default
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
None => None,
|
None => None,
|
||||||
|
|
@ -10184,7 +10149,6 @@ impl<'db> UnionTypeInstance<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
// The `Divergent` elimination rules are different within union types.
|
// The `Divergent` elimination rules are different within union types.
|
||||||
// See `UnionType::recursive_type_normalized_impl` for details.
|
// See `UnionType::recursive_type_normalized_impl` for details.
|
||||||
|
|
@ -10192,14 +10156,14 @@ impl<'db> UnionTypeInstance<'db> {
|
||||||
Some(types) if nested => Some(
|
Some(types) if nested => Some(
|
||||||
types
|
types
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| ty.recursive_type_normalized_impl(db, div, nested, visitor))
|
.map(|ty| ty.recursive_type_normalized_impl(db, div, nested))
|
||||||
.collect::<Option<Box<_>>>()?,
|
.collect::<Option<Box<_>>>()?,
|
||||||
),
|
),
|
||||||
Some(types) => Some(
|
Some(types) => Some(
|
||||||
types
|
types
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| {
|
.map(|ty| {
|
||||||
ty.recursive_type_normalized_impl(db, div, nested, visitor)
|
ty.recursive_type_normalized_impl(db, div, nested)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
})
|
})
|
||||||
.collect::<Box<_>>(),
|
.collect::<Box<_>>(),
|
||||||
|
|
@ -10207,9 +10171,9 @@ impl<'db> UnionTypeInstance<'db> {
|
||||||
None => None,
|
None => None,
|
||||||
};
|
};
|
||||||
let union_type = match self.union_type(db).clone() {
|
let union_type = match self.union_type(db).clone() {
|
||||||
Ok(ty) if nested => Ok(ty.recursive_type_normalized_impl(db, div, nested, visitor)?),
|
Ok(ty) if nested => Ok(ty.recursive_type_normalized_impl(db, div, nested)?),
|
||||||
Ok(ty) => Ok(ty
|
Ok(ty) => Ok(ty
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.unwrap_or(div)),
|
.unwrap_or(div)),
|
||||||
Err(err) => Err(err),
|
Err(err) => Err(err),
|
||||||
};
|
};
|
||||||
|
|
@ -10241,14 +10205,13 @@ impl<'db> InternedType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
let inner = if nested {
|
let inner = if nested {
|
||||||
self.inner(db)
|
self.inner(db)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?
|
.recursive_type_normalized_impl(db, div, nested)?
|
||||||
} else {
|
} else {
|
||||||
self.inner(db)
|
self.inner(db)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)
|
.recursive_type_normalized_impl(db, div, nested)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
};
|
};
|
||||||
Some(InternedType::new(db, inner))
|
Some(InternedType::new(db, inner))
|
||||||
|
|
@ -11560,14 +11523,13 @@ impl<'db> BoundMethodType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self::new(
|
Some(Self::new(
|
||||||
db,
|
db,
|
||||||
self.function(db)
|
self.function(db)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
self.self_instance(db)
|
self.self_instance(db)
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)?,
|
.recursive_type_normalized_impl(db, div, true)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -11732,12 +11694,11 @@ impl<'db> CallableType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(CallableType::new(
|
Some(CallableType::new(
|
||||||
db,
|
db,
|
||||||
self.signatures(db)
|
self.signatures(db)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
self.is_function_like(db),
|
self.is_function_like(db),
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
@ -12175,27 +12136,26 @@ impl<'db> KnownBoundMethodType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self {
|
match self {
|
||||||
KnownBoundMethodType::FunctionTypeDunderGet(function) => {
|
KnownBoundMethodType::FunctionTypeDunderGet(function) => {
|
||||||
Some(KnownBoundMethodType::FunctionTypeDunderGet(
|
Some(KnownBoundMethodType::FunctionTypeDunderGet(
|
||||||
function.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
function.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
KnownBoundMethodType::FunctionTypeDunderCall(function) => {
|
KnownBoundMethodType::FunctionTypeDunderCall(function) => {
|
||||||
Some(KnownBoundMethodType::FunctionTypeDunderCall(
|
Some(KnownBoundMethodType::FunctionTypeDunderCall(
|
||||||
function.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
function.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
KnownBoundMethodType::PropertyDunderGet(property) => {
|
KnownBoundMethodType::PropertyDunderGet(property) => {
|
||||||
Some(KnownBoundMethodType::PropertyDunderGet(
|
Some(KnownBoundMethodType::PropertyDunderGet(
|
||||||
property.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
property.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
KnownBoundMethodType::PropertyDunderSet(property) => {
|
KnownBoundMethodType::PropertyDunderSet(property) => {
|
||||||
Some(KnownBoundMethodType::PropertyDunderSet(
|
Some(KnownBoundMethodType::PropertyDunderSet(
|
||||||
property.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
property.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
KnownBoundMethodType::StrStartswith(_)
|
KnownBoundMethodType::StrStartswith(_)
|
||||||
|
|
@ -12858,18 +12818,14 @@ impl<'db> ManualPEP695TypeAliasType<'db> {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn recursive_type_normalized_impl(
|
// TODO: with full support for manual PEP-695 style type aliases, this method should become unnecessary.
|
||||||
self,
|
fn recursive_type_normalized_impl(self, db: &'db dyn Db, div: Type<'db>) -> Option<Self> {
|
||||||
db: &'db dyn Db,
|
|
||||||
div: Type<'db>,
|
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
|
||||||
Some(Self::new(
|
Some(Self::new(
|
||||||
db,
|
db,
|
||||||
self.name(db),
|
self.name(db),
|
||||||
self.definition(db),
|
self.definition(db),
|
||||||
self.value(db)
|
self.value(db)
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)?,
|
.recursive_type_normalized_impl(db, div, true)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -12914,16 +12870,11 @@ impl<'db> TypeAliasType<'db> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn recursive_type_normalized_impl(
|
fn recursive_type_normalized_impl(self, db: &'db dyn Db, div: Type<'db>) -> Option<Self> {
|
||||||
self,
|
|
||||||
db: &'db dyn Db,
|
|
||||||
div: Type<'db>,
|
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
|
||||||
match self {
|
match self {
|
||||||
TypeAliasType::PEP695(type_alias) => Some(TypeAliasType::PEP695(type_alias)),
|
TypeAliasType::PEP695(type_alias) => Some(TypeAliasType::PEP695(type_alias)),
|
||||||
TypeAliasType::ManualPEP695(type_alias) => Some(TypeAliasType::ManualPEP695(
|
TypeAliasType::ManualPEP695(type_alias) => Some(TypeAliasType::ManualPEP695(
|
||||||
type_alias.recursive_type_normalized_impl(db, div, visitor)?,
|
type_alias.recursive_type_normalized_impl(db, div)?,
|
||||||
)),
|
)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -13248,7 +13199,6 @@ impl<'db> UnionType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Type<'db>> {
|
) -> Option<Type<'db>> {
|
||||||
let mut builder = UnionBuilder::new(db)
|
let mut builder = UnionBuilder::new(db)
|
||||||
.order_elements(false)
|
.order_elements(false)
|
||||||
|
|
@ -13258,7 +13208,7 @@ impl<'db> UnionType<'db> {
|
||||||
for ty in self.elements(db) {
|
for ty in self.elements(db) {
|
||||||
if nested {
|
if nested {
|
||||||
// list[T | Divergent] => list[Divergent]
|
// list[T | Divergent] => list[Divergent]
|
||||||
let ty = ty.recursive_type_normalized_impl(db, div, nested, visitor)?;
|
let ty = ty.recursive_type_normalized_impl(db, div, nested)?;
|
||||||
if ty == div {
|
if ty == div {
|
||||||
return Some(ty);
|
return Some(ty);
|
||||||
}
|
}
|
||||||
|
|
@ -13271,7 +13221,7 @@ impl<'db> UnionType<'db> {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
builder = builder.add(
|
builder = builder.add(
|
||||||
ty.recursive_type_normalized_impl(db, div, nested, visitor)
|
ty.recursive_type_normalized_impl(db, div, nested)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
);
|
);
|
||||||
empty = false;
|
empty = false;
|
||||||
|
|
@ -13389,18 +13339,16 @@ impl<'db> IntersectionType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
fn opt_normalized_set<'db>(
|
fn opt_normalized_set<'db>(
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
elements: &FxOrderSet<Type<'db>>,
|
elements: &FxOrderSet<Type<'db>>,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<FxOrderSet<Type<'db>>> {
|
) -> Option<FxOrderSet<Type<'db>>> {
|
||||||
elements
|
elements
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| ty.recursive_type_normalized_impl(db, div, nested, visitor))
|
.map(|ty| ty.recursive_type_normalized_impl(db, div, nested))
|
||||||
.collect()
|
.collect()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -13409,26 +13357,25 @@ impl<'db> IntersectionType<'db> {
|
||||||
elements: &FxOrderSet<Type<'db>>,
|
elements: &FxOrderSet<Type<'db>>,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> FxOrderSet<Type<'db>> {
|
) -> FxOrderSet<Type<'db>> {
|
||||||
elements
|
elements
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| {
|
.map(|ty| {
|
||||||
ty.recursive_type_normalized_impl(db, div, nested, visitor)
|
ty.recursive_type_normalized_impl(db, div, nested)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
})
|
})
|
||||||
.collect()
|
.collect()
|
||||||
}
|
}
|
||||||
|
|
||||||
let positive = if nested {
|
let positive = if nested {
|
||||||
opt_normalized_set(db, self.positive(db), div, nested, visitor)?
|
opt_normalized_set(db, self.positive(db), div, nested)?
|
||||||
} else {
|
} else {
|
||||||
normalized_set(db, self.positive(db), div, nested, visitor)
|
normalized_set(db, self.positive(db), div, nested)
|
||||||
};
|
};
|
||||||
let negative = if nested {
|
let negative = if nested {
|
||||||
opt_normalized_set(db, self.negative(db), div, nested, visitor)?
|
opt_normalized_set(db, self.negative(db), div, nested)?
|
||||||
} else {
|
} else {
|
||||||
normalized_set(db, self.negative(db), div, nested, visitor)
|
normalized_set(db, self.negative(db), div, nested)
|
||||||
};
|
};
|
||||||
|
|
||||||
Some(IntersectionType::new(db, positive, negative))
|
Some(IntersectionType::new(db, positive, negative))
|
||||||
|
|
@ -13911,16 +13858,15 @@ pub(crate) mod tests {
|
||||||
nested_rec.display(&db).to_string(),
|
nested_rec.display(&db).to_string(),
|
||||||
"list[list[Divergent] | None]"
|
"list[list[Divergent] | None]"
|
||||||
);
|
);
|
||||||
let visitor = NormalizedVisitor::default();
|
|
||||||
let normalized = nested_rec
|
let normalized = nested_rec
|
||||||
.recursive_type_normalized_impl(&db, div, false, &visitor)
|
.recursive_type_normalized_impl(&db, div, false)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
assert_eq!(normalized.display(&db).to_string(), "list[Divergent]");
|
assert_eq!(normalized.display(&db).to_string(), "list[Divergent]");
|
||||||
|
|
||||||
let union = UnionType::from_elements(&db, [div, KnownClass::Int.to_instance(&db)]);
|
let union = UnionType::from_elements(&db, [div, KnownClass::Int.to_instance(&db)]);
|
||||||
assert_eq!(union.display(&db).to_string(), "Divergent | int");
|
assert_eq!(union.display(&db).to_string(), "Divergent | int");
|
||||||
let normalized = union
|
let normalized = union
|
||||||
.recursive_type_normalized_impl(&db, div, false, &visitor)
|
.recursive_type_normalized_impl(&db, div, false)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
assert_eq!(normalized.display(&db).to_string(), "int");
|
assert_eq!(normalized.display(&db).to_string(), "int");
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -197,17 +197,16 @@ impl<'db> SuperOwnerKind<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self {
|
match self {
|
||||||
SuperOwnerKind::Dynamic(dynamic) => {
|
SuperOwnerKind::Dynamic(dynamic) => {
|
||||||
Some(SuperOwnerKind::Dynamic(dynamic.recursive_type_normalized()))
|
Some(SuperOwnerKind::Dynamic(dynamic.recursive_type_normalized()))
|
||||||
}
|
}
|
||||||
SuperOwnerKind::Class(class) => Some(SuperOwnerKind::Class(
|
SuperOwnerKind::Class(class) => Some(SuperOwnerKind::Class(
|
||||||
class.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
class.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
SuperOwnerKind::Instance(instance) => Some(SuperOwnerKind::Instance(
|
SuperOwnerKind::Instance(instance) => Some(SuperOwnerKind::Instance(
|
||||||
instance.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
instance.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -620,14 +619,13 @@ impl<'db> BoundSuperType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self::new(
|
Some(Self::new(
|
||||||
db,
|
db,
|
||||||
self.pivot_class(db)
|
self.pivot_class(db)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
self.owner(db)
|
self.owner(db)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -284,13 +284,12 @@ impl<'db> GenericAlias<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self::new(
|
Some(Self::new(
|
||||||
db,
|
db,
|
||||||
self.origin(db),
|
self.origin(db),
|
||||||
self.specialization(db)
|
self.specialization(db)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -443,12 +442,11 @@ impl<'db> ClassType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self {
|
match self {
|
||||||
Self::NonGeneric(_) => Some(self),
|
Self::NonGeneric(_) => Some(self),
|
||||||
Self::Generic(generic) => Some(Self::Generic(
|
Self::Generic(generic) => Some(Self::Generic(
|
||||||
generic.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
generic.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -48,12 +48,11 @@ impl<'db> ClassBase<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self {
|
match self {
|
||||||
Self::Dynamic(dynamic) => Some(Self::Dynamic(dynamic.recursive_type_normalized())),
|
Self::Dynamic(dynamic) => Some(Self::Dynamic(dynamic.recursive_type_normalized())),
|
||||||
Self::Class(class) => Some(Self::Class(
|
Self::Class(class) => Some(Self::Class(
|
||||||
class.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
class.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
Self::Protocol | Self::Generic | Self::TypedDict => Some(self),
|
Self::Protocol | Self::Generic | Self::TypedDict => Some(self),
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1112,19 +1112,14 @@ impl<'db> FunctionType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
let literal = self.literal(db);
|
let literal = self.literal(db);
|
||||||
let updated_signature = match self.updated_signature(db) {
|
let updated_signature = match self.updated_signature(db) {
|
||||||
Some(signature) => {
|
Some(signature) => Some(signature.recursive_type_normalized_impl(db, div, nested)?),
|
||||||
Some(signature.recursive_type_normalized_impl(db, div, nested, visitor)?)
|
|
||||||
}
|
|
||||||
None => None,
|
None => None,
|
||||||
};
|
};
|
||||||
let updated_last_definition_signature = match self.updated_last_definition_signature(db) {
|
let updated_last_definition_signature = match self.updated_last_definition_signature(db) {
|
||||||
Some(signature) => {
|
Some(signature) => Some(signature.recursive_type_normalized_impl(db, div, nested)?),
|
||||||
Some(signature.recursive_type_normalized_impl(db, div, nested, visitor)?)
|
|
||||||
}
|
|
||||||
None => None,
|
None => None,
|
||||||
};
|
};
|
||||||
Some(Self::new(
|
Some(Self::new(
|
||||||
|
|
|
||||||
|
|
@ -1045,24 +1045,23 @@ impl<'db> Specialization<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
let types = if nested {
|
let types = if nested {
|
||||||
self.types(db)
|
self.types(db)
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| ty.recursive_type_normalized_impl(db, div, true, visitor))
|
.map(|ty| ty.recursive_type_normalized_impl(db, div, true))
|
||||||
.collect::<Option<Box<[_]>>>()?
|
.collect::<Option<Box<[_]>>>()?
|
||||||
} else {
|
} else {
|
||||||
self.types(db)
|
self.types(db)
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| {
|
.map(|ty| {
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
})
|
})
|
||||||
.collect::<Box<[_]>>()
|
.collect::<Box<[_]>>()
|
||||||
};
|
};
|
||||||
let tuple_inner = match self.tuple_inner(db) {
|
let tuple_inner = match self.tuple_inner(db) {
|
||||||
Some(tuple) => Some(tuple.recursive_type_normalized_impl(db, div, nested, visitor)?),
|
Some(tuple) => Some(tuple.recursive_type_normalized_impl(db, div, nested)?),
|
||||||
None => None,
|
None => None,
|
||||||
};
|
};
|
||||||
let context = self.generic_context(db);
|
let context = self.generic_context(db);
|
||||||
|
|
|
||||||
|
|
@ -379,16 +379,15 @@ impl<'db> NominalInstanceType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self.0 {
|
match self.0 {
|
||||||
NominalInstanceInner::ExactTuple(tuple) => {
|
NominalInstanceInner::ExactTuple(tuple) => {
|
||||||
Some(Self(NominalInstanceInner::ExactTuple(
|
Some(Self(NominalInstanceInner::ExactTuple(
|
||||||
tuple.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
tuple.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)))
|
)))
|
||||||
}
|
}
|
||||||
NominalInstanceInner::NonTuple(class) => Some(Self(NominalInstanceInner::NonTuple(
|
NominalInstanceInner::NonTuple(class) => Some(Self(NominalInstanceInner::NonTuple(
|
||||||
class.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
class.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))),
|
))),
|
||||||
NominalInstanceInner::Object => Some(Self(NominalInstanceInner::Object)),
|
NominalInstanceInner::Object => Some(Self(NominalInstanceInner::Object)),
|
||||||
}
|
}
|
||||||
|
|
@ -750,12 +749,9 @@ impl<'db> ProtocolInstanceType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self {
|
Some(Self {
|
||||||
inner: self
|
inner: self.inner.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
.inner
|
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
|
||||||
_phantom: PhantomData,
|
_phantom: PhantomData,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
@ -877,14 +873,13 @@ impl<'db> Protocol<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self {
|
match self {
|
||||||
Self::FromClass(class) => Some(Self::FromClass(
|
Self::FromClass(class) => Some(Self::FromClass(
|
||||||
class.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
class.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
Self::Synthesized(synthesized) => Some(Self::Synthesized(
|
Self::Synthesized(synthesized) => Some(Self::Synthesized(
|
||||||
synthesized.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
synthesized.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -963,11 +958,9 @@ mod synthesized_protocol {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self(
|
Some(Self(
|
||||||
self.0
|
self.0.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -150,11 +150,9 @@ impl<'db> ProtocolClass<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self(
|
Some(Self(
|
||||||
self.0
|
self.0.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -386,7 +384,6 @@ impl<'db> ProtocolInterface<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self::new(
|
Some(Self::new(
|
||||||
db,
|
db,
|
||||||
|
|
@ -395,7 +392,7 @@ impl<'db> ProtocolInterface<'db> {
|
||||||
.map(|(name, data)| {
|
.map(|(name, data)| {
|
||||||
Some((
|
Some((
|
||||||
name.clone(),
|
name.clone(),
|
||||||
data.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
data.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))
|
))
|
||||||
})
|
})
|
||||||
.collect::<Option<BTreeMap<_, _>>>()?,
|
.collect::<Option<BTreeMap<_, _>>>()?,
|
||||||
|
|
@ -498,21 +495,20 @@ impl<'db> ProtocolMemberData<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self {
|
Some(Self {
|
||||||
kind: match &self.kind {
|
kind: match &self.kind {
|
||||||
ProtocolMemberKind::Method(callable) => ProtocolMemberKind::Method(
|
ProtocolMemberKind::Method(callable) => ProtocolMemberKind::Method(
|
||||||
callable.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
callable.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
),
|
),
|
||||||
ProtocolMemberKind::Property(property) => ProtocolMemberKind::Property(
|
ProtocolMemberKind::Property(property) => ProtocolMemberKind::Property(
|
||||||
property.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
property.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
),
|
|
||||||
ProtocolMemberKind::Other(ty) if nested => ProtocolMemberKind::Other(
|
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)?,
|
|
||||||
),
|
),
|
||||||
|
ProtocolMemberKind::Other(ty) if nested => {
|
||||||
|
ProtocolMemberKind::Other(ty.recursive_type_normalized_impl(db, div, true)?)
|
||||||
|
}
|
||||||
ProtocolMemberKind::Other(ty) => ProtocolMemberKind::Other(
|
ProtocolMemberKind::Other(ty) => ProtocolMemberKind::Other(
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
|
|
|
||||||
|
|
@ -179,13 +179,12 @@ impl<'db> CallableSignature<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self {
|
Some(Self {
|
||||||
overloads: self
|
overloads: self
|
||||||
.overloads
|
.overloads
|
||||||
.iter()
|
.iter()
|
||||||
.map(|signature| signature.recursive_type_normalized_impl(db, div, nested, visitor))
|
.map(|signature| signature.recursive_type_normalized_impl(db, div, nested))
|
||||||
.collect::<Option<SmallVec<_>>>()?,
|
.collect::<Option<SmallVec<_>>>()?,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
@ -575,15 +574,14 @@ impl<'db> Signature<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
let return_ty = match self.return_ty {
|
let return_ty = match self.return_ty {
|
||||||
Some(return_ty) if nested => {
|
Some(return_ty) if nested => {
|
||||||
Some(return_ty.recursive_type_normalized_impl(db, div, true, visitor)?)
|
Some(return_ty.recursive_type_normalized_impl(db, div, true)?)
|
||||||
}
|
}
|
||||||
Some(return_ty) => Some(
|
Some(return_ty) => Some(
|
||||||
return_ty
|
return_ty
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
None => None,
|
None => None,
|
||||||
|
|
@ -591,7 +589,7 @@ impl<'db> Signature<'db> {
|
||||||
let parameters = {
|
let parameters = {
|
||||||
let mut parameters = Vec::with_capacity(self.parameters.len());
|
let mut parameters = Vec::with_capacity(self.parameters.len());
|
||||||
for param in &self.parameters {
|
for param in &self.parameters {
|
||||||
parameters.push(param.recursive_type_normalized_impl(db, div, nested, visitor)?);
|
parameters.push(param.recursive_type_normalized_impl(db, div, nested)?);
|
||||||
}
|
}
|
||||||
Parameters::new(db, parameters)
|
Parameters::new(db, parameters)
|
||||||
};
|
};
|
||||||
|
|
@ -1906,7 +1904,6 @@ impl<'db> Parameter<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
let Parameter {
|
let Parameter {
|
||||||
annotated_type,
|
annotated_type,
|
||||||
|
|
@ -1916,9 +1913,9 @@ impl<'db> Parameter<'db> {
|
||||||
} = self;
|
} = self;
|
||||||
|
|
||||||
let annotated_type = match annotated_type {
|
let annotated_type = match annotated_type {
|
||||||
Some(ty) if nested => Some(ty.recursive_type_normalized_impl(db, div, true, visitor)?),
|
Some(ty) if nested => Some(ty.recursive_type_normalized_impl(db, div, true)?),
|
||||||
Some(ty) => Some(
|
Some(ty) => Some(
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
None => None,
|
None => None,
|
||||||
|
|
@ -1928,11 +1925,9 @@ impl<'db> Parameter<'db> {
|
||||||
ParameterKind::PositionalOnly { name, default_type } => ParameterKind::PositionalOnly {
|
ParameterKind::PositionalOnly { name, default_type } => ParameterKind::PositionalOnly {
|
||||||
name: name.clone(),
|
name: name.clone(),
|
||||||
default_type: match default_type {
|
default_type: match default_type {
|
||||||
Some(ty) if nested => {
|
Some(ty) if nested => Some(ty.recursive_type_normalized_impl(db, div, true)?),
|
||||||
Some(ty.recursive_type_normalized_impl(db, div, true, visitor)?)
|
|
||||||
}
|
|
||||||
Some(ty) => Some(
|
Some(ty) => Some(
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
None => None,
|
None => None,
|
||||||
|
|
@ -1943,10 +1938,10 @@ impl<'db> Parameter<'db> {
|
||||||
name: name.clone(),
|
name: name.clone(),
|
||||||
default_type: match default_type {
|
default_type: match default_type {
|
||||||
Some(ty) if nested => {
|
Some(ty) if nested => {
|
||||||
Some(ty.recursive_type_normalized_impl(db, div, true, visitor)?)
|
Some(ty.recursive_type_normalized_impl(db, div, true)?)
|
||||||
}
|
}
|
||||||
Some(ty) => Some(
|
Some(ty) => Some(
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
None => None,
|
None => None,
|
||||||
|
|
@ -1956,11 +1951,9 @@ impl<'db> Parameter<'db> {
|
||||||
ParameterKind::KeywordOnly { name, default_type } => ParameterKind::KeywordOnly {
|
ParameterKind::KeywordOnly { name, default_type } => ParameterKind::KeywordOnly {
|
||||||
name: name.clone(),
|
name: name.clone(),
|
||||||
default_type: match default_type {
|
default_type: match default_type {
|
||||||
Some(ty) if nested => {
|
Some(ty) if nested => Some(ty.recursive_type_normalized_impl(db, div, true)?),
|
||||||
Some(ty.recursive_type_normalized_impl(db, div, true, visitor)?)
|
|
||||||
}
|
|
||||||
Some(ty) => Some(
|
Some(ty) => Some(
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div),
|
.unwrap_or(div),
|
||||||
),
|
),
|
||||||
None => None,
|
None => None,
|
||||||
|
|
|
||||||
|
|
@ -272,12 +272,11 @@ impl<'db> SubclassOfType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self {
|
Some(Self {
|
||||||
subclass_of: self
|
subclass_of: self
|
||||||
.subclass_of
|
.subclass_of
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -449,11 +448,10 @@ impl<'db> SubclassOfInner<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self {
|
match self {
|
||||||
Self::Class(class) => Some(Self::Class(
|
Self::Class(class) => Some(Self::Class(
|
||||||
class.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
class.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
Self::Dynamic(dynamic) => Some(Self::Dynamic(dynamic.recursive_type_normalized())),
|
Self::Dynamic(dynamic) => Some(Self::Dynamic(dynamic.recursive_type_normalized())),
|
||||||
Self::TypeVar(_) => Some(self),
|
Self::TypeVar(_) => Some(self),
|
||||||
|
|
|
||||||
|
|
@ -234,12 +234,11 @@ impl<'db> TupleType<'db> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
Some(Self::new_internal(
|
Some(Self::new_internal(
|
||||||
db,
|
db,
|
||||||
self.tuple(db)
|
self.tuple(db)
|
||||||
.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -411,13 +410,12 @@ impl<'db> FixedLengthTuple<Type<'db>> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
if nested {
|
if nested {
|
||||||
Some(Self::from_elements(
|
Some(Self::from_elements(
|
||||||
self.0
|
self.0
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| ty.recursive_type_normalized_impl(db, div, true, visitor))
|
.map(|ty| ty.recursive_type_normalized_impl(db, div, true))
|
||||||
.collect::<Option<Box<[_]>>>()?,
|
.collect::<Option<Box<[_]>>>()?,
|
||||||
))
|
))
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -425,7 +423,7 @@ impl<'db> FixedLengthTuple<Type<'db>> {
|
||||||
self.0
|
self.0
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| {
|
.map(|ty| {
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
})
|
})
|
||||||
.collect::<Box<[_]>>(),
|
.collect::<Box<[_]>>(),
|
||||||
|
|
@ -804,18 +802,17 @@ impl<'db> VariableLengthTuple<Type<'db>> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
let prefix = if nested {
|
let prefix = if nested {
|
||||||
self.prefix
|
self.prefix
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| ty.recursive_type_normalized_impl(db, div, true, visitor))
|
.map(|ty| ty.recursive_type_normalized_impl(db, div, true))
|
||||||
.collect::<Option<Box<_>>>()?
|
.collect::<Option<Box<_>>>()?
|
||||||
} else {
|
} else {
|
||||||
self.prefix
|
self.prefix
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| {
|
.map(|ty| {
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
})
|
})
|
||||||
.collect::<Box<_>>()
|
.collect::<Box<_>>()
|
||||||
|
|
@ -823,23 +820,23 @@ impl<'db> VariableLengthTuple<Type<'db>> {
|
||||||
let suffix = if nested {
|
let suffix = if nested {
|
||||||
self.suffix
|
self.suffix
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| ty.recursive_type_normalized_impl(db, div, true, visitor))
|
.map(|ty| ty.recursive_type_normalized_impl(db, div, true))
|
||||||
.collect::<Option<Box<_>>>()?
|
.collect::<Option<Box<_>>>()?
|
||||||
} else {
|
} else {
|
||||||
self.suffix
|
self.suffix
|
||||||
.iter()
|
.iter()
|
||||||
.map(|ty| {
|
.map(|ty| {
|
||||||
ty.recursive_type_normalized_impl(db, div, true, visitor)
|
ty.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
})
|
})
|
||||||
.collect::<Box<_>>()
|
.collect::<Box<_>>()
|
||||||
};
|
};
|
||||||
let variable = if nested {
|
let variable = if nested {
|
||||||
self.variable
|
self.variable
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)?
|
.recursive_type_normalized_impl(db, div, true)?
|
||||||
} else {
|
} else {
|
||||||
self.variable
|
self.variable
|
||||||
.recursive_type_normalized_impl(db, div, true, visitor)
|
.recursive_type_normalized_impl(db, div, true)
|
||||||
.unwrap_or(div)
|
.unwrap_or(div)
|
||||||
};
|
};
|
||||||
Some(Self {
|
Some(Self {
|
||||||
|
|
@ -1250,14 +1247,13 @@ impl<'db> Tuple<Type<'db>> {
|
||||||
db: &'db dyn Db,
|
db: &'db dyn Db,
|
||||||
div: Type<'db>,
|
div: Type<'db>,
|
||||||
nested: bool,
|
nested: bool,
|
||||||
visitor: &NormalizedVisitor<'db>,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
match self {
|
match self {
|
||||||
Tuple::Fixed(tuple) => Some(Tuple::Fixed(
|
Tuple::Fixed(tuple) => Some(Tuple::Fixed(
|
||||||
tuple.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
tuple.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
Tuple::Variable(tuple) => Some(Tuple::Variable(
|
Tuple::Variable(tuple) => Some(Tuple::Variable(
|
||||||
tuple.recursive_type_normalized_impl(db, div, nested, visitor)?,
|
tuple.recursive_type_normalized_impl(db, div, nested)?,
|
||||||
)),
|
)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue