每个 class 获取一个 Roslyn 语法接收器
Getting one Roslyn syntax receiver per class
我有一个简单的源代码生成器定义为
[Generator]
public class NestedObjectGenerator : ISourceGenerator
{
public void Initialize(GeneratorInitializationContext context)
{
context.RegisterForSyntaxNotifications(() => new MySyntaxReceiver());
}
public void Execute(GeneratorExecutionContext context)
{
var recv = (MySyntaxReceiver)context.SyntaxReceiver;
ClassDeclarationSyntax cds = recv?.Class;
if (cds is null) return;
// use cds here
}
private class MySyntaxReceiver : ISyntaxReceiver
{
public ClassDeclarationSyntax Class { get; private set; }
public void OnVisitSyntaxNode(SyntaxNode node)
{
if (node is ClassDeclarationSyntax cds &&
cds.Modifiers.Any(SyntaxKind.PartialKeyword))
Class = cds;
}
}
}
我正在 运行 将此生成器连接到一个文件中,该文件中有多个部分 classes。但是,似乎 Execute()
只被调用一次,并且包含的 Class
是具有 Main()
方法的 class,即使我有其他 class在文件中。
所以,我的问题是:如何在每个受影响的语法节点中将 Execute()
变为 运行 一次,即,对于每个部分 class 将其变为 运行 一次?
您可以这样更改您的接收器:
private class MySyntaxReceiver : ISyntaxReceiver
{
public List<ClassDeclarationSyntax> ClassCandidates { get; } = new();
public void OnVisitSyntaxNode(SyntaxNode node)
{
if (node is ClassDeclarationSyntax cds && cds.Modifiers.Any(SyntaxKind.PartialKeyword))
ClassCandidates.Add(cds);
}
}
然后在源代码生成器的 Execute 方法中,您可以在您收集的所有节点上循环。
我从一个非常有用的视频中得到了这种方法
https://www.youtube.com/watch?v=P9Pv5IdinMU
这里是 github 演示文稿中的演示,我从这些示例中学到了这一点:
我有一个简单的源代码生成器定义为
[Generator]
public class NestedObjectGenerator : ISourceGenerator
{
public void Initialize(GeneratorInitializationContext context)
{
context.RegisterForSyntaxNotifications(() => new MySyntaxReceiver());
}
public void Execute(GeneratorExecutionContext context)
{
var recv = (MySyntaxReceiver)context.SyntaxReceiver;
ClassDeclarationSyntax cds = recv?.Class;
if (cds is null) return;
// use cds here
}
private class MySyntaxReceiver : ISyntaxReceiver
{
public ClassDeclarationSyntax Class { get; private set; }
public void OnVisitSyntaxNode(SyntaxNode node)
{
if (node is ClassDeclarationSyntax cds &&
cds.Modifiers.Any(SyntaxKind.PartialKeyword))
Class = cds;
}
}
}
我正在 运行 将此生成器连接到一个文件中,该文件中有多个部分 classes。但是,似乎 Execute()
只被调用一次,并且包含的 Class
是具有 Main()
方法的 class,即使我有其他 class在文件中。
所以,我的问题是:如何在每个受影响的语法节点中将 Execute()
变为 运行 一次,即,对于每个部分 class 将其变为 运行 一次?
您可以这样更改您的接收器:
private class MySyntaxReceiver : ISyntaxReceiver
{
public List<ClassDeclarationSyntax> ClassCandidates { get; } = new();
public void OnVisitSyntaxNode(SyntaxNode node)
{
if (node is ClassDeclarationSyntax cds && cds.Modifiers.Any(SyntaxKind.PartialKeyword))
ClassCandidates.Add(cds);
}
}
然后在源代码生成器的 Execute 方法中,您可以在您收集的所有节点上循环。 我从一个非常有用的视频中得到了这种方法
https://www.youtube.com/watch?v=P9Pv5IdinMU
这里是 github 演示文稿中的演示,我从这些示例中学到了这一点: