Skip to content
This repository has been archived by the owner on Jan 16, 2022. It is now read-only.

Commit

Permalink
Fix calculating properties visibility which come from external library
Browse files Browse the repository at this point in the history
  • Loading branch information
cezarypiatek committed Oct 21, 2018
1 parent 94e5909 commit b472faf
Show file tree
Hide file tree
Showing 9 changed files with 321 additions and 2 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@

<ItemGroup>
<PackageReference Include="Appveyor.TestLogger" Version="2.0.0" />
<PackageReference Include="Microsoft.AspNet.Identity.EntityFramework" Version="2.2.2" />
<PackageReference Include="Microsoft.CodeAnalysis.CSharp.Workspaces" Version="2.8.2" />
<PackageReference Include="Microsoft.CodeAnalysis.VisualBasic.Workspaces" Version="2.8.2" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.3.0" />
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
Expand Up @@ -226,4 +226,16 @@
<data name="_018_CollectionMappingWithPostfixGenericNameInSingular_FIXED" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>TestCaseData\018_CollectionMappingWithPostfixGenericNameInSingular_FIXED.txt;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8</value>
</data>
<data name="_019_MappingPropertiesInheritedFromLibraryClass" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>TestCaseData\019_MappingPropertiesInheritedFromLibraryClass.txt;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8</value>
</data>
<data name="_019_MappingPropertiesInheritedFromLibraryClass_FIXED" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>TestCaseData\019_MappingPropertiesInheritedFromLibraryClass_FIXED.txt;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8</value>
</data>
<data name="_020_MappingPropertiesInConstructorInheritedFromLibraryClass" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>TestCaseData\020_MappingPropertiesInConstructorInheritedFromLibraryClass.txt;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8</value>
</data>
<data name="_020_MappingPropertiesInConstructorInheritedFromLibraryClass_FIXED" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>TestCaseData\020_MappingPropertiesInConstructorInheritedFromLibraryClass_FIXED.txt;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8</value>
</data>
</root>
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
using Microsoft.CodeAnalysis;
using System.Collections.Immutable;
using Microsoft.AspNet.Identity.EntityFramework;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.CodeRefactorings;
using NUnit.Framework;
using RoslynNUnitLight;
Expand Down Expand Up @@ -120,11 +122,28 @@ public void should_be_able_to_generate_collection_mapping_with_lambda_parameter_
TestCodeRefactoring(_018_CollectionMappingWithPostfixGenericNameInSingular, _018_CollectionMappingWithPostfixGenericNameInSingular_FIXED);
}

[Test]
public void should_be_able_to_map_properties_inherited_from_class_declared_in_external_library()
{
TestCodeRefactoring(_019_MappingPropertiesInheritedFromLibraryClass, _019_MappingPropertiesInheritedFromLibraryClass_FIXED);
}

[Test]
public void should_be_able_to_map_properties_inside_constructor_inherited_from_class_declared_in_external_library()
{
TestCodeRefactoring(_020_MappingPropertiesInConstructorInheritedFromLibraryClass, _020_MappingPropertiesInConstructorInheritedFromLibraryClass_FIXED);
}

protected override string LanguageName => LanguageNames.CSharp;

protected override CodeRefactoringProvider CreateProvider()
{
return new MappingGeneratorRefactoring();
}

protected override ImmutableList<MetadataReference> References { get => new MetadataReference[]
{
MetadataReference.CreateFromFile(typeof(IdentityUser).Assembly.Location)
}.ToImmutableList();}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
using Microsoft.AspNet.Identity.EntityFramework;
using System;

namespace TestAutoMapper
{
public static class ExternalUserTest
{
public static ApplicationUserEntity [|ToEntity|](this UserModel model)
{
throw new NotImplementedException();
}
}

public class UserModel
{
public string NewProperty1 { get; set; }
public string NewProperty2 { get; set; }

public virtual string Email { get; set; }

public virtual bool EmailConfirmed { get; set; }

public virtual string PasswordHash { get; set; }

public virtual string SecurityStamp { get; set; }

public virtual string PhoneNumber { get; set; }
public virtual bool PhoneNumberConfirmed { get; set; }

}

public class ApplicationUserEntity: IdentityUser
{
public string NewProperty1 { get; set; }
public string NewProperty2 { get; set; }
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
using Microsoft.AspNet.Identity.EntityFramework;
using System;

namespace TestAutoMapper
{
public static class ExternalUserTest
{
public static ApplicationUserEntity ToEntity(this UserModel model)
{
return new ApplicationUserEntity()
{
NewProperty1 = model.NewProperty1,
NewProperty2 = model.NewProperty2,
Email = model.Email,
EmailConfirmed = model.EmailConfirmed,
PasswordHash = model.PasswordHash,
SecurityStamp = model.SecurityStamp,
PhoneNumber = model.PhoneNumber,
PhoneNumberConfirmed = model.PhoneNumberConfirmed
};
}
}

public class UserModel
{
public string NewProperty1 { get; set; }
public string NewProperty2 { get; set; }

public virtual string Email { get; set; }

public virtual bool EmailConfirmed { get; set; }

public virtual string PasswordHash { get; set; }

public virtual string SecurityStamp { get; set; }

public virtual string PhoneNumber { get; set; }
public virtual bool PhoneNumberConfirmed { get; set; }

}

public class ApplicationUserEntity: IdentityUser
{
public string NewProperty1 { get; set; }
public string NewProperty2 { get; set; }
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
using Microsoft.AspNet.Identity.EntityFramework;
using System;

namespace TestAutoMapper
{
public class UserModel
{
public string NewProperty1 { get; set; }
public string NewProperty2 { get; set; }

public virtual string Email { get; set; }

public virtual bool EmailConfirmed { get; set; }

public virtual string PasswordHash { get; set; }

public virtual string SecurityStamp { get; set; }

public virtual string PhoneNumber { get; set; }
public virtual bool PhoneNumberConfirmed { get; set; }

}

public class ApplicationUserEntity: IdentityUser
{
public string NewProperty1 { get; set; }
public string NewProperty2 { get; set; }

public [|ApplicationUserEntity|](UserModel model)
{
throw new NotImplementedException();
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
using Microsoft.AspNet.Identity.EntityFramework;
using System;

namespace TestAutoMapper
{
public class UserModel
{
public string NewProperty1 { get; set; }
public string NewProperty2 { get; set; }

public virtual string Email { get; set; }

public virtual bool EmailConfirmed { get; set; }

public virtual string PasswordHash { get; set; }

public virtual string SecurityStamp { get; set; }

public virtual string PhoneNumber { get; set; }
public virtual bool PhoneNumberConfirmed { get; set; }

}

public class ApplicationUserEntity: IdentityUser
{
public string NewProperty1 { get; set; }
public string NewProperty2 { get; set; }

public ApplicationUserEntity(UserModel model)
{
NewProperty1 = model.NewProperty1;
NewProperty2 = model.NewProperty2;
Email = model.Email;
EmailConfirmed = model.EmailConfirmed;
PasswordHash = model.PasswordHash;
SecurityStamp = model.SecurityStamp;
PhoneNumber = model.PhoneNumber;
PhoneNumberConfirmed = model.PhoneNumberConfirmed;
}
}
}
21 changes: 21 additions & 0 deletions MappingGenerator/MappingGenerator/MappingGenerator/SymbolHelper.cs
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,13 @@ public static bool CanBeSetPrivately(this IPropertySymbol property)

public static bool CanBeSetPublicly(this IPropertySymbol property, bool isInternalAccessible)
{
if (IsDeclaredOutsideTheSourcecode(property))
{
return property.IsReadOnly == false &&
property.SetMethod != null &&
property.SetMethod.DeclaredAccessibility == Accessibility.Public;
}

var propertyDeclaration = property.DeclaringSyntaxReferences.Select(x => x.GetSyntax()).OfType<PropertyDeclarationSyntax>().FirstOrDefault();
if (propertyDeclaration?.AccessorList == null)
{
Expand All @@ -92,6 +99,15 @@ public static bool CanBeSetPublicly(this IPropertySymbol property, bool isIntern

public static bool CanBeSetOnlyFromConstructor(this IPropertySymbol property)
{
if (IsDeclaredOutsideTheSourcecode(property))
{
return property.IsReadOnly ||
(property.SetMethod != null &&
new[] {Accessibility.Public, Accessibility.Protected}.Contains(property.SetMethod.DeclaredAccessibility)
);
}


var propertyDeclaration = property.DeclaringSyntaxReferences.Select(x => x.GetSyntax()).OfType<PropertyDeclarationSyntax>().FirstOrDefault();
if (propertyDeclaration?.AccessorList == null)
{
Expand All @@ -106,6 +122,11 @@ public static bool CanBeSetOnlyFromConstructor(this IPropertySymbol property)
return propertyDeclaration.AccessorList.Accessors.Count == 1 && propertyDeclaration.AccessorList.Accessors.SingleOrDefault(IsAutoGetter) != null;
}

private static bool IsDeclaredOutsideTheSourcecode(IPropertySymbol property)
{
return property.DeclaringSyntaxReferences.Length == 0;
}

private static bool HasPrivateSetter(PropertyDeclarationSyntax propertyDeclaration)
{
return propertyDeclaration.AccessorList.Accessors.Any(x =>x.Keyword.Kind() == SyntaxKind.SetKeyword && x.Modifiers.Any(m => m.Kind() == SyntaxKind.PrivateKeyword));
Expand Down

0 comments on commit b472faf

Please sign in to comment.