Service Fabric 在启动时生成 actor

Service Fabric spawn actor on startup

有没有办法要求系统在启动时生成特定的 actor。

目前我在演员注册后在Program.cs中激活我需要的演员集。

这工作正常,但我偶尔会收到 ReminderLoadInProgressException,因为正在激活的 actor 需要注册提醒,但在它尝试这样做时并非所有提醒都已加载。

是否有标准的方法来播种集群?

不,你需要一些东西来激活你的演员。

Program.cs 不是执行此操作的最佳位置,因为它的执行并不真正符合您服务的生命周期,正如您可能已经注意到的那样。

如果您需要在 actor 服务启动时激活一些 actor,那么在 actor 服务的 RunAsync 方法中执行此操作是一个不错的选择。您可以通过编写从中派生的服务来自定义您的 actor 服务,就像您编写有状态服务时所做的那样:

编辑:确保先致电并等待 base.RunAsync()!

class MyActorService : ActorService
{
    public MyActorService(StatefulServiceContext context, ActorTypeInformation typeInfo, Func<ActorBase> newActor)
        : base(context, typeInfo, newActor)
    { }

    protected async override Task RunAsync(CancellationToken cancellationToken)
    {
        await base.RunAsync(cancellationToken);

        var proxy = ActorProxy.Create<IMyActor>(new ActorId(0));
        await proxy.StartDoingStuff();
    }
}

然后注册您的 actor 服务,以便运行时知道使用它来托管您的 actor 实例:

static class Program
{
    private static void Main()
    {
        ActorRuntime.RegisterActorAsync<MyActor>(
            (context, actorType) => new MyActorService(context, actorType, () => new MyActor()))
            .GetAwaiter().GetResult();

        Thread.Sleep(Timeout.Infinite);
    }
}

只需确保 actor 方法是幂等的,因为每次启动 actor 服务的主副本时都会执行(在故障转移、资源平衡、应用程序升级等之后),但好的是它赢了' 在您的 actor 服务准备好之前执行,并且它将始终在服务启动时执行。

有关如何使用演员服务的更多信息,请参阅此处:https://azure.microsoft.com/en-us/documentation/articles/service-fabric-reliable-actors-platform/

无法发表评论,所以我将评论放在这里:

为了完整起见:如果您的 ActorService 子类没有默认名称(来自 ServiceManifest.xml - 例如您动态生成服务实例),您将不得不使用双参数 ActorProxy.Create 像这样重载:

var actor = ActorProxy.Create<IMyActor>(new ActorId(0), this.Context.ServiceName);

否则你会得到 "Service does not exist" 异常:

System.Fabric.FabricServiceNotFoundException: Service does not exist. 
---> System.Runtime.InteropServices.COMException: Exception from HRESULT: 0x80071BCD at
System.Fabric.Interop.NativeClient.IFabricServiceManagementClient4
.EndResolveServicePartition(IFabricAsyncOperationContext context)
...