zio / zio-actors

A high-performance, purely-functional library for building, composing, and supervising typed actors based on ZIO
https://zio.dev/zio-actors
Apache License 2.0
265 stars 56 forks source link
actor-model functional-programming scala zio

ZIO Actors

ZIO Actors is a high-performance, purely functional library for building, composing, and supervising typed actors based on ZIO.

Production Ready CI Badge Sonatype Releases Sonatype Snapshots javadoc ZIO Actors

Introduction

The Actor Model is used to build distributed highly scalable applications. The core concept behind the actor model is the ability to create multiple actors which run concurrently. The actor would receive a message do some computation on the message and then output a new message. Each actor runs independently of each other with no shared state between them and as such failure of one actor won't have an affect on the running of another. In its simplest form the goal of this project is to provide the ability to write actors in Functional Way that are typed leveraging ZIO.

ZIO Actors is based on the Actor Model which is a conceptual model of concurrent computation. In the actor model, the actor is the fundamental unit of computation, unlike the ZIO concurrency model, which is the fiber.

Each actor has a mailbox that stores and processes the incoming messages in FIFO order. An actor allowed to:

Some characteristics of an Actor Model:

Here's list of contents available:

Installation

To use this library, we need to add the following line to our library dependencies in build.sbt file:

libraryDependencies += "dev.zio" %% "zio-actors" % "0.1.0"

Akka actors also has some other optional modules for persistence (which is useful for event sourcing) and integration with Akka toolkit:

libraryDependencies += "dev.zio" %% "zio-actors-persistence"      % "0.1.0"
libraryDependencies += "dev.zio" %% "zio-actors-persistence-jdbc" % "0.1.0"
libraryDependencies += "dev.zio" %% "zio-actors-akka-interop"     % "0.1.0"

Example

Let's try to implement a simple Counter Actor which receives two Increase and Get commands:

import zio.actors.Actor.Stateful
import zio.actors._
import zio.clock.Clock
import zio.console.putStrLn
import zio.{ExitCode, UIO, URIO, ZIO}

sealed trait Message[+_]
case object Increase extends Message[Unit]
case object Get      extends Message[Int]

object CounterActorExample extends zio.App {

  // Definition of stateful actor
  val counterActor: Stateful[Any, Int, Message] =
    new Stateful[Any, Int, Message] {
      override def receive[A](
          state: Int,
          msg: Message[A],
          context: Context
      ): UIO[(Int, A)] =
        msg match {
          case Increase => UIO((state + 1, ()))
          case Get      => UIO((state, state))
        }
    }

  val myApp: ZIO[Clock, Throwable, Int] =
    for {
      system <- ActorSystem("MyActorSystem")
      actor  <- system.make("counter", Supervisor.none, 0, counterActor)
      _      <- actor ! Increase
      _      <- actor ! Increase
      s      <- actor ? Get
    } yield s

  override def run(args: List[String]): URIO[zio.ZEnv, ExitCode] =
    myApp
      .flatMap(state => putStrLn(s"The final state of counter: $state"))
      .exitCode
}

Resources

Documentation

Learn more on the ZIO Actors homepage!

Contributing

For the general guidelines, see ZIO contributor's guide.

Code of Conduct

See the Code of Conduct

Support

Come chat with us on Badge-Discord.

License

License