diff options
| -rw-r--r-- | src/lib.rs | 12 | ||||
| -rw-r--r-- | src/transform.rs | 28 | ||||
| -rw-r--r-- | ui-tests/src/bin/qualified_self_opt.rs | 10 | ||||
| -rw-r--r-- | ui-tests/src/bin/qualified_self_opt.stderr | 5 | 
4 files changed, 40 insertions, 15 deletions
| @@ -373,7 +373,17 @@ fn generate_blanket_impl(  }  fn path_is_assoc_type(path: &TypePath) -> bool { -    path.path.segments[0].ident == "Self" +    if path.path.segments[0].ident == "Self" { +        return true; +    } +    if let Some(qself) = &path.qself { +        if let Type::Path(path) = qself.ty.as_ref() { +            if path.path.segments[0].ident == "Self" { +                return true; +            } +        } +    } +    false  }  fn match_assoc_type(item: &Type) -> bool { diff --git a/src/transform.rs b/src/transform.rs index 39d3cab..74ab9e6 100644 --- a/src/transform.rs +++ b/src/transform.rs @@ -3,14 +3,13 @@ use std::collections::HashMap;  use proc_macro2::Span;  use quote::quote;  use syn::{ -    spanned::Spanned, GenericArgument, Generics, Ident, PathArguments, QSelf, TraitBound, Type, +    spanned::Spanned, GenericArgument, Generics, Ident, PathArguments, TraitBound, Type,      TypeParamBound, TypePath, TypeReference, TypeTraitObject, WherePredicate,  };  use crate::{      filter_map_assoc_paths, match_assoc_type,      parse_assoc_type::{BoxType, DestType}, -    path_is_assoc_type,      syn_utils::{iter_path, iter_type, type_arguments_mut},      trait_sig::{MethodError, TypeTransform},  }; @@ -59,17 +58,6 @@ impl TypeConverter<'_> {      }      pub fn convert_type(&self, type_: &mut Type) -> Result<TypeTransform, (Span, TransformError)> { -        if let Type::Path(TypePath { -            qself: Some(QSelf { ty, .. }), -            .. -        }) = type_ -        { -            if let Type::Path(path) = ty.as_ref() { -                if path_is_assoc_type(path) { -                    return Err((path.span(), TransformError::QualifiedSelfAssociatedType)); -                } -            } -        }          if !iter_type(type_).any(match_assoc_type) {              return Ok(TypeTransform::NoOp);          } @@ -125,7 +113,19 @@ impl TypeConverter<'_> {              }          } -        if let Type::Path(TypePath { path, qself: None }) = type_ { +        if let Type::Path(TypePath { +            qself: Some(qself), .. +        }) = type_ +        { +            if let Type::Path(self_path) = qself.ty.as_ref() { +                if self_path.path.segments[0].ident == "Self" { +                    return Err(( +                        self_path.span(), +                        TransformError::QualifiedSelfAssociatedType, +                    )); +                } +            } +        } else if let Type::Path(TypePath { path, qself: None }) = type_ {              if path.segments[0].ident == "Self" {                  if path.segments.len() == 2 {                      let ident = &path.segments.last().unwrap().ident; diff --git a/ui-tests/src/bin/qualified_self_opt.rs b/ui-tests/src/bin/qualified_self_opt.rs new file mode 100644 index 0000000..5de8b71 --- /dev/null +++ b/ui-tests/src/bin/qualified_self_opt.rs @@ -0,0 +1,10 @@ +trait Foo { +    type X: Into<String>; +} + +#[dynamize::dynamize] +trait Bar: Foo { +    fn test(&self) -> Option<<Self as Foo>::X>; +} + +fn main() {} diff --git a/ui-tests/src/bin/qualified_self_opt.stderr b/ui-tests/src/bin/qualified_self_opt.stderr new file mode 100644 index 0000000..e032be5 --- /dev/null +++ b/ui-tests/src/bin/qualified_self_opt.stderr @@ -0,0 +1,5 @@ +error: dynamize does not support associated types of a qualified Self + --> src/bin/qualified_self_opt.rs:7:31 +  | +7 |     fn test(&self) -> Option<<Self as Foo>::X>; +  |                               ^^^^ | 
