ProxyBaseClasses (#27)

This commit is contained in:
Stef Heyenrath
2022-02-01 18:49:01 +01:00
committed by GitHub
parent 649ed89bb6
commit f9664e0564
45 changed files with 1305 additions and 836 deletions
@@ -1,4 +1,3 @@
using System;
using System.Text;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.CSharp;
@@ -6,83 +5,95 @@ using Microsoft.CodeAnalysis.Text;
using ProxyInterfaceSourceGenerator.FileGenerators;
using ProxyInterfaceSourceGenerator.SyntaxReceiver;
namespace ProxyInterfaceSourceGenerator
namespace ProxyInterfaceSourceGenerator;
[Generator]
internal class ProxyInterfaceCodeGenerator : ISourceGenerator
{
[Generator]
internal class ProxyInterfaceCodeGenerator : ISourceGenerator
private readonly ProxyAttributeGenerator _proxyAttributeGenerator = new ProxyAttributeGenerator();
public void Initialize(GeneratorInitializationContext context)
{
private readonly ProxyAttributeGenerator _proxyAttributeGenerator = new ProxyAttributeGenerator();
//if (!System.Diagnostics.Debugger.IsAttached)
//{
// System.Diagnostics.Debugger.Launch();
//}
public void Initialize(GeneratorInitializationContext context)
context.RegisterForSyntaxNotifications(() => new ProxySyntaxReceiver());
}
public void Execute(GeneratorExecutionContext context)
{
if (context.ParseOptions is not CSharpParseOptions csharpParseOptions)
{
//if (!System.Diagnostics.Debugger.IsAttached)
//{
// System.Diagnostics.Debugger.Launch();
//}
context.RegisterForSyntaxNotifications(() => new ProxySyntaxReceiver());
throw new NotSupportedException("Only C# is supported.");
}
public void Execute(GeneratorExecutionContext context)
if (context.SyntaxReceiver is not ProxySyntaxReceiver receiver)
{
if (context.ParseOptions is not CSharpParseOptions csharpParseOptions)
{
throw new NotSupportedException("Only C# is supported.");
}
return;
}
if (context.SyntaxReceiver is not ProxySyntaxReceiver receiver)
{
return;
}
// https://github.com/reactiveui/refit/blob/main/InterfaceStubGenerator.Core/InterfaceStubGenerator.cs
var supportsNullable = csharpParseOptions.LanguageVersion >= LanguageVersion.CSharp8;
// https://github.com/reactiveui/refit/blob/main/InterfaceStubGenerator.Core/InterfaceStubGenerator.cs
var supportsNullable = csharpParseOptions.LanguageVersion >= LanguageVersion.CSharp8;
try
{
GenerateProxyAttribute(context, receiver);
GeneratePartialInterfaces(context, receiver, supportsNullable);
GenerateProxyClasses(context, receiver, supportsNullable);
}
private void GenerateProxyAttribute(GeneratorExecutionContext ctx, ProxySyntaxReceiver receiver)
catch (Exception exception)
{
var context = new Context
{
GeneratorExecutionContext = ctx,
CandidateInterfaces = receiver.CandidateInterfaces
};
var attributeData = _proxyAttributeGenerator.GenerateFile();
context.GeneratorExecutionContext.AddSource(attributeData.FileName, SourceText.From(attributeData.Text, Encoding.UTF8));
GenerateError(context, exception);
}
}
private static void GeneratePartialInterfaces(GeneratorExecutionContext ctx, ProxySyntaxReceiver receiver, bool supportsNullable)
private void GenerateError(GeneratorExecutionContext context, Exception exception)
{
var message = $"/*\r\n{nameof(ProxyInterfaceCodeGenerator)}\r\n\r\n{exception}\r\n*/";
context.AddSource("Error.g", SourceText.From(message, Encoding.UTF8));
}
private void GenerateProxyAttribute(GeneratorExecutionContext ctx, ProxySyntaxReceiver receiver)
{
var context = new Context
{
var context = new Context
{
GeneratorExecutionContext = ctx,
CandidateInterfaces = receiver.CandidateInterfaces
};
GeneratorExecutionContext = ctx,
CandidateInterfaces = receiver.CandidateInterfaces
};
var partialInterfacesGenerator = new PartialInterfacesGenerator(context, supportsNullable);
foreach (var data in partialInterfacesGenerator.GenerateFiles())
{
context.GeneratorExecutionContext.AddSource(data.FileName, SourceText.From(data.Text, Encoding.UTF8));
}
var attributeData = _proxyAttributeGenerator.GenerateFile();
context.GeneratorExecutionContext.AddSource(attributeData.FileName, SourceText.From(attributeData.Text, Encoding.UTF8));
}
private static void GeneratePartialInterfaces(GeneratorExecutionContext ctx, ProxySyntaxReceiver receiver, bool supportsNullable)
{
var context = new Context
{
GeneratorExecutionContext = ctx,
CandidateInterfaces = receiver.CandidateInterfaces
};
var partialInterfacesGenerator = new PartialInterfacesGenerator(context, supportsNullable);
foreach (var data in partialInterfacesGenerator.GenerateFiles())
{
context.GeneratorExecutionContext.AddSource(data.FileName, SourceText.From(data.Text, Encoding.UTF8));
}
}
private static void GenerateProxyClasses(GeneratorExecutionContext ctx, ProxySyntaxReceiver receiver, bool supportsNullable)
private static void GenerateProxyClasses(GeneratorExecutionContext ctx, ProxySyntaxReceiver receiver, bool supportsNullable)
{
var context = new Context
{
var context = new Context
{
GeneratorExecutionContext = ctx,
CandidateInterfaces = receiver.CandidateInterfaces
};
GeneratorExecutionContext = ctx,
CandidateInterfaces = receiver.CandidateInterfaces
};
var proxyClassesGenerator = new ProxyClassesGenerator(context, supportsNullable);
foreach (var data in proxyClassesGenerator.GenerateFiles())
{
context.GeneratorExecutionContext.AddSource(data.FileName, SourceText.From(data.Text, Encoding.UTF8));
}
var proxyClassesGenerator = new ProxyClassesGenerator(context, supportsNullable);
foreach (var data in proxyClassesGenerator.GenerateFiles())
{
context.GeneratorExecutionContext.AddSource(data.FileName, SourceText.From(data.Text, Encoding.UTF8));
}
}
}