ASP.NET Identity UserStore:为什么是 return 任务?
ASP.NET Identity UserStore: Why return Task?
我想知道这个问题有一段时间了,所有 UserStore
方法 return 一个 Task
或一个类型 Task<T>
,但为什么会这样?为什么不只是 return T?
我知道它们是 Aync 方法并且是 OWIN 中间件的一部分,这与它有什么关系吗?
我还注意到一些方法 return 一个普通的旧 Task
实际上 return 一个空的 Task
。
asp.net 网站的示例 return Task.FromResult<object>(null)
http://www.asp.net/identity/overview/extensibility/overview-of-custom-storage-providers-for-aspnet-identity。
我也看到了 Task.FromResult(0)
,如果我 return 一个带有 Action
的任务:
return new Task(() =>
{
context.User.Add(new User); context.SaveChanges()
})
那么Task
里面的Action
就不会被调用。为什么会这样,return 空 Task
有什么意义?在我看来 returning Task
类似于 void
方法,对吗?
首先,我真的会推荐您阅读 MSDN / Asynchronous Programming with Async and Await,这对于了解 async/await 的所有工作原理(幕后)非常有帮助。
实际使用这些技术的原因是 UserManager 实现通常意味着针对数据库工作,这在计算机时间是 "slow"(Jeff Atwood 关于该主题的精彩读物:http://blog.codinghorror.com/the-infinite-space-between-words/ ).
出于这个原因,UserManager 方法承诺在将来为您提供 TypeX
或 ResultY
,但这需要 时间 。为了在您的应用程序等待数据库响应时释放资源(例如),等待线程 进入睡眠状态 返回到线程池,并且可以使用释放的容量对于另一个传入请求(或在此期间可能已异步完成的任何任务)。
编辑:谢谢@Neil Hibbert
根据 MSDN/异步编程文档:
Asynchrony is essential for activities that are potentially blocking,
such as when your application accesses the web. Access to a web
resource sometimes is slow or delayed. If such an activity is blocked
within a synchronous process, the entire application must wait. In an
asynchronous process, the application can continue with other work
that doesn't depend on the web resource until the potentially blocking
task finishes.
数据库调用(特别是在 Microsoft Azure 等云环境中)正在阻塞 I/O 进程,因此 ASP.NET 身份系统中的大多数 API 都是异步的。
为什么空Task
? return清空 Task
是 Async/Await Programming
模型中的最佳实践。异步方法有三种可能的 return 类型:Task
、Task<T>
;和 void
,但是异步方法的自然 return 类型只是 Task
和 Task<T>
。当从同步代码转换为异步代码时,任何 returning 类型 T
的方法都变成了 returning Task<T>
的异步方法,而任何 returning void
成为异步方法 returning Task
.
- Async void 方法具有不同的错误处理语义。当一个
async Task 或 async Task
方法抛出异常,
该异常被捕获并放置在 Task 对象上。使用异步
void 方法,没有 Task 对象,因此抛出任何异常
async void 方法的 将直接在
async void 方法时处于活动状态的 SynchronizationContext
开始了。
- Async void 方法具有不同的组合语义。异步方法
returning Task 或 Task
可以使用 await 轻松组合,
Task.WhenAny、Task.WhenAll 等等。异步方法 returning void
没有提供一种简单的方法来通知调用代码他们已经
完全的。启动几个 async void 方法很容易,但是
不容易确定他们什么时候完成。异步无效方法将
在开始和结束时通知他们的 SynchronizationContext,但是
自定义 SynchronizationContext 是常规的复杂解决方案
申请代码。
- Async void 方法很难测试。因为差异
在错误处理和组合中,很难编写单元测试
调用 async void 方法。 MSTest 异步测试支持
仅适用于异步方法 returning Task 或 Task
。这是可能的
安装一个 SynchronizationContext 来检测所有异步无效的时间
方法已经完成并收集了任何异常,但是它太多了
更容易只制作异步无效方法 return 任务。
您应该更喜欢 async Task
而不是 async void
。 Async Task
方法使错误处理、可组合性和可测试性更容易。有关更多信息,请阅读这篇文章:Best Practices in Asynchronous Programming
我想知道这个问题有一段时间了,所有 UserStore
方法 return 一个 Task
或一个类型 Task<T>
,但为什么会这样?为什么不只是 return T?
我知道它们是 Aync 方法并且是 OWIN 中间件的一部分,这与它有什么关系吗?
我还注意到一些方法 return 一个普通的旧 Task
实际上 return 一个空的 Task
。
asp.net 网站的示例 return Task.FromResult<object>(null)
http://www.asp.net/identity/overview/extensibility/overview-of-custom-storage-providers-for-aspnet-identity。
我也看到了 Task.FromResult(0)
,如果我 return 一个带有 Action
的任务:
return new Task(() =>
{
context.User.Add(new User); context.SaveChanges()
})
那么Task
里面的Action
就不会被调用。为什么会这样,return 空 Task
有什么意义?在我看来 returning Task
类似于 void
方法,对吗?
首先,我真的会推荐您阅读 MSDN / Asynchronous Programming with Async and Await,这对于了解 async/await 的所有工作原理(幕后)非常有帮助。
实际使用这些技术的原因是 UserManager 实现通常意味着针对数据库工作,这在计算机时间是 "slow"(Jeff Atwood 关于该主题的精彩读物:http://blog.codinghorror.com/the-infinite-space-between-words/ ).
出于这个原因,UserManager 方法承诺在将来为您提供 TypeX
或 ResultY
,但这需要 时间 。为了在您的应用程序等待数据库响应时释放资源(例如),等待线程 进入睡眠状态 返回到线程池,并且可以使用释放的容量对于另一个传入请求(或在此期间可能已异步完成的任何任务)。
编辑:谢谢@Neil Hibbert
根据 MSDN/异步编程文档:
Asynchrony is essential for activities that are potentially blocking, such as when your application accesses the web. Access to a web resource sometimes is slow or delayed. If such an activity is blocked within a synchronous process, the entire application must wait. In an asynchronous process, the application can continue with other work that doesn't depend on the web resource until the potentially blocking task finishes.
数据库调用(特别是在 Microsoft Azure 等云环境中)正在阻塞 I/O 进程,因此 ASP.NET 身份系统中的大多数 API 都是异步的。
为什么空Task
? return清空 Task
是 Async/Await Programming
模型中的最佳实践。异步方法有三种可能的 return 类型:Task
、Task<T>
;和 void
,但是异步方法的自然 return 类型只是 Task
和 Task<T>
。当从同步代码转换为异步代码时,任何 returning 类型 T
的方法都变成了 returning Task<T>
的异步方法,而任何 returning void
成为异步方法 returning Task
.
- Async void 方法具有不同的错误处理语义。当一个
async Task 或 async Task
方法抛出异常, 该异常被捕获并放置在 Task 对象上。使用异步 void 方法,没有 Task 对象,因此抛出任何异常 async void 方法的 将直接在 async void 方法时处于活动状态的 SynchronizationContext 开始了。 - Async void 方法具有不同的组合语义。异步方法
returning Task 或 Task
可以使用 await 轻松组合, Task.WhenAny、Task.WhenAll 等等。异步方法 returning void 没有提供一种简单的方法来通知调用代码他们已经 完全的。启动几个 async void 方法很容易,但是 不容易确定他们什么时候完成。异步无效方法将 在开始和结束时通知他们的 SynchronizationContext,但是 自定义 SynchronizationContext 是常规的复杂解决方案 申请代码。 - Async void 方法很难测试。因为差异
在错误处理和组合中,很难编写单元测试
调用 async void 方法。 MSTest 异步测试支持
仅适用于异步方法 returning Task 或 Task
。这是可能的 安装一个 SynchronizationContext 来检测所有异步无效的时间 方法已经完成并收集了任何异常,但是它太多了 更容易只制作异步无效方法 return 任务。
您应该更喜欢 async Task
而不是 async void
。 Async Task
方法使错误处理、可组合性和可测试性更容易。有关更多信息,请阅读这篇文章:Best Practices in Asynchronous Programming