异步ctp MVC4和工作流程

时间:2012-04-02 13:23:13

标签: asp.net-mvc task workflow-foundation-4 async-await

我有以下代码调用工作流程。我想知道我是否可以使用async ctp将控制器更改为异步。

public ActionResult Index()
    {
        var input = new Dictionary<string, object>();
        input["ViewData"] = this.ViewData;
        var userState = "BeginInvoke example";

        var invoker = new WorkflowInvoker(HelloMvcDefinition);

        Task workflowTask = Task.Factory.FromAsync<IDictionary<string, object>>(
            invoker.BeginInvoke(input, WorkflowCompletedCallback, userState),
            invoker.EndInvoke);

        workflowTask.Wait();

        return View();
    }

我试过这个,但我似乎无法让它起作用:

public async Task<ActionResult> Index()
    {
        var input = new Dictionary<string, object>();
        input["ViewData"] = this.ViewData;
        var userState = "BeginInvoke example";

        var invoker = new WorkflowInvoker(HelloMvcDefinition);

        Task workflowTask = Task.Factory.FromAsync<IDictionary<string, object>>(
            invoker.BeginInvoke(input, WorkflowCompletedCallback, userState),
            invoker.EndInvoke);

        await workflowTask;

        return View();
    }

不幸的是,这个观点似乎不起作用。关于我做错了什么想法?

EDIT 在接受建议后,我已将方法更改为此

public class HelloController : AsyncController
{
    private static readonly HelloWorkflow HelloMvcDefinition = new HelloWorkflow();

    public Task<ViewResult> Index()
    {
        var input = new Dictionary<string, object>();
        input["ViewData"] = ViewData;
        const string userState = "BeginInvoke example";

        var invoker = new WorkflowInvoker(HelloMvcDefinition);

        return Task.Factory.FromAsync<IDictionary<string, object>>(
            invoker.BeginInvoke(input, WorkflowCompletedCallback, userState),
            invoker.EndInvoke).ContinueWith(t => View());
    }       

    static void WorkflowCompletedCallback(IAsyncResult result)
    {

    }
}

哪个工作正常,所以问题必须是我如何使用async关键字。

由于

2 个答案:

答案 0 :(得分:1)

我们可以使用TAP模式调用Windows工作流,如下所示 - (详情见我的博文http://tweetycodingxp.blogspot.com/2013/06/invoke-workflow-wf-using-task-based.html

public async Task<ActionResult> Index(string id)
{
    var wfInputArgs = new Dictionary<string, object>
    {
        ...
    };

    var wfOutputArgs = await Task<IDictionary<string, object>>.Factory.StartNew(
        () => WorkflowInvoker.Invoke(new MyWorkflow(), wfInputArgs));
    var result = wfOutputArgs["Output1"] as IEnumerable<Class1>;
    ...
    return View(model);
}

答案 1 :(得分:0)

AsyncController而不是Controller派生。

编辑:如果操作返回已完成的Task,您可能还会遇到known bug,其中ASP.NET MVC4将挂起。您可以通过在操作方法的顶部添加await Task.Yield();来解决此错误。

在一个不相关的说明中,此代码更有效(也更短):

var workflowTask = Task.Factory.FromAsync(invoker.BeginInvoke, invoker.EndInvoke,
    input, userState);