package lib; import lib.args.CLIArgs; import lib.args.ArgType; import kernel.ps.IProcess; import kernel.ps.ProcessHandle; using tink.CoreApi; abstract class CLIAppBase implements IProcess { private var handle:ProcessHandle; private final _subcommandsSync:Map Bool> = []; private final _subcommandsAsync:Map Future> = []; private final _subcommandsArgs:Map> = []; public final function run(handle:ProcessHandle) { this.handle = handle; var subcommand = handle.args[0]; if (subcommand == null || subcommand == "") { handle.writeLine("No subcommand specified"); printHelp(); return handle.close(false); } var args = handle.args.slice(1); if (_subcommandsSync.exists(subcommand)) { var argParser = new CLIArgs(_subcommandsArgs.get(subcommand)); if (!argParser.parse(args)) { handle.writeLine(argParser.getError()); return handle.close(false); } return handle.close(_subcommandsSync[subcommand](argParser)); } else if (_subcommandsAsync.exists(subcommand)) { var argParser = new CLIArgs(_subcommandsArgs.get(subcommand)); if (!argParser.parse(args)) { handle.writeLine(argParser.getError()); return handle.close(false); } _subcommandsAsync[subcommand](argParser).handle(handle.close); } else { handle.writeLine("Unknown subcommand: " + subcommand); printHelp(); return handle.close(false); } } private function registerSyncSubcommand(command:String, callback:(CLIArgs) -> Bool, args:Array = null) { _subcommandsSync.set(command, callback); _subcommandsArgs.set(command, args ?? []); } private function registerAsyncSubcommand(command:String, callback:(CLIArgs) -> Future, args:Array = null) { _subcommandsAsync.set(command, callback); _subcommandsArgs.set(command, args ?? []); } private function printHelp() { handle.writeLine("Usage: [args]"); handle.writeLine("Subcommands:"); for (k => v in this._subcommandsArgs) { handle.writeLine(' $k ${CLIArgs.getSynopsis(v)}'); } } }