Full example code
Here below is the complete source code from the three classes, Greeter
, GreeterBot
, GreeterMain
and AkkaQuickstart
, that creates the sample application:
Greeter.java
package $package$;
import akka.actor.typed.ActorRef;
import akka.actor.typed.Behavior;
import akka.actor.typed.javadsl.*;
import java.util.Objects;
// #greeter
public class Greeter extends AbstractBehavior<Greeter.Greet> {
public static record Greet(String whom, ActorRef<Greeted> replyTo) {}
public static record Greeted(String whom, ActorRef<Greet> from) {}
public static Behavior<Greet> create() {
return Behaviors.setup(Greeter::new);
}
private Greeter(ActorContext<Greet> context) {
super(context);
}
@Override
public Receive<Greet> createReceive() {
return newReceiveBuilder().onMessage(Greet.class, this::onGreet).build();
}
private Behavior<Greet> onGreet(Greet command) {
getContext().getLog().info("Hello {}!", command.whom());
//#greeter-send-message
command.replyTo().tell(new Greeted(command.whom(), getContext().getSelf()));
//#greeter-send-message
return this;
}
}
// #greeter
GreeterBot.java
package $package$;
import akka.actor.typed.Behavior;
import akka.actor.typed.javadsl.*;
public class GreeterBot extends AbstractBehavior<Greeter.Greeted> {
public static Behavior<Greeter.Greeted> create(int max) {
return Behaviors.setup(context -> new GreeterBot(context, max));
}
private final int max;
private int greetingCounter;
private GreeterBot(ActorContext<Greeter.Greeted> context, int max) {
super(context);
this.max = max;
}
@Override
public Receive<Greeter.Greeted> createReceive() {
return newReceiveBuilder().onMessage(Greeter.Greeted.class, this::onGreeted).build();
}
private Behavior<Greeter.Greeted> onGreeted(Greeter.Greeted message) {
greetingCounter++;
getContext().getLog().info("Greeting {} for {}", greetingCounter, message.whom());
if (greetingCounter == max) {
return Behaviors.stopped();
} else {
message.from().tell(new Greeter.Greet(message.whom(), getContext().getSelf()));
return this;
}
}
}
GreeterMain.java
package $package$;
import akka.actor.typed.ActorRef;
import akka.actor.typed.Behavior;
import akka.actor.typed.javadsl.*;
public class GreeterMain extends AbstractBehavior<GreeterMain.SayHello> {
public static class SayHello {
public final String name;
public SayHello(String name) {
this.name = name;
}
}
private final ActorRef<Greeter.Greet> greeter;
public static Behavior<SayHello> create() {
return Behaviors.setup(GreeterMain::new);
}
private GreeterMain(ActorContext<SayHello> context) {
super(context);
//#create-actors
greeter = context.spawn(Greeter.create(), "greeter");
//#create-actors
}
@Override
public Receive<SayHello> createReceive() {
return newReceiveBuilder().onMessage(SayHello.class, this::onSayHello).build();
}
private Behavior<SayHello> onSayHello(SayHello command) {
//#create-actors
ActorRef<Greeter.Greeted> replyTo =
getContext().spawn(GreeterBot.create(3), command.name);
greeter.tell(new Greeter.Greet(command.name, replyTo));
//#create-actors
return this;
}
}
AkkaQuickstart.java
package $package$;
import akka.actor.typed.ActorSystem;
import java.io.IOException;
public class AkkaQuickstart {
public static void main(String[] args) {
//#actor-system
final ActorSystem<GreeterMain.SayHello> greeterMain = ActorSystem.create(GreeterMain.create(), "helloakka");
//#actor-system
//#main-send-messages
greeterMain.tell(new GreeterMain.SayHello("Charles"));
//#main-send-messages
try {
System.out.println(">>> Press ENTER to exit <<<");
System.in.read();
} catch (IOException ignored) {
} finally {
greeterMain.terminate();
}
}
}
As another best practice we should provide some test coverage.