static async Task <R> Run <R>(ICmd <Task <R> > cmd, R fail, After after) { try { var result = await cmd.Execute(); after.ProcessOk(); return(result); } catch (Exception e) { after.ProcessFailed(e); return(fail); } }
/// <summary> /// The residence of the listening-socket thread, one for each of the <see cref="ICmd"/> /// </summary> /// <param name="cmd"></param> /// <param name="cmdPort"></param> protected internal void HostCmd(ICmd cmd, int cmdPort) { using (var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp)) { //this should NOT be reachable from any other machine var endPt = new IPEndPoint(IPAddress.Loopback, cmdPort); socket.Bind(endPt); socket.Listen(Constants.SOCKET_LISTEN_NUM); for (; ; )//ever { try { var buffer = new List<byte>(); var client = socket.Accept(); PrintToConsole($"Connect from port {cmdPort}"); var data = new byte[Constants.DEFAULT_BLOCK_SIZE]; //park for first data received client.Receive(data, 0, data.Length, SocketFlags.None); buffer.AddRange(data.Where(b => b != (byte)'\0')); while (client.Available > 0) { if (client.Available < Constants.DEFAULT_BLOCK_SIZE) { data = new byte[client.Available]; client.Receive(data, 0, client.Available, SocketFlags.None); } else { data = new byte[Constants.DEFAULT_BLOCK_SIZE]; client.Receive(data, 0, (int)Constants.DEFAULT_BLOCK_SIZE, SocketFlags.None); } buffer.AddRange(data.Where(b => b != (byte)'\0')); } var output = cmd.Execute(buffer.ToArray()); client.Send(output); client.Close(); } catch (Exception ex) { PrintToConsole(ex); } } } }
/// <summary> /// The residence of the listening-socket thread, one for each of the <see cref="ICmd"/> /// </summary> /// <param name="cmd"></param> /// <param name="cmdPort"></param> protected internal void HostCmd(ICmd cmd, int cmdPort) { using (var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp)) { //this should NOT be reachable from any other machine var endPt = new IPEndPoint(IpAddress, cmdPort); PrintToConsole($"Listening on port {cmdPort}"); socket.Bind(endPt); socket.Listen(SOCKET_LISTEN_NUM); for (; ;) //ever { try { var buffer = new List <byte>(); var client = socket.Accept(); var data = new byte[NfConfig.DefaultBlockSize]; //park for first data received client.Receive(data, 0, data.Length, SocketFlags.None); buffer.AddRange(data.Where(b => b != (byte)'\0')); while (client.Available > 0) { var avail = client.Available; data = avail < NfConfig.DefaultBlockSize ? new byte[avail] : new byte[NfConfig.DefaultBlockSize]; client.Receive(data, 0, data.Length, SocketFlags.None); buffer.AddRange(data.Where(b => b != (byte)'\0')); if (client.Available <= 0) { Thread.Sleep(NfConfig.ThreadSleepTime);//give it a moment } } var output = cmd.Execute(buffer.ToArray()); client.Send(output); client.Close(); } catch (Exception ex) { PrintToConsole(ex); } } } }
private async Task ExecuteCmd(SocketMessage message, ICmd cmd, CaptureCollection args) { try { CancellationTokenSource cancelSource = new CancellationTokenSource(TimeSpan.FromSeconds(Config.Timeout)); Task executeTask = cmd.Execute(new Call(this, message, args, cancelSource.Token)); await executeTask; bool cancelled = cancelSource.IsCancellationRequested; cancelSource.Dispose(); if (cancelled) { throw new TimeoutException(); } else if (executeTask.Exception != null) { Exception exc = executeTask.Exception; while (exc.InnerException != null) { exc = exc.InnerException; } throw exc; } } catch (TimeoutException) { Trace.TraceWarning(strings.CmdOutOfTime); await message.Channel.SendMessageAsync( "The bot ran out of time to respond! Try again shortly."); } catch (Exception exc) { StringBuilder excBuilder = new StringBuilder(); excBuilder.Append("A command failed to execute: "); excBuilder.Append(exc.Message); excBuilder.AppendLine(); excBuilder.AppendLine(); excBuilder.Append(exc.StackTrace); Trace.TraceError(excBuilder.ToString()); await message.Channel.SendMessageAsync(strings.CmdFailedToExecute); } }