2016-05-07 22 views
1

我有一個簡單的羣集,每個節點上都有一個名爲「service」的服務actor。此服務分別使用ClusterClientRecptionist公開,以便能夠使用集羣外部的ist,並使用ClusterClientAkka ActorSelection over a cluser

客戶端然後註冊在羣集的隨機節點上創建的用戶(因爲ClusterClient隨機調度)。例如節點1上的/user/service/user1和節點2上的/user/service/user2

我現在想要做的是向所有註冊用戶發送一條消息,而與他們的物理位置無關。我通過使用像/user/service/*這樣的ActorSelection很容易。但是這隻能解析相應節點上的本地交流者。

我用Java的方式工作。

回答

1

選項1

我剛通過使用DistributedPubSubMediatorthis question描述和記載here解決它。

private ActorRef mediator = DistributedPubSub.get(getContext().system()).mediator(); 

@Override 
public void onReceive(Object msg) throws Exception { 
    String msgStr = msg.toString(); 
    String val = msgStr.substring(4); 
    if (msgStr.startsWith("add")) { 
     ActorRef act = context().actorOf(Props.create(User.class, val), val); 
     // subscribe the newly created user on topic "allUsers" 
     mediator.tell(new DistributedPubSubMediator.Subscribe("allUsers", act), self()); 
     System.out.println("user created: " + act); 
    } else if (msgStr.startsWith("say")) { 
     // broadcast text message to all subscribed users 
     mediator.tell(new DistributedPubSubMediator.Publish("allUsers", new Text(val)), self()); 
    } 
} 

選項2

第二成功的選擇是通過使用BroadcastGroup路由器。重要的是,在配置中啓用集羣:

akka.actor.deployment { 
    /allUsers { 
    router = broadcast-group 
    routees.paths = ["/user/service/*"] 
    cluster { 
     enabled = on 
     allow-local-routees = on 
    } 
    } 
} 

之後,它可以直接使用,如記錄。

ActorRef allUsers = system.actorOf(FromConfig.getInstance().props(), "allUsers"); 
[...] 
allUsers.tell(new Text(val), self());