Roslyn還出現這么低級的錯誤,不應該呀!


前幾天對Dora.Interception作了簡單的重構,想提供C#腳本來定義Interception Policy,毫無疑問微軟提供的編譯平台Roslyn使C#腳本化提供了支持。但是沒有想到隨便嘗試了一個簡單的功能就出現了問題,我個人覺得這應該是Roslyn的Bug。但是Roslyn經歷了這么多次版本的迭代還出現如此低級的錯誤,實在有點說不過去。

閑話少說,我們現在通過幾行簡單的代碼來重現這個Bug。我們創建了一個.NET Core 2.1的控制台應用,並添加針對NuGet包”Microsoft.CodeAnalysis.CSharp.Scripting“(版本2.8.2)的依賴。如下所示的是.csproj的完整定義。

<Project Sdk="Microsoft.NET.Sdk">
    <PropertyGroup>
        <OutputType>Exe</OutputType>
        <TargetFramework>netcoreapp2.1</TargetFramework>
        <AssemblyName>App</AssemblyName>
        <RootNamespace>App</RootNamespace>
    </PropertyGroup>
    <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
        <LangVersion>7.3</LangVersion>
    </PropertyGroup>
    <ItemGroup>
        <PackageReference Include="Microsoft.CodeAnalysis.CSharp.Scripting" Version="2.8.2" />
    </ItemGroup>
</Project>

接下來我們編寫了一段簡單的程序。如下面的代碼片段所示,我們只是采用腳本的形式創建了一個Foo對象並利用它創建出Bar對象,然后調用后者的Print方法而已。

namespace Scripting
{
    public class Foo { }
    public class Bar
    {
        public Foo Foo { get; }
        public Bar(Foo foo) => Foo = foo;
        public void Print() => Console.WriteLine(Foo);
    }

    class Program
    {
        static async Task Main(string[] args)
        {
            var options = ScriptOptions.Default
                .AddReferences(typeof(Program).Assembly)
                .AddImports("Scripting");

            //Success
            await CSharpScript
               .Create("var bar = new Bar(new Foo());", options)
               .ContinueWith("bar.Print()")
               .RunAsync();
        }
    }
}

這段代碼是沒有問題的,運行之后Print方法輸出的結果可以正常出現在入下所示的控制台上。

image

接下來我們將“var bar = new Bar(new Foo());”這行代碼按照如下的方式拆分成兩行執行。

class Program
{
    static async Task Main(string[] args)
    {
        //Fail
        await CSharpScript
            .Create("var foo = new Foo();", options)
            .ContinueWith("var bar = new Bar(foo);")
            .ContinueWith("bar.Print()")
            .RunAsync();
    }
}

在此運行該程序后出現如下所示的“Microsoft.CodeAnalysis.Scripting.CompilationErrorException”異常,並提示“cannot convert from 'Scripting.Foo [App, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]' to 'Scripting.Foo [c:\users\jinnan\Source\Repos\App\App\bin\Debug\netcoreapp2.1\App.dll]”。

image

如下所示的是完整的錯誤信息:

Unhandled Exception: Microsoft.CodeAnalysis.Scripting.CompilationErrorException: (1,19): error CS1503: Argument 1: cannot convert from 'Scripting.Foo [App, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]' to 'Scripting.Foo [c:\users\jinnan\Source\Repos\App\App\bin\Debug\netcoreapp2.1\App.dll]'
   at Microsoft.CodeAnalysis.Scripting.ScriptBuilder.ThrowIfAnyCompilationErrors(DiagnosticBag diagnostics, DiagnosticFormatter formatter) in /_/src/Scripting/Core/ScriptBuilder.cs:line 104
   at Microsoft.CodeAnalysis.Scripting.ScriptBuilder.CreateExecutor[T](ScriptCompiler compiler, Compilation compilation, Boolean emitDebugInformation, CancellationToken cancellationToken) in /_/src/Scripting/Core/ScriptBuilder.cs:line 89
   at Microsoft.CodeAnalysis.Scripting.Script`1.GetExecutor(CancellationToken cancellationToken) in /_/src/Scripting/Core/Script.cs:line 359
   at Microsoft.CodeAnalysis.Scripting.Script`1.CommonGetExecutor(CancellationToken cancellationToken) in /_/src/Scripting/Core/Script.cs:line 343
   at Microsoft.CodeAnalysis.Scripting.Script`1.TryGetPrecedingExecutors(Script lastExecutedScriptInChainOpt, CancellationToken cancellationToken) in /_/src/Scripting/Core/Script.cs:line 407
   at Microsoft.CodeAnalysis.Scripting.Script`1.GetPrecedingExecutors(CancellationToken cancellationToken) in /_/src/Scripting/Core/Script.cs:line 370
   at Microsoft.CodeAnalysis.Scripting.Script`1.RunAsync(Object globals, Func`2 catchException, CancellationToken cancellationToken) in /_/src/Scripting/Core/Script.cs:line 459
   at Scripting.Program.Main(String[] args) in c:\users\jinnan\Source\Repos\App\App\Program.cs:line 31
   at Scripting.Program.<Main>(String[] args)

這是我提交的issue鏈接:https://github.com/dotnet/roslyn/issues/28803#issuecomment-407894956


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM