You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

增量源代码生成器在间接关联项目中运行的问题及解决方法

问题原因及解决方案

原因分析

  • NuGet的依赖传递特性:当你在"Models"项目中引用源代码生成器NuGet包时,所有引用"Models"的其他项目会自动继承这个包作为间接依赖,NuGet默认会传递所有依赖项到下游项目。
  • 增量源代码生成器的编译时加载机制:生成器属于编译阶段的组件,只要项目的依赖链中存在生成器包,Roslyn编译引擎就会在该项目编译时加载并执行生成器,不管引用是直接还是间接的。

阻止生成器在间接引用项目中运行的方法

1. 限制NuGet包的依赖传递性

在"Models"项目的.csproj文件中,修改生成器包的引用配置,添加PrivateAssets="all"属性,将该包的所有资产标记为仅当前项目可用,不会传递到下游项目:

<PackageReference Include="你的生成器包名称" Version="对应版本号" PrivateAssets="all" />

2. 在生成器代码中添加项目过滤逻辑

在生成器的Initialize方法里添加判断逻辑,仅在目标项目(如"Models"项目)中执行生成操作。可以通过检查项目的程序集名称来过滤:

using Microsoft.CodeAnalysis;

[Generator]
public class YourIncrementalGenerator : IIncrementalGenerator
{
    public void Initialize(IncrementalGeneratorInitializationContext context)
    {
        // 仅允许程序集名称包含"Models"的项目触发生成逻辑
        var shouldRunGenerator = context.CompilationProvider
            .Select((compilation, _) => compilation.AssemblyName.Name?.Contains("Models", StringComparison.OrdinalIgnoreCase) ?? false);

        // 基于过滤条件构建生成管道
        var generatorPipeline = shouldRunGenerator
            .Where(shouldRun => shouldRun)
            // 后续添加你的生成逻辑代码...
            ;

        // 注册生成输出(示例)
        // context.RegisterSourceOutput(generatorPipeline, (ctx, _) => { /* 生成代码逻辑 */ });
    }
}

3. 调整NuGet包的打包配置

如果你是生成器NuGet包的构建者,可以修改打包路径:将生成器组件从buildTransitive目录改为build目录。buildTransitive下的组件会被间接引用的项目加载,而build目录下的组件仅对直接引用的项目生效。

在生成器项目的.csproj中修改打包配置:

<ItemGroup>
    <!-- 替换原有的buildTransitive配置 -->
    <None Include="$(OutputPath)你的生成器程序集.dll" 
          Pack="true" 
          PackagePath="build" />
    <!-- 同步将配套的.props/.targets文件打包到build目录 -->
    <None Include="build\你的生成器.props" 
          Pack="true" 
          PackagePath="build" />
</ItemGroup>

内容的提问来源于stack exchange,提问作者George Fabish

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.16 10:47:48