-
-
Save rocc0/49e8623ff83859cf5028f6ecd5fbfe73 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package main | |
import ( | |
"log" | |
"os" | |
"os/signal" | |
"syscall" | |
"time" | |
"github.com/AsynkronIT/protoactor-go/actor" | |
) | |
func newInboundMiddleware() actor.ReceiverMiddleware { | |
cnt := 0 | |
return func(next actor.ReceiverFunc) actor.ReceiverFunc { | |
return func(ctx actor.ReceiverContext, envelope *actor.MessageEnvelope) { | |
cnt++ | |
log.Printf("Start handling incoming message #%d: %#v", cnt, envelope.Message) | |
next(ctx, envelope) | |
log.Printf("End handling incoming message #%d: %#v", cnt, envelope.Message) | |
} | |
} | |
} | |
func newOutboundMiddleware() actor.SenderMiddleware { | |
cnt := 0 | |
return func(next actor.SenderFunc) actor.SenderFunc { | |
return func(ctx actor.SenderContext, target *actor.PID, envelope *actor.MessageEnvelope) { | |
cnt++ | |
log.Printf("Start sending message #%d to %s", cnt, target.Id) | |
next(ctx, target, envelope) | |
log.Printf("End sending message #%d to %s", cnt, target.Id) | |
} | |
} | |
} | |
type ping struct{} | |
type pong struct{} | |
var context *actor.RootContext | |
func main() { | |
context = actor.EmptyRootContext | |
pongProps := actor. | |
PropsFromFunc(func(ctx actor.Context) { | |
switch ctx.Message().(type) { | |
case *ping: | |
ctx.Respond(&pong{}) | |
} | |
}) | |
pongPid, _ := context.SpawnNamed(pongProps, "pong") | |
// Output should be somewhat like below. | |
// Because ping actor receives both signal of struct{}{} and a pong message of &pong{}, | |
// the printed number of execution is doubled comparing to that of pong actor. | |
// | |
// 2018/11/24 12:59:25 Start handling incoming message #1: &actor.Started{} | |
// 2018/11/24 12:59:25 End handling incoming message #1: &actor.Started{} | |
// 2018/11/24 12:59:26 Start handling incoming message #2: struct {}{} | |
// 2018/11/24 12:59:26 Received signal | |
// 2018/11/24 12:59:26 Start sending message #1 to pong | |
// 2018/11/24 12:59:26 End sending message #1 to pong | |
// 2018/11/24 12:59:26 End handling incoming message #2: struct {}{} | |
// 2018/11/24 12:59:26 Start handling incoming message #3: &main.pong{} | |
// 2018/11/24 12:59:26 Received pong | |
// 2018/11/24 12:59:26 End handling incoming message #3: &main.pong{} | |
// 2018/11/24 12:59:27 Start handling incoming message #4: struct {}{} | |
// 2018/11/24 12:59:27 Received signal | |
// 2018/11/24 12:59:27 Start sending message #2 to pong | |
// 2018/11/24 12:59:27 End sending message #2 to pong | |
// 2018/11/24 12:59:27 End handling incoming message #4: struct {}{} | |
// 2018/11/24 12:59:27 Start handling incoming message #5: &main.pong{} | |
// 2018/11/24 12:59:27 Received pong | |
// 2018/11/24 12:59:27 End handling incoming message #5: &main.pong{} | |
// 2018/11/24 12:59:28 Start handling incoming message #6: struct {}{} | |
// 2018/11/24 12:59:28 Received signal | |
// 2018/11/24 12:59:28 Start sending message #3 to pong | |
// 2018/11/24 12:59:28 End sending message #3 to pong | |
// 2018/11/24 12:59:28 End handling incoming message #6: struct {}{} | |
// 2018/11/24 12:59:28 Start handling incoming message #7: &main.pong{} | |
// 2018/11/24 12:59:28 Received pong | |
// 2018/11/24 12:59:28 End handling incoming message #7: &main.pong{} | |
// ^C2018/11/24 12:59:29 Finish | |
pingProps := actor. | |
PropsFromFunc(func(ctx actor.Context) { | |
switch ctx.Message().(type) { | |
case struct{}: | |
log.Print("Received signal") | |
ctx.Request(pongPid, &ping{}) | |
case *pong: | |
log.Print("Received pong") | |
} | |
}). | |
WithReceiverMiddleware(newInboundMiddleware()). | |
WithSenderMiddleware(newOutboundMiddleware()) | |
pingPid, _ := context.SpawnNamed(pingProps, "ping") | |
finish := make(chan os.Signal, 1) | |
signal.Notify(finish, os.Interrupt) | |
signal.Notify(finish, syscall.SIGTERM) | |
ticker := time.NewTicker(1 * time.Second) | |
defer ticker.Stop() | |
for { | |
select { | |
case <-ticker.C: | |
context.Send(pingPid, struct{}{}) | |
case <-finish: | |
context.Poison(pingPid) | |
context.Poison(pongPid) | |
log.Print("Finish") | |
return | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment