'Main' 通过 Roslyn 编译时未找到方法

'Main' method not found when compiling through Roslyn

我正在使用 Roslyn 编译具有 运行 时间生成代码的解决方案。虽然解决方案在从 Visual Studio 打开时编译完美,但在 Roslyn 中失败:

error CS5001: Program does not contain a static 'Main' method suitable for an entry point

我尝试编译的解决方案只有一个 ASP.NET Core 2 (.NET Framework 4.6.2) 项目,当然在根目录下的程序 class 中有一个 Main 方法项目的:

public class Program
{
    public static void Main(string[] args)
    {
        var host = new WebHostBuilder()
            .UseKestrel()
            .UseContentRoot(Directory.GetCurrentDirectory())
            .UseIISIntegration()
            .UseStartup<Startup>()
            .Build();

        host.Run();
    }
}

这是我 运行 从 .NET 4.7 WPF 应用程序编译该解决方案的代码:

private static async Task<bool> CompileSolution(string solutionPath, string outputDir)
{
    var workspace = MSBuildWorkspace.Create();
    var solution = await workspace.OpenSolutionAsync(solutionPath);
    var projectCompilation = await solution.Projects.Single().GetCompilationAsync();

    if (string.IsNullOrEmpty(projectCompilation?.AssemblyName))
    {
        return false;
    }

    using (var stream = File.Create(Path.Combine(outputDir, $"{projectCompilation.AssemblyName}.dll")))
    {
        var result = projectCompilation.Emit(stream);
        return result.Success;
    }
}

projectCompilation.Emit 失败:

  • warning CS8021: No value for RuntimeMetadataVersion found. No assembly containing System.Object was found nor was a value for RuntimeMetadataVersion specified through options.
  • error CS5001: Program does not contain a static 'Main' method suitable for an entry point

会不会是正在使用的NuGet包还没有正确支持.NET Core 2项目?我没有任何待定(甚至没有预览)的软件包更新。

我现在已将 ASP.NET Core 项目更新为 .NET 4.7,因此两个解决方案的版本相同,但未更改生成的错误。 csproj 看起来像这样:

<Project Sdk="Microsoft.NET.Sdk.Web">
  <PropertyGroup>
    <TargetFramework>net47</TargetFramework>
    <MvcRazorCompileOnPublish>true</MvcRazorCompileOnPublish>
    <TargetFrameworkVersion>v4.7</TargetFrameworkVersion>
    <ApplicationIcon />
    <OutputType>Exe</OutputType>
    <StartupObject>Practia.CrudGenerator.Web.Program</StartupObject>
  </PropertyGroup>
  <ItemGroup>..NUGET PACKAGES...</ItemGroup>
</Project>

通过在尝试发出结果之前添加这两行解决了问题:

compilation = compilation.AddReferences(MetadataReference.CreateFromFile(typeof(object).Assembly.Location));
compilation = compilation.WithOptions(new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary));

注意AddReferencesWithOptionsreturn都是新的Compilation实例,所以需要重新赋值。