82 lines
2.9 KiB
C#
82 lines
2.9 KiB
C#
using System.CommandLine;
|
|
using System.Dynamic;
|
|
using System.Text;
|
|
using IronPython.Hosting;
|
|
using MycroForge.CLI.Commands.Interfaces;
|
|
|
|
namespace MycroForge.CLI.Commands;
|
|
|
|
public partial class MycroForge
|
|
{
|
|
public partial class Script
|
|
{
|
|
public class Run : Command, ISubCommandOf<Script>
|
|
{
|
|
private readonly ProjectContext _context;
|
|
|
|
private static readonly Argument<string> NameArgument =
|
|
new(name: "name", description: "The name of the script");
|
|
|
|
private static readonly Argument<IEnumerable<string>> ArgsArgument =
|
|
new(name: "args", description: "The args to the script");
|
|
|
|
public Run(ProjectContext context) : base("run", "Run a script")
|
|
{
|
|
_context = context;
|
|
AddArgument(NameArgument);
|
|
AddArgument(ArgsArgument);
|
|
this.SetHandler(ExecuteAsync, NameArgument, ArgsArgument);
|
|
}
|
|
|
|
private void ExecuteAsync(string name, IEnumerable<string> args)
|
|
{
|
|
var engine = Python.CreateEngine();
|
|
using var output = new MemoryStream();
|
|
using var error = new MemoryStream();
|
|
engine.Runtime.IO.SetOutput(output, Encoding.Default);
|
|
engine.Runtime.IO.SetErrorOutput(error, Encoding.Default);
|
|
|
|
var scope = engine.CreateScope();
|
|
scope.SetVariable("args", args.ToArray());
|
|
scope.SetVariable("context", CreateScriptContext());
|
|
|
|
try
|
|
{
|
|
var scriptPath = Path.Combine(
|
|
Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), ".m4g", $"{name}.py"
|
|
);
|
|
engine.ExecuteFile(scriptPath, scope);
|
|
|
|
if (output.Length > 0)
|
|
Console.WriteLine(Encoding.Default.GetString(output.ToArray()));
|
|
if (error.Length > 0)
|
|
Console.WriteLine(Encoding.Default.GetString(error.ToArray()));
|
|
}
|
|
catch (Exception e)
|
|
{
|
|
Console.WriteLine(e);
|
|
}
|
|
finally
|
|
{
|
|
engine.Runtime.Shutdown();
|
|
}
|
|
}
|
|
|
|
private dynamic CreateScriptContext()
|
|
{
|
|
var createFile = _context.CreateFile;
|
|
var readFile = _context.ReadFile;
|
|
var writeFile = _context.WriteFile;
|
|
var bash = _context.Bash;
|
|
|
|
dynamic context = new ExpandoObject();
|
|
context.create_file = createFile;
|
|
context.read_file = readFile;
|
|
context.write_file = writeFile;
|
|
context.bash = bash;
|
|
|
|
return context;
|
|
}
|
|
}
|
|
}
|
|
} |