我已经实现了一个 Web API。
<authentication mode="None" />
我正在使用基本授权,并在我的 AuthorizeAttribute 中设置 Thread.CurrentPrincipal。
第一次启动/调试应用程序后,我提交了一个请求,设置了 Thread.CurrentPrincipal(使用 IsAuthenticated = true)服务器端,并且 IsAuthenticated 在我的 Controller 中按预期返回 true。但是,此后的任何请求都会将 Thread.CurrentPrincipal 设置为正常,但是当执行命中我的 Controller 方法时, Controller 的 User.Identity 属性已更改,并且 IsAuthenticated = false。
我无法弄清楚为什么 IsAuthenticated=true 仅在启动应用程序后第一次出现?!每次都应该如此,因为我正在手动设置 Thread.CurrentPrinciple,但在那里和我的 Controller 之间的某个地方,它正在被替换!
更新
这与我添加的 MediaTypeFormatter 有关。当我删除格式化程序时,我没有遇到问题。执行的格式化程序代码如下:
public override Task<object> ReadFromStreamAsync(Type type, System.IO.Stream webStream, System.Net.Http.HttpContent content, IFormatterLogger formatterLogger)
{
return Task.Factory.StartNew(() =>
{
string temporaryFilePath = Path.Combine(TemporaryDirectory, Path.GetRandomFileName());
using (FileStream fileStream = new FileStream(temporaryFilePath, FileMode.CreateNew, FileAccess.Write, FileShare.Read))
{
webStream.CopyTo(fileStream);
}
return (object)new CustomFile(temporaryFilePath);
});
}
最佳答案
here 详细解释了答案。
总之,设置 Thread.CurrentPrincipal 是不够的。我现在也设置了 HttpContext.Current.User,它正在工作。
在最初的帖子中,MediaTypeFormatter 上的异步方法被调用,创建了额外的线程,导致 CurrentPrinciple 被附加到某个其他线程,而不是您的 Controller 操作最终被执行的那个线程。
至于为什么一定要设置在两个地方,可以在 here 找到说明。它说:
关于.net - WebApi : User. Identity.IsAuthenticated 第一次请求为真,之后为假,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/17089207/