public async Task GetKeyStatus(IProcessKeyStatus status) { logger.Log("Process " + Id + " sending key/value fetch for " + status.GetKey() + ":" + status.GetVersion() + ":" + status.GetTimeout()); IComputer remote; Task computerInterrupt; lock (this) { // use a lock to ensure memory safety since these are set on another thread remote = computer; computerInterrupt = computerCancellation; } Task interrupt = Task.WhenAny(computerInterrupt, AsyncCancelTask); StringBuilder sb = new StringBuilder(directory); sb.AppendFormat("?key={0}", status.GetKey()); sb.AppendFormat("&timeout={0}", status.GetTimeout()); sb.AppendFormat("&version={0}", status.GetVersion()); Task<IHttpResponse> completed; try { IHttpRequest request = HttpClient.Create(remote.ProcessServer + sb.ToString()); request.Timeout = status.GetTimeout() + 30000; Task<IHttpResponse> bail = interrupt.ContinueWith((t) => null as IHttpResponse); completed = await Task.WhenAny(bail, request.GetResponseAsync()); if (completed == bail) { logger.Log("Process " + Id + " abandoned property fetch due to interrupt"); return; } } catch (NotHttpException e) { string error = "Status fetch failed message " + e.Message + " status " + e.Response.StatusCode + ": " + e.Response.StatusDescription; logger.Log("Process " + Id + " got remote property fetch failure from " + remote.Name + " at " + remote.Host + ": " + error); status.OnCompleted(0, null, 1, error); return; } catch (Exception e) { string error = "Status fetch failed message " + e.ToString(); logger.Log("Process " + Id + " got remote property fetch failure from " + remote.Name + " at " + remote.Host + ": " + error); status.OnCompleted(0, null, 1, error); return; } using (IHttpResponse response = completed.Result) { try { using (MemoryStream ms = new MemoryStream()) { Task payload; using (Stream payloadStream = response.GetResponseStream()) { payload = await Task.WhenAny(interrupt, payloadStream.CopyToAsync(ms)); } if (payload == interrupt) { logger.Log("Process " + Id + " abandoned property fetch due to interrupt"); return; } logger.Log("Process " + Id + " completed property fetch"); UInt64 newVersion = UInt64.Parse(response.Headers["X-Dryad-ValueVersion"]); string stateString = response.Headers["X-Dryad-ProcessStatus"]; int exitCode = Int32.Parse(response.Headers["X-Dryad-ProcessExitCode"]); logger.Log("Process " + Id + " property fetch: " + status.GetKey() + ":" + newVersion + ":" + stateString); status.OnCompleted(newVersion, ms.ToArray(), exitCode, null); } } catch (NotHttpException e) { string error = "Status fetch failed message " + e.Message + " status " + e.Response.StatusCode + ": " + e.Response.StatusDescription; logger.Log("Process " + Id + " got remote property fetch failure from " + remote.Name + " at " + remote.Host + ": " + error); status.OnCompleted(0, null, 1, error); } catch (Exception e) { string error = "Header fetch failed message " + e.ToString() + " headers " + response.Headers; logger.Log("Process " + Id + " got remote property fetch failure from " + remote.Name + " at " + remote.Host + ": " + error); status.OnCompleted(0, null, 1, error); } } }
public void GetProcessStatus(IProcess ip, IProcessKeyStatus status) { Process process = ip as Process; Task.Run(() => process.GetKeyStatus(status)); }
public async Task GetKeyStatus(IProcessKeyStatus status) { logger.Log("Process " + Id + " sending key/value fetch for " + status.GetKey() + ":" + status.GetVersion() + ":" + status.GetTimeout()); IComputer remote; Task computerInterrupt; lock (this) { // use a lock to ensure memory safety since these are set on another thread remote = computer; computerInterrupt = computerCancellation; } Task interrupt = Task.WhenAny(computerInterrupt, AsyncCancelTask); StringBuilder sb = new StringBuilder(directory); sb.AppendFormat("?key={0}", status.GetKey()); sb.AppendFormat("&timeout={0}", status.GetTimeout()); sb.AppendFormat("&version={0}", status.GetVersion()); Task <IHttpResponse> completed; try { IHttpRequest request = HttpClient.Create(remote.ProcessServer + sb.ToString()); request.Timeout = status.GetTimeout() + 30000; Task <IHttpResponse> bail = interrupt.ContinueWith((t) => null as IHttpResponse); completed = await Task.WhenAny(bail, request.GetResponseAsync()); if (completed == bail) { logger.Log("Process " + Id + " abandoned property fetch due to interrupt"); return; } } catch (NotHttpException e) { string error = "Status fetch failed message " + e.Message + " status " + e.Response.StatusCode + ": " + e.Response.StatusDescription; logger.Log("Process " + Id + " got remote property fetch failure from " + remote.Name + " at " + remote.Host + ": " + error); status.OnCompleted(0, null, 1, error); return; } catch (Exception e) { string error = "Status fetch failed message " + e.ToString(); logger.Log("Process " + Id + " got remote property fetch failure from " + remote.Name + " at " + remote.Host + ": " + error); status.OnCompleted(0, null, 1, error); return; } using (IHttpResponse response = completed.Result) { try { using (MemoryStream ms = new MemoryStream()) { Task payload; using (Stream payloadStream = response.GetResponseStream()) { payload = await Task.WhenAny(interrupt, payloadStream.CopyToAsync(ms)); } if (payload == interrupt) { logger.Log("Process " + Id + " abandoned property fetch due to interrupt"); return; } logger.Log("Process " + Id + " completed property fetch"); UInt64 newVersion = UInt64.Parse(response.Headers["X-Dryad-ValueVersion"]); string stateString = response.Headers["X-Dryad-ProcessStatus"]; int exitCode = Int32.Parse(response.Headers["X-Dryad-ProcessExitCode"]); logger.Log("Process " + Id + " property fetch: " + status.GetKey() + ":" + newVersion + ":" + stateString); status.OnCompleted(newVersion, ms.ToArray(), exitCode, null); } } catch (NotHttpException e) { string error = "Status fetch failed message " + e.Message + " status " + e.Response.StatusCode + ": " + e.Response.StatusDescription; logger.Log("Process " + Id + " got remote property fetch failure from " + remote.Name + " at " + remote.Host + ": " + error); status.OnCompleted(0, null, 1, error); } catch (Exception e) { string error = "Header fetch failed message " + e.ToString() + " headers " + response.Headers; logger.Log("Process " + Id + " got remote property fetch failure from " + remote.Name + " at " + remote.Host + ": " + error); status.OnCompleted(0, null, 1, error); } } }