如何在运行时读取给定项目中的 MSBuild 属性?

jul*_*gon 11 c# msbuild parameters .net-4.5

我想访问单元测试中的 MSBuild 变量,这是一个 .NET 4.5 类库项目(经典 csproj),但我找不到任何讨论将值从 MSBuild 传递到执行上下文的方法的文章。

我考虑过在编译期间设置环境变量,然后在执行期间读取该环境变量,但这似乎需要自定义任务来设置环境变量值,而且我有点担心变量的范围(理想情况下,我只想它可用于当前正在执行的项目,而不是全局)。

是否有已知的解决方案可以在运行时从 DLL 项目内部读取 MSBuild 属性?MSBuild 属性可以在执行过程中以某种方式“作为参数传递”吗?

jul*_*gon 12

我最终通过使用 .Net Core 项目中默认使用的相同代码生成任务使其工作。唯一的区别是我必须Target在 csproj 文件中手动添加它才能工作,因为代码创建不是框架项目的标准:

<Target Name="BeforeBuild">
  <ItemGroup>
    <AssemblyAttributes Include="MyProject.SolutionFileAttribute">
      <_Parameter1>$(SolutionPath)</_Parameter1>
    </AssemblyAttributes>
  </ItemGroup>
  <WriteCodeFragment AssemblyAttributes="@(AssemblyAttributes)" Language="C#" OutputDirectory="$(IntermediateOutputPath)" OutputFile="SolutionInfo.cs">
    <Output TaskParameter="OutputFile" ItemName="Compile" />
    <Output TaskParameter="OutputFile" ItemName="FileWrites" />
  </WriteCodeFragment>
</Target>
Run Code Online (Sandbox Code Playgroud)

Compile与和 的线条FileWrites可以很好地与 clean 等一起发挥作用(请参阅上面我的评论中的链接答案)。其他一切都应该足够直观。

项目编译时,自定义属性会添加到程序集中,然后我可以使用正常反射来检索该属性:

Assembly
    .GetExecutingAssembly()
    .GetCustomAttribute<SolutionFileAttribute>()
    .SolutionFile
Run Code Online (Sandbox Code Playgroud)

这非常有效,使我可以避免对解决方案文件进行任何硬编码搜索。