首页 > 解决方案 > ServiceStack 消息 API:在 OnAfterInit 中使用 HostContet.AppHost.ExecuteMessage 会产生 NullReferenceException

问题描述

如前所述,我有时会使用这种方法在内部执行服务

IMessage theMessage = new Message<Startup>(new Startup());
var reply = HostContext.AppHost.ExecuteMessage(theMessage); // The way to get the pipeline to execute when we do internal call, and get DI to work etc

这工作得很好并且符合预期,除了在一种情况下:当我从OnAfterInit方法中调用它时,我会覆盖它。

这个想法是我想在 AppHost 准备好时做一些启动工作,在初始化之后,但是这样做时,它会失败并显示NullReferenceException

public override void OnAfterInit()
{
    base.OnAfterInit();

    IMessage theMessage = new Message<Startup>(new Startup());
    var reply = HostContext.AppHost.ExecuteMessage(theMessage); 
}

错误:

在此处输入图像描述

   at ServiceStack.ServiceStackHost.<ApplyRequestConvertersAsync>d__361.MoveNext() in C:\BuildAgent\work\3481147c480f4a2f\src\ServiceStack\ServiceStackHost.Runtime.cs:line 45
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter`1.GetResult()
   at ServiceStack.Host.ServiceController.ExecuteMessage(IMessage dto, IRequest req) in C:\BuildAgent\work\3481147c480f4a2f\src\ServiceStack\Host\ServiceController.cs:line 584
   at ServiceStack.ServiceStackHost.ExecuteMessage(IMessage mqMessage) in C:\BuildAgent\work\3481147c480f4a2f\src\ServiceStack\ServiceStackHost.cs:line 1486
   at Test.Test.OnAfterInit() in C:\Git\Test\Test.cs:line 59

似乎并非所有内容都已初始化并准备就绪。如果我这样做,它会起作用:

public override void OnAfterInit()
{
    base.OnAfterInit();
    System.Threading.Timer t = new System.Threading.Timer((o) => 
    {
        IMessage theMessage = new Message<Startup>(new Startup());
        var reply = HostContext.AppHost.ExecuteMessage(theMessage);
    }, null, 100, int.MaxValue);
}

我很高兴知道我是否遗漏了什么,以及是否有更好的方法来解决这个问题。定时器的东西有效,但它不适合我。

标签: servicestackmessaging

解决方案


理想情况下,执行服务应该在运行时而不是在启动时完成,但是如果您确实想要执行服务,您需要在启动的最后执行它们,此时 ServiceStack 的其余部分已经像在中一样初始化AfterInitCallbacks,例如:

AfterInitCallbacks.Add(host => 
    host.ExecuteMessage(new Message<Startup>(new Startup()));

推荐阅读