将命令行参数传递给 roslyn 编译器
Passing command line arguments to roslyn compiler
我想知道是否有办法在编译和执行代码时将命令行参数传递给 roslyn。
我当前用于生成编译器和执行源代码的代码如下所示:
CSharpCompilation compilation = CSharpCompilation.Create(Path.GetFileName(assemblyPath))
.WithOptions(new CSharpCompilationOptions(OutputKind.ConsoleApplication))
.AddReferences(references)
.AddSyntaxTrees(syntaxTree);
using (var memStream = new MemoryStream())
{
var result = compilation.Emit(memStream);
if (!result.Success)
{
IEnumerable<Diagnostic> failures = result.Diagnostics.Where(diagnostic =>
diagnostic.IsWarningAsError ||
diagnostic.Severity == DiagnosticSeverity.Error);
foreach (Diagnostic diagnostic in failures)
{
Console.Error.WriteLine("{0}: {1}", diagnostic.Id, diagnostic.GetMessage());
}
}
else
{
memStream.Seek(0, SeekOrigin.Begin);
Assembly assembly = Assembly.Load(memStream.ToArray());
var test = assembly;
}
}
目标是拥有像这样的某种源代码:
using System;
class Program
{
static string StringToUppercase(string str)
{
return str.ToUppercase();
}
static void Main(string[] args)
{
string str = Console.ReadLine();
string result = StringToUppercase(str);
Console.WriteLine(result);
}
}
我可以在其中传递命令行参数并获得 Console.WriteLine() 的结果。处理这个问题的最佳方法是什么?当前代码确实构建并将编译和分析源代码。
代码将在 .NET core 3.1 mvc 网络应用程序中编写。
我猜您想将参数传递给编译后的应用程序而不是 roslyn :)
执行编译后的代码,使用Console.SetOut(TextWriter)
to get its output (example: sof link):
Assembly assembly = Assembly.Load(memStream.ToArray());
// Console.SetOut to a writer
var test = assembly.EntryPoint.Invoke(null, new object[] { "arg1", "arg2" });
// And restore it
或者为其启动一个新进程:
memStream.CopyTo(File.OpenWrite("temp.exe"))
// Copied from MSDN
// https://docs.microsoft.com/en-us/dotnet/api/system.diagnostics.process.standardoutput
using (Process process = new Process())
{
process.StartInfo.FileName = "temp.exe";
process.StartInfo.UseShellExecute = false;
process.StartInfo.RedirectStandardOutput = true;
process.Start();
// Synchronously read the standard output of the spawned process.
StreamReader reader = process.StandardOutput;
string output = reader.ReadToEnd();
// Write the redirected output to this application's window.
Console.WriteLine(output);
process.WaitForExit();
}
如果您有多个 Console.ReadLine 您可以将输入保存为文本文件并使用 StramReader 阅读:
var inputFile = folder + "/input.txt";
File.WriteAllLines(inputFile, "your command line input");
using (var consoleout = new StreamWriter(folder + "/output.txt")) {
using (var consolein = new StreamReader(inputFile)) {
Console.SetOut(consoleout);
Console.SetIn(consolein);
assembly.EntryPoint.Invoke(null, new string[] {});
consoleout.Flush();
var resultOutput = File.ReadAllText(folder + "/output.txt");
Console.WriteLine(resultOutput);
}
}
我想知道是否有办法在编译和执行代码时将命令行参数传递给 roslyn。
我当前用于生成编译器和执行源代码的代码如下所示:
CSharpCompilation compilation = CSharpCompilation.Create(Path.GetFileName(assemblyPath))
.WithOptions(new CSharpCompilationOptions(OutputKind.ConsoleApplication))
.AddReferences(references)
.AddSyntaxTrees(syntaxTree);
using (var memStream = new MemoryStream())
{
var result = compilation.Emit(memStream);
if (!result.Success)
{
IEnumerable<Diagnostic> failures = result.Diagnostics.Where(diagnostic =>
diagnostic.IsWarningAsError ||
diagnostic.Severity == DiagnosticSeverity.Error);
foreach (Diagnostic diagnostic in failures)
{
Console.Error.WriteLine("{0}: {1}", diagnostic.Id, diagnostic.GetMessage());
}
}
else
{
memStream.Seek(0, SeekOrigin.Begin);
Assembly assembly = Assembly.Load(memStream.ToArray());
var test = assembly;
}
}
目标是拥有像这样的某种源代码:
using System;
class Program
{
static string StringToUppercase(string str)
{
return str.ToUppercase();
}
static void Main(string[] args)
{
string str = Console.ReadLine();
string result = StringToUppercase(str);
Console.WriteLine(result);
}
}
我可以在其中传递命令行参数并获得 Console.WriteLine() 的结果。处理这个问题的最佳方法是什么?当前代码确实构建并将编译和分析源代码。
代码将在 .NET core 3.1 mvc 网络应用程序中编写。
我猜您想将参数传递给编译后的应用程序而不是 roslyn :)
执行编译后的代码,使用Console.SetOut(TextWriter)
to get its output (example: sof link):
Assembly assembly = Assembly.Load(memStream.ToArray());
// Console.SetOut to a writer
var test = assembly.EntryPoint.Invoke(null, new object[] { "arg1", "arg2" });
// And restore it
或者为其启动一个新进程:
memStream.CopyTo(File.OpenWrite("temp.exe"))
// Copied from MSDN
// https://docs.microsoft.com/en-us/dotnet/api/system.diagnostics.process.standardoutput
using (Process process = new Process())
{
process.StartInfo.FileName = "temp.exe";
process.StartInfo.UseShellExecute = false;
process.StartInfo.RedirectStandardOutput = true;
process.Start();
// Synchronously read the standard output of the spawned process.
StreamReader reader = process.StandardOutput;
string output = reader.ReadToEnd();
// Write the redirected output to this application's window.
Console.WriteLine(output);
process.WaitForExit();
}
如果您有多个 Console.ReadLine 您可以将输入保存为文本文件并使用 StramReader 阅读:
var inputFile = folder + "/input.txt";
File.WriteAllLines(inputFile, "your command line input");
using (var consoleout = new StreamWriter(folder + "/output.txt")) {
using (var consolein = new StreamReader(inputFile)) {
Console.SetOut(consoleout);
Console.SetIn(consolein);
assembly.EntryPoint.Invoke(null, new string[] {});
consoleout.Flush();
var resultOutput = File.ReadAllText(folder + "/output.txt");
Console.WriteLine(resultOutput);
}
}