【问题标题】:Can't include Newtonsoft JSON in CSharpCodeProvider script不能在 CSharpCodeProvider 脚本中包含 Newtonsoft JSON
【发布时间】:2020-11-30 06:01:30
【问题描述】:

我正在尝试在动态编译的脚本中使用 JSON。但是,当我包含库并添加 JObject 时,我收到如下错误:“类型‘System.Dynamic.IDynamicMetaObjectProvider’是在未引用的程序集中定义的。您必须添加对程序集‘System.Core,版本’的引用=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'。”

我很好地包含了 MathNet.Numerics。

这是我的设置。

  • 控制台应用程序 .NET Framework 4(因此它匹配运行时 编译)
  • Nuget 安装 MathNet.Numerics
  • Nuget 安装 Newtonsoft
  • 将运行时编译指向带有 dll 的调试文件夹。

测试代码

using System;
using System.IO;
using System.Collections.Generic;
using Newtonsoft.Json.Linq;
using Newtonsoft.Json;
using Microsoft.CSharp;
using System.Reflection;
using System.CodeDom.Compiler;

namespace ConsoleApp1
{

  public class RunScript0
  {


    public bool Compile()
    {

      //Add using statements here
      string source = "namespace UserScript\r\n{\r\nusing System;\r\n" +
                "using System.IO;\r\n" +
                "using System.Collections.Generic;\r\n" +
                "using MathNet.Numerics.Distributions;\r\n" +
                "using Newtonsoft.Json.Linq;\r\n" +
                "using Newtonsoft.Json;\r\n" +
                "public class RunScript\r\n{\r\n" +
                "private const int x = 99;\r\n" +
                "public int Eval()\r\n{\r\n" +
                //Remove following line and all works fine
                "JObject j = new JObject();\r\n" +
                "return x; \r\n\r\n}\r\n}\r\n}";

      Dictionary<string, string> provOptions =
        new Dictionary<string, string>();

      provOptions.Add("CompilerVersion", "v4.0");
      CodeDomProvider compiler = new CSharpCodeProvider(provOptions);


      CompilerParameters parameters = new CompilerParameters();
      string appPath = System.IO.Directory.GetCurrentDirectory();
      parameters.ReferencedAssemblies.Add(appPath + "\\MathNet.Numerics.dll");
      parameters.ReferencedAssemblies.Add(appPath + "\\Newtonsoft.Json.dll");
      //Tried adding but didn't help parameters.ReferencedAssemblies.Add(appPath + "\\System.Core.dll");

      parameters.GenerateInMemory = true;
      var results = compiler.CompileAssemblyFromSource(parameters, source);
      // Check for compile errors / warnings
      if (results.Errors.HasErrors || results.Errors.HasWarnings)
      {
        Console.WriteLine(results.Errors.Count.ToString() + " Erorrs");
        for (int i = 0; i < results.Errors.Count; i++)
          Console.WriteLine(results.Errors[i].ToString());
        return false;
      }
      else
      {
        Console.WriteLine("Compiled Successfully");
        return true;
      }
    }
  }
  class Program
  {
    static void Main(string[] args)
    {
      RunScript0 A = new RunScript0();
      A.Compile();
    }
  }
}

【问题讨论】:

  • 你用什么 .NET 版本来编译?
  • 我相信它是 4.0,如代码所示 - provOptions.Add("CompilerVersion", "v4.0");还是你的意思是别的?
  • 我的问题是所有代码的 .Net 版本(不是元代码)。
  • Project Target Framwork = .Net Framework 4。我选择了这个来匹配元编译“v4.0”,这样exe目录中的任何dll都是正确的版本,可以在元代码。

标签: c# json.net csharpcodeprovider


【解决方案1】:

您需要从 GAC(全局程序集缓存)中添加对 SystemSystem.Core 的引用:

parameters.ReferencedAssemblies.Add("System.dll");
parameters.ReferencedAssemblies.Add("System.Core.dll");

我认为它依赖于 Newtonsoft.Json

【讨论】:

  • Nuget 的依赖中没有列出那些。
  • 奇怪,您的建议在我的测试应用程序中有效,但在我的真实应用程序中,我得到了其他错误。我在测试函数下复制了完全相同的代码和 dll,我得到的第一个错误是 - 类型“System.Dynamic.IDynamicMetaObjectProvider”是在未引用的程序集中定义的。您必须添加对程序集“netstandard,Version=2.0.0.0,Culture=neutral,PublicKeyToken=cc7b13ffcd2ddd51”的引用。如果我像 system.dll 一样添加 dotstandard.dll,那么我会得到大量“在多个程序集中定义”
  • 谢谢,我希望我以前见过这个。其中的循环和 addRange 示例非常完美。
猜你喜欢
  • 2021-01-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-01-03
  • 1970-01-01
相关资源
最近更新 更多