Visual studio 如何使用Roslyn Workspace预编译项目
我需要编译一个启用预编译的ASP.NETWeb应用程序(web窗体和MVC)。我正在使用Microsoft.CodeAnalysis.MSBuild.MSBuildWorkspace打开项目并发出项目级程序集。我已经确定RazorGenerator可以用于预编译,但这会给我的解决方案增加额外的复杂性,有没有一种方法可以简单地使用Roslyn Workspace来实现这一点?我提出了以下代码来生成预编译的构建,但是,我正在寻找一种不需要很多文件级操作的更健壮的方法Visual studio 如何使用Roslyn Workspace预编译项目,visual-studio,visual-studio-2015,roslyn-code-analysis,microsoft.codeanalysis,Visual Studio,Visual Studio 2015,Roslyn Code Analysis,Microsoft.codeanalysis,我需要编译一个启用预编译的ASP.NETWeb应用程序(web窗体和MVC)。我正在使用Microsoft.CodeAnalysis.MSBuild.MSBuildWorkspace打开项目并发出项目级程序集。我已经确定RazorGenerator可以用于预编译,但这会给我的解决方案增加额外的复杂性,有没有一种方法可以简单地使用Roslyn Workspace来实现这一点?我提出了以下代码来生成预编译的构建,但是,我正在寻找一种不需要很多文件级操作的更健壮的方法 static void
static void Main(string[] args)
{
//MVC APP
string projectFileName = @"C:\MVCWebApplication\MVCWebApplication\MVCWebApplication.csproj";
string appName = "MVCWebApplication";
//ASP.NET Web Forma App
//string projectFileName = @"C:\AapApp\WebGoat\WebGoat.NET.csproj";
//string appName = "WebGoat.NET";
//Build Artifacts will be drop to this location
string publishDrop = Path.Combine(Path.GetTempPath(), Path.GetRandomFileName());
//aspnet compiler will drop precompiled artifacts to this location
string precompiledDrop = Path.Combine(Path.GetTempPath(), Path.GetRandomFileName());
//Publishing the extension without precompile
var pc = new ProjectCollection();
var globalProperty = new Dictionary<string, string>();
globalProperty.Add("Configuration", "Debug");
globalProperty.Add("Platform", "x86");
globalProperty.Add("OutputPath", publishDrop);
globalProperty.Add("WebPublishMethod", "FileSystem");
globalProperty.Add("EnableUpdateable", "false");
globalProperty.Add("DebugSymbols", "true");
globalProperty.Add("VisualStudioVersion", "14.0");//TODO: Get from IDE
var buidlRequest = new BuildRequestData(projectFileName, globalProperty, null, new string[] { "Build" }, null);
var buildResult = BuildManager.DefaultBuildManager.Build(new BuildParameters(pc), buidlRequest);
//If build errors; then trow
if (buildResult.Exception != null)
{
throw buildResult.Exception;
}
//Rslyn folder not getting created in required location in VS 2015 MVC app template
//https://stackoverflow.com/questions/32780315/could-not-find-a-part-of-the-path-bin-roslyn-csc-exe
//Moving it to proper location manually
string publish = Path.Combine(publishDrop, "_PublishedWebsites", appName);
if (!Directory.Exists(Path.Combine(publish, "bin", "Roslyn")) &&
Directory.Exists(Path.Combine(publishDrop, "Roslyn")))
{
Directory.Move(Path.Combine(publishDrop, "Roslyn"), Path.Combine(publish, "bin", "Roslyn"));
}
//Executing aspnet compiler to get the final output
using (var cmd = new Process())
{
cmd.StartInfo.FileName = @"C:\Windows\Microsoft.NET\Framework\v4.0.30319\aspnet_compiler.exe";
cmd.StartInfo.Arguments = @"-v / -p " + publishDrop + @"\_PublishedWebsites\" + appName + " " + precompiledDrop;
cmd.StartInfo.RedirectStandardInput = true;
cmd.StartInfo.RedirectStandardOutput = true;
cmd.StartInfo.CreateNoWindow = true;
cmd.StartInfo.UseShellExecute = false;
cmd.Start();
cmd.StandardInput.Flush();
cmd.StandardInput.Close();
cmd.WaitForExit();
Console.WriteLine(cmd.StandardOutput.ReadToEnd());
//TODO: Check result for any precompilation errors,
}
//Cleanup files in final precopiled artifact drop
if (Directory.Exists(Path.Combine(precompiledDrop, "bin", "Roslyn")))
{
Directory.Delete(Path.Combine(precompiledDrop, "bin", "Roslyn"), true);
}
Console.ReadKey();
}
static void Main(字符串[]args)
{
//MVC应用程序
string projectFileName=@“C:\MVCWebApplication\MVCWebApplication\MVCWebApplication.csproj”;
字符串appName=“MVCWebApplication”;
//ASP.NET Web Forma应用程序
//字符串projectFileName=@“C:\AapApp\WebGoat\WebGoat.NET.csproj”;
//字符串appName=“WebGoat.NET”;
//生成工件将被放置到此位置
string publishDrop=Path.Combine(Path.GetTempPath(),Path.GetRandomFileName());
//aspnet编译器将把预编译的工件放到这个位置
string precompiledDrop=Path.Combine(Path.GetTempPath(),Path.GetRandomFileName());
//在不预编译的情况下发布扩展
var pc=新项目集合();
var globalProperty=新字典();
添加(“配置”、“调试”);
添加(“平台”、“x86”);
添加(“OutputPath”,publishDrop);
添加(“WebPublishMethod”、“文件系统”);
globalProperty.Add(“EnableUpdateable”、“false”);
添加(“调试符号”、“真”);
globalProperty.Add(“VisualStudioVersion”,“14.0”);//TODO:从IDE获取
var buidlRequest=newbuildrequestdata(projectFileName,globalProperty,null,新字符串[]{“Build”},null);
var buildResult=BuildManager.DefaultBuildManager.Build(新的BuildParameters(pc),buildRequest);
//如果生成错误,则trow
if(buildResult.Exception!=null)
{
抛出buildResult.Exception;
}
//未在VS 2015 MVC应用程序模板中的所需位置创建Rslyn文件夹
//https://stackoverflow.com/questions/32780315/could-not-find-a-part-of-the-path-bin-roslyn-csc-exe
//手动将其移动到适当的位置
字符串publish=Path.Combine(publishDrop,“\u PublishedWebsites”,appName);
如果(!Directory.Exists)(Path.Combine(publish,“bin”,“Roslyn”))&&
目录.Exists(Path.Combine(publishDrop,“Roslyn”))
{
Directory.Move(Path.Combine(publishDrop,“Roslyn”)、Path.Combine(publish,“bin”,“Roslyn”);
}
//执行aspnet编译器以获得最终输出
使用(var cmd=new Process())
{
cmd.StartInfo.FileName=@“C:\Windows\Microsoft.NET\Framework\v4.0.30319\aspnet\u compiler.exe”;
cmd.StartInfo.Arguments=@“-v/-p”+publishDrop+@“\\\ U PublishedWebsites\\”+appName+“”+precompiledDrop;
cmd.StartInfo.RedirectStandardInput=true;
cmd.StartInfo.RedirectStandardOutput=true;
cmd.StartInfo.CreateNoWindow=true;
cmd.StartInfo.UseShellExecute=false;
cmd.Start();
cmd.StandardInput.Flush();
cmd.StandardInput.Close();
cmd.WaitForExit();
Console.WriteLine(cmd.StandardOutput.ReadToEnd());
//TODO:检查结果是否存在任何预编译错误,
}
//清理最终预编译工件放置中的文件
if(Directory.Exists(Path.Combine(预编译的drop,“bin”,“Roslyn”)))
{
Directory.Delete(Path.Combine(precompiledDrop,“bin”,“Roslyn”),true);
}
Console.ReadKey();
}
MSBuildWorkspace是Roslyn工作区。我怀疑RazorGenerator正在为项目中的内容生成额外的源代码,因此从MSBuildWorkspace发出编译不太可能工作,因为它不会包含所有源代码。@MattWarren:是的Matt Warren,我必须使用MSBuild将web应用发布到一个文件夹中,并使用aspnet_comiler.exe预编译发布的工件(请参考我的答案)。此方法生成所需的二进制文件,但是我正在为此寻找一段更健壮的代码,可能会避免MSBuild和aspnet_compiler.exe。此代码工作正常,并发出预期的输出,但有更健壮的方法吗?