private async Task <IActionResult> Process(Guid id, int revision, string verb, TransactionStatus state, int timeout) { var factory = new TransactionFactory(this.storage); Transaction trans; try { trans = await factory.ContinueTransactionAsync(id, revision); } catch (TransactionConflictException) { return(new StatusCodeResult(409)); } catch (TransactionMissingException) { return(this.NotFound()); } Task <Transaction> waitTask; try { var delta = await trans.CreateDelta(revision, false, (ref TransactionMutableData data) => { data.Expires = DateTime.UtcNow; data.Script = $"Handler.{verb}(Transaction);"; }); waitTask = this.storage.WaitForAsync(x => x.Id == id && (x.Status == state || x.Status == TransactionStatus.Failed), timeout); } finally { await trans.Free(); } if (timeout == 0) { return(new StatusCodeResult(202)); } var transaction = await waitTask; if (transaction == null) { return(new StatusCodeResult(202)); } return(this.Created(this.Url.RouteUrl("TransactionGetRevision", new { id = transaction.Id, revision = transaction.Revision }), TransactionMapper.ToTransactionResult(transaction))); }
public async Task <IActionResult> Post(Guid id, [FromRoute] int?revision, [FromBody] IDictionary <string, object> model) { var factory = new TransactionFactory(this.storage); Transaction trans; if (revision != null) { trans = await factory.ContinueTransactionAsync(id, (int)revision, -1); } else { trans = await factory.ContinueTransactionAsync(id); } Transaction result; try { DateTime?expires; if (model.ContainsKey("expires")) { if (model["expires"] == null) { expires = null; } else { if (model["expires"] is DateTime) { expires = (DateTime)model["expires"]; } else if (!DateTimeParser.TryParseDateTime(model["expires"] as string, out expires)) { return(this.BadRequest("The specified expiration date could not be parsed as standard ISO UTC time.")); } } } else { expires = trans.Expires; } TransactionStatus state; if (model.ContainsKey("state")) { if (!Enum.TryParse((string)model["state"], false, out state)) { return(this.BadRequest("Could not parse transaction state.")); } } else { state = trans.Status; } result = await trans.CreateDelta(trans.Revision + 1, false, (ref TransactionMutableData data) => { data.Expires = expires; data.Payload = model.ContainsKey("payload") ? model["payload"] : trans.Payload; data.Script = model.ContainsKey("script") ? model["script"] as string : trans.Script; data.Status = state; }); } finally { await trans.Free(); } return(this.Created(this.Url.RouteUrl("TransactionGet", new { id = result.Id }), result.ToTransactionResult())); }