【问题标题】:How to force CSharpCodeProvider to compile for a specific target framework?如何强制 CSharpCodeProvider 为特定的目标框架进行编译?
【发布时间】:2017-11-10 09:43:01
【问题描述】:

我有一个包含 c# 项目的解决方案,一些 netstandard 2.0 和其他 .net4.7。启动项目当然是net47

在某一时刻,该项目使用CodeDom 创建代码并使用CSharpCodeProvider 编译它。问题是在某些机器上,它尝试为 .netstandard 编译程序集但失败了。预期会失败:生成的程序集引用EF,仅适用于完整的.net framework

如何强制 CSharpCodeProvider 针对 .net47 进行编译?

public bool GenerateAssembly(
        CodeDomBusinessCode compileUnit
        , string fileName
        , string assembliesPath
        , out IEnumerable<string> errors)
    {
        var provider = new CSharpCodeProvider();
        var parameters = new CompilerParameters
        {
            GenerateExecutable = false,
            OutputAssembly = fileName,
            GenerateInMemory = false
        };
        parameters.ReferencedAssemblies.Add("System.dll");
        parameters.ReferencedAssemblies.Add("System.Runtime.dll");
        parameters.ReferencedAssemblies.Add("System.Core.dll");
        parameters.ReferencedAssemblies.Add("System.ComponentModel.Composition.dll");
        parameters.ReferencedAssemblies.Add(Path.Combine(assembliesPath, "EntityFramework.dll"));
        parameters.ReferencedAssemblies.Add("System.ComponentModel.DataAnnotations.dll");
        parameters.ReferencedAssemblies.Add(Path.Combine(assembliesPath, "GlobalE.Server.Contracts.dll"));

        var results = provider.CompileAssemblyFromDom(parameters, compileUnit.Code);
        if (results.Errors.Count > 0)
        {
            errors = results.Errors.OfType<CompilerError>().Select(x => x.ToString());
            return false;
        }
        errors = null;
        return true;
    }

错误:

error CS0012: The type 'System.IDisposable' is defined in an assembly
 that is not referenced. You must add a reference to assembly 
'netstandard, Version=2.0.0.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51'.

更新: 如果我将所有项目都更改为net47(这样解决方案中就没有netstandard项目),错误就会消失,但我想在netstandard上保留尽可能多的项目。

【问题讨论】:

  • @HansPassant 嗯,EF 肯定存在:我可以在 bin 目录中看到它,当我从另一台计算机(只有我们的程序集,而不是它的依赖项)带来已编译的程序集时,一切都开始工作了。显然,这只是编译步骤。更新了问题以包含实际的错误消息。
  • CSharpCodeProvider 是旧版,它只能针对已安装的 .NET 版本,CompilerVersion 的有效选项是 2.0、3.0 或 4.0。您的程序将由 C:\Windows\Microsoft.NET\Framework\v4.0.30319\csc.exe 编译。那是遗留的 C# 编译器,最后在 .NET 4.5 中更新,它对 .NETStandard 一无所知。你必须bring your own

标签: c# roslyn codedom


【解决方案1】:

根据您的错误,您应该添加“netstandard.dll”作为引用,这可能会导致在 .net 4.7 中“System.IDisposable”在“mscorlib.dll”中,而 .netstatndard 在“ netstandard.dll”。

【讨论】:

    【解决方案2】:

    试试这个

    var options = new Dictionary<string, string> 
                  {
                      { "CompilerVersion", "v4.7" }
                  };
    var provider = new CSharpCodeProvider(options);
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-02-24
      • 2021-11-02
      相关资源
      最近更新 更多