Skip to content

Commit

Permalink
fix: dont map to read only dictionaries (#285)
Browse files Browse the repository at this point in the history
  • Loading branch information
latonz authored Mar 17, 2023
1 parent 60cfc38 commit dce4b42
Show file tree
Hide file tree
Showing 4 changed files with 49 additions and 6 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,9 @@ public static class DictionaryMappingBuilder
return null;
}

if (!ctx.Target.ImplementsGeneric(ctx.Types.IDictionary, out _))
return null;

return new ForEachSetDictionaryMapping(
ctx.Source,
ctx.Target,
Expand All @@ -54,6 +57,9 @@ public static class DictionaryMappingBuilder

public static IExistingTargetMapping? TryBuildExistingTargetMapping(MappingBuilderContext ctx)
{
if (!ctx.Target.ImplementsGeneric(ctx.Types.IDictionary, out _))
return null;

if (BuildKeyValueMapping(ctx) is not var (keyMapping, valueMapping))
return null;

Expand Down
37 changes: 37 additions & 0 deletions test/Riok.Mapperly.Tests/Mapping/DictionaryTest.cs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
using Riok.Mapperly.Diagnostics;

namespace Riok.Mapperly.Tests.Mapping;

[UsesVerify]
Expand Down Expand Up @@ -229,4 +231,39 @@ public Task DictionaryToCustomDictionaryWithPrivateCtorShouldDiagnostic()
"class A : Dictionary<string, int> { private A(){} }");
return TestHelper.VerifyGenerator(source);
}

[Fact]
public void ReadOnlyDictionaryToCustomTypeReadOnlyReadOnlyDictionaryShouldIgnore()
{
var source = TestSourceBuilder.Mapping(
"IReadOnlyDictionary<string, string>",
"A",
"class A : IReadOnlyDictionary<int, int> {}");
TestHelper.GenerateMapper(source, TestHelperOptions.AllowDiagnostics)
.Should()
.HaveDiagnostic(new(DiagnosticDescriptors.CannotMapToReadOnlyProperty))
.HaveMapMethodBody(
"""
var target = new A();
return target;
""");
}

[Fact]
public void ReadOnlyDictionaryToReadOnlyDictionaryExistingInstanceShouldIgnore()
{
var source = TestSourceBuilder.Mapping(
"A",
"B",
"class A { public IReadOnlyDictionary<string, string> Values { get; } }",
"class B { public IReadOnlyDictionary<string, string> Values { get; } }");
TestHelper.GenerateMapper(source, TestHelperOptions.AllowDiagnostics)
.Should()
.HaveDiagnostic(new(DiagnosticDescriptors.CannotMapToReadOnlyProperty))
.HaveSingleMethodBody(
"""
var target = new B();
return target;
""");
}
}
2 changes: 1 addition & 1 deletion test/Riok.Mapperly.Tests/Mapping/ObjectPropertyTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -225,7 +225,7 @@ public Task WithManualMappedNotFoundTargetPropertyShouldDiagnostic()
public Task WithManualMappedNotFoundSourcePropertyShouldDiagnostic()
{
var source = TestSourceBuilder.MapperWithBodyAndTypes(
"[MapProperty(\"A.StringValue9\", nameof(B.StringValue2)] partial B Map(A source);",
"[MapProperty(\"StringValue9\", nameof(B.StringValue2)] partial B Map(A source);",
"class A { public string StringValue { get; set; } }",
"class B { public string StringValue2 { get; set; } }");

Expand Down
Original file line number Diff line number Diff line change
@@ -1,28 +1,28 @@
{
{
Diagnostics: [
{
Id: RMG006,
Title: Mapping source property not found,
Severity: Error,
WarningLevel: 0,
Location: : (11,4)-(11,83),
Location: : (11,4)-(11,81),
Description: ,
HelpLink: ,
MessageFormat: Specified property {0} on source type {1} was not found,
Message: Specified property A.StringValue9 on source type A was not found,
Message: Specified property StringValue9 on source type A was not found,
Category: Mapper
},
{
Id: RMG020,
Title: Source property is not mapped to any target property,
Severity: Info,
WarningLevel: 1,
Location: : (11,4)-(11,83),
Location: : (11,4)-(11,81),
Description: ,
HelpLink: ,
MessageFormat: The property {0} on the mapping source type {1} is not mapped to any property on the mapping target type {2},
Message: The property StringValue on the mapping source type A is not mapped to any property on the mapping target type B,
Category: Mapper
}
]
}
}

0 comments on commit dce4b42

Please sign in to comment.