c# - 服务执行期间的ServiceStack操作顺序问题
问题描述
我们正在从 v3.9.64 升级 ServiceStack v5.11.0 的经典 ASP.NET 应用程序,并渴望成为 ServiceStack 的付费客户。但我们必须解决这个问题。ServiceStack 中的生命周期和操作顺序发生了变化。ServiceStack 处理的请求生命周期中的某些点HttpContext.Current
尚未填充。我们所有的代码都希望设置它,因此我们必须在处理或请求中避免这种情况。以下是我们认为需要的操作顺序。
- 首先,
HttpContext.Current
必须由系统填充。 - 接下来,我们需要一个事件来触发我们的
AppHost : AppHostBase
,它允许我们初始化我们的中间层。我们目前正在尝试 AppHost.OnPreExecuteServiceFilter,但由于调用了插件,这被证明是有问题的。请继续阅读。 - 接下来,我们编写了一个插件来执行身份验证,该插件被添加到 AppHost.Configure 中的插件中。我们需要在第 2 步之后调用它。
- 然后我们希望调用我们的服务代码。
- 最后,我们需要调用 AppHost.OnEndRequest。
上面我们面临的问题是我们的身份验证插件在 AppHost.OnPreExecuteServiceFilter 之前被调用,所以我们的代码失败了,因为我们还没有初始化我们的中间层。所以目前第 2 步和第 3 步的顺序是错误的。我们如何解决这个问题?在填充 HttpContext.Current 之后和调用插件之前是否会触发不同的 AppHost 事件?或者我们可以将我们的插件配置为在 AppHost.OnPreExecuteServiceFilter 之后调用吗?
对此的进一步说明。在 v3.9.64 中,我们的 Global.Application_BeginRequest 和 EndRequest 事件被用于上述目的,并且一直运行良好。我确实看到这些事件是在传入的 ServiceStack 请求时触发的,但它们的发生顺序与以前不同,因此我们面临这个问题。
解决方案
操作顺序只是在 ServiceStack 请求中执行不同的钩子和过滤器的顺序。
OnPreExecuteServiceFilter
顾名思义,就是在服务执行之前执行的过滤器。
接下来,我们编写了一个插件来执行身份验证,该插件被添加到 AppHost.Configure 中的插件中。我们需要在第 2 步之后调用它。
AppHost.Configure()
仅在启动时执行一次,以配置您的 AppHost。如果您希望插件在请求期间执行逻辑,则需要注册在ServiceStack 请求管道中执行的自定义过滤器。
我们上面面临的问题是我们的身份验证插件在 AppHost.OnPreExecuteServiceFilter 之前被调用
此方法在执行服务之前执行,在此方法之后但在服务之前执行的唯一其他过滤器是服务过滤器和操作请求过滤器属性。
填充 HttpContext.Current 后是否触发了不同的 AppHost 事件
HttpContext.Current
在执行任何 ServiceStack Request 之前由 ASP.NET Framework 填充,这意味着它始终在ServiceStack Request pipeline中的任何过滤器之前填充。它不会被填充的主要原因是如果在运行时的请求期间没有从 ASP.NET 请求工作线程访问它。
在调用插件之前?
这是不可能回答的,因为您的问题遗漏了关于您的插件究竟在哪里注册其自定义处理程序的重要信息?即在此之前执行哪些过滤器取决于您的插件正在注册的请求过滤器。在请求期间执行不同处理程序的顺序记录在我们的操作顺序页面中。
如果您指的是您的插件Register(IAppHost)
,则此AppHost.Configure()
操作仅在启动时执行一次,您无法HttpContext.Current
在启动时访问,它仅在请求期间可用。启动初始化逻辑是您的插件将注册其请求过滤器的地方,例如,appHost.PreRequestFilters
或者appHost.GlobalRequestFilters
在执行 ServiceStack 服务之前的请求期间执行的过滤器。而在*ResponseFilters
服务执行之后执行。
NowHttpContext.Current
用于在请求上下文不可用时从单例上下文访问 ASP.NET 请求上下文,但这在 ServiceStack 中通常是不必要的,因为每个请求过滤器都可以从 ServiceStack 检索 ASP.NET 请求上下文IRequest.OriginalRequest
,例如:
PreRequestFilters.Add((req, res) =>
{
var aspReq = req.OriginalRequest as HttpRequestBase;
});
例如。在您可以访问的服务IRequest
中base.Request
。
推荐阅读
- windows - “npm run serve”在 Windows cmd 中给出错误
- javascript - 无法将 Ripple (Cryptocurrency Coin - XRP) 发送到钱包
- mysql - 如何从 MySQL DB 中的滚动计数中找到实际计数
- css - 如何 CSS onclick 重定向?
- android - aidl.exe'' 以非零退出值 -1073741701 结束
- python - 将复杂数据拟合到模型中
- java - 如何在 iBatis 中获得排序/排序的结果?
- python-3.x - 使用 3x3 卷积核将彩色图像转换为灰度图像
- c# - Npgsql替换连接字符串中的主机名
- php - 如何在 Symfony OneToMany 中进行搜索?