[英]How do I pass security principal from my request into a thread in asp.net MVC
In my ASP.net MVC application I have a request that does a lot of calculations to return the result. 在我的ASP.net MVC应用程序中,我有一个请求,它会执行大量计算以返回结果。 This works fine on my own servers, but when I move to Azure the connection/request gets closed after 4 minutes so I don't ever get the results back I just get an error. 这在我自己的服务器上工作正常,但是当我移动到Azure时,连接/请求在4分钟后关闭,所以我没有得到结果我只是得到一个错误。
To resolve this I was planning to run the long calculation in a thread and have the client poll to see when it is done. 为了解决这个问题,我计划在一个线程中运行长计算并让客户端轮询以查看它何时完成。
I have tried all sorts of ways of doing this (threads, thread pools, tasks and hangfire) but i can't get the security context/principal/identity to pass from my request to my new thread. 我已经尝试了各种各样的方法(线程,线程池,任务和hangfire),但我不能让安全上下文/主体/身份从我的请求传递到我的新线程。
Here is some sudo code for what I am doing. 这是我正在做的一些sudo代码。 (I realize that there should be some better synchronization for multiple requests, but this is sudo code) (我意识到多个请求应该有更好的同步,但这是sudo代码)
public static void SlowCalculation(params)
{
_calculationIsRunning = true;
var principal = System.Security.Principal.GenericPrincipal.Current;
if (principal?.IsInRole("MySecurityGroup") ?? false)
{
// lots of long calculations
_resutsAreReady = true;
_calculationIsRunning = true;
}
}
//
// POST: /Get/
public ActionResult GetResults(params)
{
if (_calculationIsRunning)
return View("InProgress");
else if (_resutsAreReady)
return View("Results", results);
else
// start the calcualtion on a new thread to avoiding having very long running connection that azure will close
System.Threading.Tasks.Task.Run(() => SlowCalculation(params));
}
The security check that I show in SlowCalculation is actually berried way down in some libraries I use, so I don't really want to change that if I can help it. 我在SlowCalculation中显示的安全检查在我使用的某些库中实际上已经过时了,所以如果我能帮助它,我真的不想改变它。 I just want to get the principal from my request into my thread. 我只是想从我的请求中获取主体到我的主题。
I have tried passing the identity into the thread function, but it gets disposed when the request completes. 我已经尝试将标识传递给线程函数,但是在请求完成时它会被释放。
Why are you trying to check the security principal in each thread. 为什么要尝试检查每个线程中的安全主体。 You only need to check the security principal before running the SlowCalculation method. 您只需在运行SlowCalculation方法之前检查安全主体。
Or if you really want to 或者,如果你真的想
public static void SlowCalculation(params, System.Security.Principal.GenericPrincipal principal)
{
_calculationIsRunning = true;
if (principal.IsInRole("MySecurityGroup") ?? false)
{
// lots of long calculations
_resutsAreReady = true;
_calculationIsRunning = true;
}
}
//
// POST: /Get/
public ActionResult GetResults(params)
{
if (_calculationIsRunning)
return View("InProgress");
else if (_resutsAreReady)
return View("Results", results);
else
{
// start the calcualtion on a new thread to avoiding having very long running connection that azure will close
var principal = System.Security.Principal.GenericPrincipal.Current;
System.Threading.Tasks.Task.Run(() => SlowCalculation(params, principal));
}
}
It's not a good idea to have long running background threads in an ASP.NET process. 在ASP.NET进程中长时间运行后台线程并不是一个好主意。 The proper way to solve this is to put a calculation request on the Azure service bus for example and have some worker process be notified of this and run the calculation. 解决此问题的正确方法是在Azure服务总线上放置计算请求,并通知某个工作进程并运行计算。
You can do your authorization check in the web application and have the worker process execute the calculation without authorization check. 您可以在Web应用程序中执行授权检查,并让工作进程在未经授权检查的情况下执行计算。 If the calculation depends on the user's identity, things get a little more difficult as you'll need to deal with the possibility of session/token expiration. 如果计算取决于用户的身份,那么事情会变得更加困难,因为您需要处理会话/令牌过期的可能性。 See my question here for how to deal with that. 在这里查看我的问题,了解如何处理。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.