There is this note in the akka-stream docs stating as follows:
… a reusable flow description cannot be bound to “live” resources, any connection to or allocation of such resources must be deferred until materialization time. Examples of “live” resources are already existing TCP connections, a multicast Publisher, etc.; …
I have several questions concerning the note:
- Apart from the these two examples, what other resource counts as a live?
- Anything that cannot be safely (deep)copied? Like a
Thread
? - Should I also avoid sharing anything that's not thread-safe?
- Anything that cannot be safely (deep)copied? Like a
- What about an
ActorRef
existing in theActorSystem
used by theActorFlowMaterializer
? - How to defer allocation until materialization time? Is it safe for example to allocate it in the constructor of a
PushPullStage
but not in the create function of aFlowGraph
?
The problem here is a common problem if we consider webservices, RMI connections or any other communication protocol. It's always recommended sharing "primitive" values then references, because marshalling/unmarshalling or serializing/unserializing is always a headache. Also think of different types of environments communicating each other. Sharing solid values is a safe way to solve communication.
Akka by itself is a good example of "microservices" communicating actors each other. When I read the documentation of Akka, one good word defines Akka actors very well. Actors are like mailbox clients and you can think of each client has a mailbox. When you pass a variable, it's just like you got a new email.
Short result of long story, be avoid sharing "dependent" objects that can be invalidated before it's read from another actor. Additionally, if your system names actorRefs dynamically, avoid calling them by its reference.
"Materializing" is explained in docs of akka-streams.
So use parameters instead of passing "connection" itself.
Deferring a live resource is not a big think. That means if you use one connection for all system, you should keep it alive always. Or when you create a transaction in actor-1 and send it to actor-2, you shouldn't terminate the transaction in actor-1 until actor-2 finished its job with transaction.
Then how you can understand ? Then you use "Future" and "offer()".
Hope I understand your question and hope I can express myself.