Korzystanie z System.Dynamic w Roslyn

96

Zmodyfikowałem przykład dołączony do nowej wersji Roslyn, która została wydana wczoraj, aby używać dynamiki i ExpandoObject, ale otrzymuję błąd kompilatora, którego nie jestem pewien, jak naprawić. Błąd:

(7,21): błąd CS0656: brak wymaganego elementu członkowskiego kompilatora „Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfo.Create”

Czy nie możesz jeszcze używać dynamiki w nowym kompilatorze? Jak mogę to naprawić? Oto przykład, który zaktualizowałem:

[TestMethod]
public void EndToEndCompileAndRun()
{
    var text = @"using System.Dynamic;
    public class Calculator
    {
        public static object Evaluate()
        {
            dynamic x = new ExpandoObject();
            x.Result = 42;
            return x.Result;
        } 
    }";

    var tree = SyntaxFactory.ParseSyntaxTree(text);
    var compilation = CSharpCompilation.Create(
        "calc.dll",
        options: new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary),
        syntaxTrees: new[] {tree},
        references: new[] {new MetadataFileReference(typeof (object).Assembly.Location), new MetadataFileReference(typeof (ExpandoObject).Assembly.Location)});

    Assembly compiledAssembly;
    using (var stream = new MemoryStream())
    {
        var compileResult = compilation.Emit(stream);
        compiledAssembly = Assembly.Load(stream.GetBuffer());
    }

    Type calculator = compiledAssembly.GetType("Calculator");
    MethodInfo evaluate = calculator.GetMethod("Evaluate");
    string answer = evaluate.Invoke(null, null).ToString();

    Assert.AreEqual("42", answer);
}
Rush Frisby
źródło

Odpowiedzi:

219

Myślę, że powinieneś odwołać się do Microsoft.CSharp.dllzespołu

Alberto
źródło
3
Tak, to jest coś, co było wymagane od czasu dynamicwprowadzenia.
khellang
19
A jeśli Microsoft poda komunikat o błędzie, który mówi, że to znacznie ułatwiłoby sprawę.
kjbartel
1
Nie wiem, czy to rozwiązało problem, czy nie, ale dodałem <add namespace = "Microsoft.CSharp" /> do węzła Views / Web.config <namespaces>. Błąd kompilatora zniknął.
Don Rolling
3
Dodanie Microsoft.CSharp.dll przez FWIW oznacza var scriptOptions = ScriptOptions.Default.WithReferences ("Microsoft.CSharp"), czyli usunięcie biblioteki dll. Zaskoczyło mnie na kilka minut :)
Jon H
@JonH, więc powinniśmy dodać tę linię do AssemblyInfo.cs lub gdzieś zamiast odwoływać się do dll?
NH.
9

Aby kod działał w .Net Core 2.1, musiałem dodać w kompilacji następujące odwołania:

var compilation = CSharpCompilation.Create(
    "calc.dll",
    options: new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary),
    syntaxTrees: new[] {tree},
    references: new[] {
        MetadataReference.CreateFromFile(typeof(object).Assembly.Location),
        MetadataReference.CreateFromFile(typeof(ExpandoObject).Assembly.Location),
        MetadataReference.CreateFromFile(Assembly.Load(new AssemblyName("Microsoft.CSharp")).Location),
        MetadataReference.CreateFromFile(Assembly.Load(new AssemblyName("netstandard")).Location),
        MetadataReference.CreateFromFile(Assembly.Load(new AssemblyName("mscorlib")).Location),
        MetadataReference.CreateFromFile(Assembly.Load(new AssemblyName("System.Runtime")).Location),            
    }
);
Renzo Ciot
źródło
Możesz uciec z System.Linq.Expressions, System.Private.CoreLib, System.Runtime i Microsoft.CSharp, wszystko jako ciągi znaków
Simon Mourier
7

Specyficzne dla ASP.NET MVC:

Można uzyskać ten błąd w MVC 6 kontrolera jeśli zapomnij umieścić [FromBody]w POSTmetodzie.

    [HttpPost("[action]")]
    public void RunReport([FromBody]dynamic report)
    {
        ...
    }

Projekt domyślny .NETCore zawiera już Microsoft.CSharpodniesienie, ale otrzymujesz prawie taką samą wiadomość.

Po [FromBody]dodaniu możesz teraz publikować JSON, a następnie dynamicznie uzyskiwać dostęp do właściwości :-)

Simon_Weaver
źródło
Uznałem, że nie dotyczy to oryginalnego pytania wysłanego z 2014 roku (chociaż chciałem przyznać, że było pomocne). Nie byłem pewien, jaka etykieta SO podyktowała w takiej sytuacji.
tj.
Słuszna uwaga :) Właśnie dodałem to tutaj, ponieważ wydawało się to tak niejasne i to było dobre dopasowanie do tego błędu
Simon_Weaver
4

Możesz również chcieć sprawdzić właściwości wszystkich odniesień do projektu. Upewnij się, że wszelkie odwołania używają .NET nowszego niż 2.0. Mam projekt, który odwoływał się do innego projektu w tym samym rozwiązaniu i musiałem odbudować zależność przy użyciu nowszego elementu docelowego platformy .NET.

Zobacz ten post .

Nie zapomnij również dodać Microsoft.CSharpodniesienia do swojego głównego projektu, jak powiedział @Alberto.

A. Clymer
źródło
1

Jeśli projekt jest przeznaczony dla .Net Core lub .Net Standard, zamiast dodawać odwołanie, możesz zainstalować pakiet Microsoft.CSharp NuGet, aby rozwiązać ten błąd.

Kolappan N
źródło