Skip to content

Commit 8c2275f

Browse files
committed
fix select of auto generated properties.
1 parent a5508a7 commit 8c2275f

7 files changed

Lines changed: 85 additions & 9 deletions

File tree

src/RoyalCode.SmartSelector.Demo/Generated/RoyalCode.SmartSelector.Generators/RoyalCode.SmartSelector.Generators.IncrementalGenerator/BookDetails.g.cs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,13 @@ public partial class BookDetails
99

1010
public static Expression<Func<Book, BookDetails>> SelectBookExpression { get; } = a => new BookDetails
1111
{
12-
Id = a.Id
12+
Id = a.Id,
13+
Title = a.Title,
14+
Author = a.Author,
15+
PublishedDate = a.PublishedDate,
16+
ISBN = a.ISBN,
17+
Price = a.Price,
18+
InStock = a.InStock
1319
};
1420

1521
public static BookDetails From(Book book) => (selectBookFunc ??= SelectBookExpression.Compile())(book);

src/RoyalCode.SmartSelector.Generators/Generators/AutoPropertiesGenerator.cs

Lines changed: 37 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5,12 +5,27 @@ namespace RoyalCode.SmartSelector.Generators.Generators;
55

66
internal static class AutoPropertiesGenerator
77
{
8+
public const string AutoPropertiesAttributeTypedFullName = "RoyalCode.SmartSelector.AutoPropertiesAttribute`1";
9+
810
internal static MatchOptions MatchOptions { get; } = new()
911
{
1012
OriginPropertiesRetriever = new AutoPropertyOriginPropertiesRetriever(),
1113
//TargetPropertiesRetriever = new AutoPropertyTargetPropertiesRetriever(),
1214
};
1315

16+
internal static bool Predicate(SyntaxNode node, CancellationToken token)
17+
{
18+
var accept = node is ClassDeclarationSyntax;
19+
return accept;
20+
}
21+
22+
internal static AutoPropertiesInformation Transform(
23+
GeneratorAttributeSyntaxContext context, CancellationToken token)
24+
{
25+
// ainda não implementado
26+
return new(null, null);
27+
}
28+
1429
internal static AutoPropertiesInformation CreateInformation(
1530
TypeDescriptor modelType,
1631
TypeDescriptor fromType,
@@ -195,10 +210,16 @@ internal static void Generate(AutoPropertiesInformation propertiesInfo, SourcePr
195210
partialClass.FileName = $"{origin.Name}.AutoProperties.g.cs";
196211
partialClass.Generate(context);
197212
}
213+
214+
198215
}
199216

200217
internal class AutoPropertyOriginPropertiesRetriever : IOriginPropertiesRetriever
201218
{
219+
private const string AutoSelectAttributeName = "AutoSelectAttribute";
220+
private const string AutoPropertiesAttributeName = "AutoPropertiesAttribute";
221+
private const string TypedAutoPropertiesAttributeName = "AutoPropertiesAttribute<";
222+
202223
public IReadOnlyList<PropertyDescriptor> GetProperties(TypeDescriptor origin)
203224
{
204225
var typeSymbol = origin.Symbol;
@@ -208,17 +229,23 @@ public IReadOnlyList<PropertyDescriptor> GetProperties(TypeDescriptor origin)
208229
// Verifica se no type existe:
209230
// - o AutoPropertiesAttribute com AutoSelectAttribute<TFrom>
210231
// - ou AutoPropertiesAttribute<TFrom>
211-
var atrributes = typeSymbol.GetAttributes();
232+
var attributes = typeSymbol.GetAttributes();
212233

213234
// obtém o AutoPropertiesAttribute
214-
var autoPropertiesAttribute = atrributes.FirstOrDefault(
215-
attr => attr.AttributeClass?.ToDisplayString() == "RoyalCode.SmartSelector.AutoPropertiesAttribute");
235+
var autoPropertiesAttribute = attributes.FirstOrDefault(attr =>
236+
{
237+
var attrName = attr.AttributeClass?.ToDisplayString(SymbolDisplayFormat.MinimallyQualifiedFormat);
238+
return attrName == AutoPropertiesAttributeName;
239+
});
216240

217241
if (autoPropertiesAttribute is not null)
218242
{
219243
// quando tem AutoPropertiesAttribute, deve ter o AutoSelectAttribute<TFrom>
220-
var autoSelectAttribute = atrributes.FirstOrDefault(
221-
attr => attr.AttributeClass?.ToDisplayString() == "RoyalCode.SmartSelector.AutoSelectAttribute`1");
244+
var autoSelectAttribute = attributes.FirstOrDefault(attr =>
245+
{
246+
var attrName = attr.AttributeClass?.ToDisplayString(SymbolDisplayFormat.MinimallyQualifiedFormat);
247+
return attrName?.StartsWith(AutoSelectAttributeName) ?? false;
248+
});
222249

223250
// se não tiver, retorna o padrão
224251
if (autoSelectAttribute == null)
@@ -237,8 +264,11 @@ public IReadOnlyList<PropertyDescriptor> GetProperties(TypeDescriptor origin)
237264
}
238265

239266
// obtém o AutoPropertiesAttribute<TFrom>
240-
autoPropertiesAttribute = atrributes.FirstOrDefault(
241-
attr => attr.AttributeClass?.ToDisplayString() == "RoyalCode.SmartSelector.AutoPropertiesAttribute`1");
267+
autoPropertiesAttribute = attributes.FirstOrDefault(attr =>
268+
{
269+
var attrName = attr.AttributeClass?.ToDisplayString(SymbolDisplayFormat.MinimallyQualifiedFormat);
270+
return attrName?.StartsWith(TypedAutoPropertiesAttributeName) ?? false;
271+
});
242272

243273
if (autoPropertiesAttribute is not null)
244274
{

src/RoyalCode.SmartSelector.Generators/Generators/AutoPropertiesInformation.cs

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
using Microsoft.CodeAnalysis;
2+
using RoyalCode.Extensions.SourceGenerator.Descriptors.PropertySelection;
23

34
namespace RoyalCode.SmartSelector.Generators.Generators;
45

@@ -41,4 +42,20 @@ public bool Equals(AutoPropertiesInformation other)
4142
return diagnostics?.SequenceEqual(other.diagnostics) == true &&
4243
properties?.SequenceEqual(other.properties) == true;
4344
}
45+
46+
internal void Generate(SourceProductionContext context)
47+
{
48+
if (diagnostics is not null)
49+
{
50+
foreach (var diagnostic in diagnostics)
51+
{
52+
context.ReportDiagnostic(diagnostic);
53+
}
54+
}
55+
56+
if (properties is not null && originType is not null)
57+
{
58+
AutoPropertiesGenerator.Generate(this, context);
59+
}
60+
}
4461
}

src/RoyalCode.SmartSelector.Generators/Generators/AutoSelectGenerator.cs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@ internal static class AutoSelectGenerator
99
{
1010
public const string AutoSelectAttributeFullName = "RoyalCode.SmartSelector.AutoSelectAttribute`1";
1111
public const string AutoPropertiesAttributeFullName = "RoyalCode.SmartSelector.AutoPropertiesAttribute";
12-
public const string AutoPropertiesAttributeTypedFullName = "RoyalCode.SmartSelector.AutoPropertiesAttribute`1";
1312

1413
private const string AutoSelectAttributeName = "AutoSelect";
1514
private const string AutoPropertiesAttributeName = "AutoProperties";

src/RoyalCode.SmartSelector.Generators/IncrementalGenerator.cs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,11 +12,21 @@ public class IncrementalGenerator : IIncrementalGenerator
1212
/// <inheritdoc />
1313
public void Initialize(IncrementalGeneratorInitializationContext context)
1414
{
15+
var pipelineProperties = context.SyntaxProvider.ForAttributeWithMetadataName(
16+
fullyQualifiedMetadataName: AutoPropertiesGenerator.AutoPropertiesAttributeTypedFullName,
17+
predicate: AutoPropertiesGenerator.Predicate,
18+
transform: AutoPropertiesGenerator.Transform);
19+
1520
var pipelineSelect = context.SyntaxProvider.ForAttributeWithMetadataName(
1621
fullyQualifiedMetadataName: AutoSelectGenerator.AutoSelectAttributeFullName,
1722
predicate: AutoSelectGenerator.Predicate,
1823
transform: AutoSelectGenerator.Transform);
1924

25+
context.RegisterSourceOutput(pipelineProperties, static (context, model) =>
26+
{
27+
model.Generate(context);
28+
});
29+
2030
context.RegisterSourceOutput(pipelineSelect, static (context, model) =>
2131
{
2232
model.Generate(context);

src/RoyalCode.SmartSelector.Generators/Models/SelectLambdaGenerator.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,9 @@ public override string GetValue(int ident)
2121

2222
private string GetValue(int ident, StringBuilder sb, char param)
2323
{
24+
if (match.PropertyMatches.Count is 0)
25+
return sb.Append(param).Append(" => new ").AppendLine(match.OriginType.Name).Append("()").ToString();
26+
2427
// ......... a => new T
2528
// {
2629
sb.Append(param).Append(" => new ").AppendLine(match.OriginType.Name)

src/RoyalCode.SmartSelector.Tests/Tests/AutoPropertiesTests.cs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,17 @@ public void Should_Generate_All_Public_Properties()
2424
generated.Should().Contain("public List<String> Tags { get; set; }");
2525
// user complex types should NOT be generated
2626
generated.Should().NotContain("public NestedNested NestedNested { get; set; }");
27+
28+
// check the select expression
29+
generated.Should().Contain("a => new Dto");
30+
generated.Should().Contain("Id = a.Id,");
31+
generated.Should().Contain("Name = a.Name,");
32+
generated.Should().Contain("Active = a.Active,");
33+
generated.Should().Contain("CreatedAt = a.CreatedAt,");
34+
generated.Should().Contain("UpdatedAt = a.UpdatedAt,");
35+
generated.Should().Contain("Price = a.Price,");
36+
generated.Should().Contain("Nested = a.Nested,");
37+
generated.Should().Contain("Tags = a.Tags");
2738
}
2839

2940
[Fact]

0 commit comments

Comments
 (0)