Use fully qualified names to reduce namespace clashes. (#68)

* Use fully qualified names to reduce namespace clashes.

* Small code style fixes.

* Make properties in ProxyData immutable.

* Remove clutter by joining TrimEnd() to previous line.

* Introduce Extension method to retrieve ITypeSymbol FullyQualifiedDisplayString

* Fixed some code issues.

* Fixed method call in BaseGenerator

* Refactor metadata name
This commit is contained in:
David
2024-04-28 10:25:50 +02:00
committed by GitHub
parent 68864378d0
commit 39d85588e6
56 changed files with 1123 additions and 1146 deletions
@@ -6,26 +6,33 @@ using ProxyInterfaceSourceGenerator.Models;
namespace ProxyInterfaceSourceGenerator.SyntaxReceiver;
internal class ProxySyntaxReceiver : ISyntaxReceiver
internal class ProxySyntaxReceiver : ISyntaxContextReceiver
{
private static readonly string[] Modifiers = { "public", "partial" };
private const string GlobalPrefix = "global::";
private static readonly string[] GenerateProxyAttributes = { "ProxyInterfaceGenerator.Proxy", "Proxy" };
private static readonly string[] Modifiers = { "public", "partial" };
public IDictionary<InterfaceDeclarationSyntax, ProxyData> CandidateInterfaces { get; } = new Dictionary<InterfaceDeclarationSyntax, ProxyData>();
public void OnVisitSyntaxNode(SyntaxNode syntaxNode)
public void OnVisitSyntaxNode(GeneratorSyntaxContext context)
{
if (syntaxNode is InterfaceDeclarationSyntax interfaceDeclarationSyntax && TryGet(interfaceDeclarationSyntax, out var data))
var syntaxNode = context.Node;
var semanticModel = context.SemanticModel;
if (syntaxNode is InterfaceDeclarationSyntax interfaceDeclarationSyntax && TryGet(interfaceDeclarationSyntax, out var data, semanticModel!))
{
CandidateInterfaces.Add(interfaceDeclarationSyntax, data);
}
}
private static bool TryGet(InterfaceDeclarationSyntax interfaceDeclarationSyntax, [NotNullWhen(true)] out ProxyData? data)
private static string CreateFullInterfaceName(string ns, BaseTypeDeclarationSyntax classDeclarationSyntax)
{
return !string.IsNullOrEmpty(ns) ? $"{ns}.{classDeclarationSyntax.Identifier}" : classDeclarationSyntax.Identifier.ToString();
}
private static bool TryGet(InterfaceDeclarationSyntax interfaceDeclarationSyntax, [NotNullWhen(true)] out ProxyData? data, SemanticModel semanticModel)
{
data = null;
if (interfaceDeclarationSyntax.Modifiers.Select(m => m.ToString()).Except(Modifiers).Count() != 0)
if (interfaceDeclarationSyntax.Modifiers.Select(m => m.ToString()).Except(Modifiers).Any())
{
// InterfaceDeclarationSyntax should be "public" and "partial"
return false;
@@ -38,7 +45,6 @@ internal class ProxySyntaxReceiver : ISyntaxReceiver
return false;
}
var usings = new List<string>();
string ns = interfaceDeclarationSyntax.GetNamespace();
@@ -55,35 +61,25 @@ internal class ProxySyntaxReceiver : ISyntaxReceiver
}
}
var fluentBuilderAttributeArguments = AttributeArgumentListParser.ParseAttributeArguments(attributeList.Attributes.FirstOrDefault()?.ArgumentList);
var fluentBuilderAttributeArguments = AttributeArgumentListParser.ParseAttributeArguments(attributeList.Attributes.FirstOrDefault()?.ArgumentList, semanticModel);
var rawTypeNameAsString = fluentBuilderAttributeArguments.RawTypeName;
data = new ProxyData
{
Namespace = ns,
ShortInterfaceName = interfaceDeclarationSyntax.Identifier.ToString(),
FullInterfaceName = CreateFullInterfaceName(ns, interfaceDeclarationSyntax), // $"{ns}.{interfaceDeclarationSyntax.Identifier}",
FullRawTypeName = rawTypeNameAsString,
ShortTypeName = ConvertTypeName(rawTypeNameAsString).Split('.').Last(),
FullTypeName = ConvertTypeName(rawTypeNameAsString),
Usings = usings,
ProxyBaseClasses = fluentBuilderAttributeArguments.ProxyBaseClasses,
Accessibility = fluentBuilderAttributeArguments.Accessibility
};
var metadataName = fluentBuilderAttributeArguments.MetadataName;
var globalNamespace = string.IsNullOrEmpty(ns) ? string.Empty : $"{GlobalPrefix}{ns}";
var namespaceDot = string.IsNullOrEmpty(ns) ? string.Empty : $"{ns}.";
data = new ProxyData(
@namespace: ns,
namespaceDot: namespaceDot,
shortInterfaceName: interfaceDeclarationSyntax.Identifier.ToString(),
fullInterfaceName: CreateFullInterfaceName(globalNamespace, interfaceDeclarationSyntax), // $"{ns}.{interfaceDeclarationSyntax.Identifier}",
fullQualifiedTypeName: fluentBuilderAttributeArguments.FullyQualifiedDisplayString,
fullMetadataTypeName: metadataName,
shortMetadataTypeName: metadataName.Split('.').Last(),
usings: usings,
proxyBaseClasses: fluentBuilderAttributeArguments.ProxyBaseClasses,
accessibility: fluentBuilderAttributeArguments.Accessibility
);
return true;
}
private static string ConvertTypeName(string typeName)
{
return !(typeName.Contains('<') && typeName.Contains('>')) ?
typeName :
$"{typeName.Replace("<", string.Empty).Replace(">", string.Empty).Replace(",", string.Empty).Trim()}`{typeName.Count(c => c == ',') + 1}";
}
private static string CreateFullInterfaceName(string ns, BaseTypeDeclarationSyntax classDeclarationSyntax)
{
return !string.IsNullOrEmpty(ns) ? $"{ns}.{classDeclarationSyntax.Identifier}" : classDeclarationSyntax.Identifier.ToString();
}
}