MVC3 中使用 HttpWebRequest 进行异步发布
我遇到过 HttpWebRequest 的一种行为,我认为这是有意的,但由于我无法找到任何明确说明这是正确的来源,所以我想我会将其作为问题发布,看看是否有人遇到过此问题和/或可以验证这是正确的。
首先,我有一个在 IIS 7.5 上运行的 MVC3 应用程序。它有 1 个控制器,支持 1 个 post 方法。我在 IIS 中启用了 Windows 身份验证和 ASP.NET 模拟。 MVC3 应用程序背后的想法只是拥有一个简单的服务,可用于记录来自各种客户端应用程序(控制台应用程序、silverlight、asp.net、AJAX 等)的信息。该服务所做的事情之一是使用控制器中的 User 属性来记录向该服务发布数据的人。
为了简化消费应用程序的处理,我创建了一些客户端库、Silverlight、DotNet 和一个 js 库。
除了在另一个 MVC3 应用程序中使用 DotNet 库时,这一切都按预期进行。对于 DotNet 库,我使用 HttpWebRequest 并使用异步方法 (Begin/EndGetRequestStream)/(Begin/EndGetResponse) 来发布请求。我还将请求上的 .Credentials 设置为 CredentialCache.DefaultCredentials,但是当日志记录应用程序开始处理来自另一个 MVC3 应用程序的请求时,它会将用户显示为从中接收帖子的应用程序池的服务帐户。
当我发现这一点时,我将帖子的同步版本添加到 DotNet 库,并发现日志记录服务正在使用我的个人凭据。
我假设 HttpWebRequest 可能会使用不同的 DefaultCredentials,具体取决于使用它的上下文。由于这是 asp.net 并且正在调用请求的异步方法,因此在客户端 MVC3 应用程序返回响应之前,我的库代码可能尚未完成。
我无法确定情况是否确实如此。如果有人有答案或一篇文章可以为我指明正确的方向,我将不胜感激。
提前致谢
I've run come across a behavior with HttpWebRequest that I believe is intended, but as I have not been able to find any source that definitively says this is correct, I thought I would post it as a question and see if anyone has encountered this and/or can verify this is correct.
For starters I have an MVC3 app running on IIS 7.5. It has 1 controller and supports 1 post method. I have Windows Auth and ASP.NET Impersonation enabled within IIS. The idea behind the MVC3 app is just to have a simple service that can be used for logging information from a variety of client applications(console apps, silverlight, asp.net, AJAX, etc). One of the things the service does is uses the User property from the controller to also log who the person who posted data to this service.
To simplify the processing for the consuming applications I created some client libraries, Silverlight, DotNet, and a js library.
This all worked out as expected except when using the DotNet library within another MVC3 application. For the DotNet library I'm using an HttpWebRequest and using the asynchronous methods (Begin/EndGetRequestStream)/(Begin/EndGetResponse) to post the request. I'm also setting the .Credentials on the request to CredentialCache.DefaultCredentials, but when the logging application starts the processing of the request from another MVC3 app it shows the User as the service account of the app pool from which the post was received.
When I found this I added a synchronous version of the post to the DotNet library and found that the logging service was using my personal credentials.
I assume that HttpWebRequest could be using different DefaultCredentials depending on the context in which it is used. Since this is asp.net and the async method of the request are being called, my library code may not have even finished before the client MVC3 app has returned a response.
What I haven't been able to find is if this is definitively the case or not. If anyone has and answer or or an article that could point me in the right direction I would greatly appreciate it.
Thanks in advance
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
我遇到的是有意的行为。问题的根源在于在处理异步请求时,.Net 线程池中的线程以何种身份执行。在我的例子中,线程作为应用程序池创建的应用程序域的所有者执行。就我而言,它是一个服务帐户。
我能够在开始任何异步处理之前捕获模拟用户的身份,并使用 WindowsImpersonationContext 强制我的库代码作为模拟用户运行。通过执行此操作,CredentialsCache.DefaultCredentials 在 HttpWebRequest 实例上设置它时使用了我的凭据(模拟用户)而不是运行应用程序池的帐户。
What I was encountering was intended behavior. The root of the problem comes down to under which identity do threads from the .Net thread pool execute when servicing the asynchronous requests. In my case the threads were executing as the owner of the app domain that was created by the app pool. In my case it was a service account.
I was able to capture the identity of the impersonated user prior to the start of any asychronous processing and use the WindowsImpersonationContext to force my library code to run as the impersonated user. By doing this CredentialsCache.DefaultCredentials used my credentials(impersonated user) instead of the account running the app pool when setting it on the HttpWebRequest instance.