/// <summary> /// Called by the workflow runtime to execute an activity. /// </summary> /// <param name="context">The <see cref="ActionActivityContext"/> to associate with this activity and execution.</param> /// <param name="cancellationToken">The <see cref="CancellationToken"/> used to propagate notifications that the operation should be canceled.</param> /// <returns> /// The <see cref="ActionActivityResult"/> of the run task, which determines whether the activity remains in the executing state, or transitions to the closed state. /// </returns> public async Task <ActionActivityResult> ExecuteAsync(ActionActivityContext context, CancellationToken cancellationToken) { if (context.Contact != null) { var contact = await FindContactAsync(context, cancellationToken); if (contact != null) { PatchContact(contact, context.Contact); context.Contact = contact; } } var result = await ExecuteNodeAsync(context, cancellationToken); if (result == null) { throw new InvalidOperationException("Action result is required."); } // Preserve backward-compatibility and log each event received from old actions // without having an effect on the action result if (!result.HasLogAction) { await ExecuteNodeAsync(context.Clone(new ActionItem { Type = ActionType.Log, Enabled = true, Options = JObject.FromObject(new { Anonymous = true }) }), cancellationToken); } return(result); }
/// <summary> /// Invokes an activity. /// </summary> /// <param name="context">The <see cref="ActionActivityContext" /> to associate with this activity and execution.</param> /// <param name="actions">The actions.</param> /// <returns> /// The <see cref="ActionActivityResult" /> of the run task, which determines whether the activity remains in the executing state, or transitions to the closed state. /// </returns> private async Task <ActionActivityResult> ExecuteNodeListAsync(ActionActivityContext context, IEnumerable <ActionItem> actions, CancellationToken cancellationToken) { Debug.Assert(context != null); Debug.Assert(actions != null); ActionActivityResult status = null; foreach (var action in actions) { context = context.Clone(action); status = await ExecuteNodeAsync(context, cancellationToken); if (status.StatusCode == ActionActivityStatusCode.Success && status.ReturnUrl != null || status.StatusCode == ActionActivityStatusCode.Forbidden) { return(status); } } return(status ?? context.CreateResult(ActionActivityStatusCode.Failed)); }