Iota coproducts (or ‘from those Weekdays, these Writers’) – part 2

Previously on Scalera…

Let’s remember that, on previous post, we defined our favourite weekday subset as a co-product:

case object Monday
case object Tuesday
case object Wednesday
case object GroundhogDay

import iota._
import iota.syntax.all._
import TList.::

type Weekday = Cop[Monday.type :: Tuesday.type :: Wednesday.type :: TNil]

Now imagine we wanted to define a serializer for our weekdays…


Assuming that our serializer is something like this:

trait Writer[T] {
  def write(t: T): String
object Writer {
  def apply[T](implicit w: Writer[T]): Writer[T] = w

And that it has several weekday defined instances:

implicit val mondayW: Writer[Monday.type] =
  _ => "monday"

implicit val tuesdayW: Writer[Tuesday.type] =
  _ => "TUESDAY"

implicit val wednesdayW: Writer[Wednesday.type] =
  _ => "wed"

implicit val madeUpdayW: Writer[GroundhogDay.type] =
  _ => "nonsense!"

…is not a big deal: a type class with its instances.
The question now is, how can we define a generic serializer for Weekday?

The first part of the party of the first part…

We know that

Weekday = Monday U Tuesday U Wednesday

So if we have defined Writer[Monday.type], Writer[Tuesday.type] and Writer[Wednesday.type], we could say that weekday serializer will be:

WeekdayWriter = Writer[Monday.type] U Writer[Tuesday.type] U Writer[Wednesday.type]

The question is, how can we map each weekday with its serializer? Well, the answer is with the following complex (and simple) snippet:

import TList.Op.Map
type WeekdayWriter = Cop[Map[Writer, Weekday#L]]

We’ve defined the weekdays serializer as the coproduct result of mapping(Map) each T type – contained inside the Weekday TList that composes the co-product(Weekday#L) – to the Writer[T] type.

In other words, internally the compiler has done something remotely similar (mind the gap between types and instances – compile time vs runtime) to:

val weekdays = List(Monday, Tuesday, Wednesday)
val writers ={
  case Monday    => Writer[Monday.type]
  case Tuesday   => Writer[Tuesday.type]
  case Wednesday => Writer[Wednesday.type]

From now on, WeekdayWriter can’t be any other type appart from Writer[T] where T is defined inside Weekday.

Yes, but now you have two different unrelated co-products

Yep, true. Let’s establish the relationship.

…shall be known in this contract as the first part of the party of the first part…

We know that we want something similar to this:

def weekdayWriter[D](weekday: D)(implicit stuff): WeekdayWriter = ???

Which implicit evidences do we need?

  • D can be anything, but we need it to have a Writer[D](if it can’t be serialized, it’s worthless)
  • something that tell us that Writer[D] is one of the included writers in WeekdayWriter. As we explained on the previous post, this evidence is Cop.Inject.

So the method would like this:

def weekdayWriter[D](
  weekday: D)(
  implicit w: Writer[D],
  ev: Cop.Inject[Writer[D], WeekdayWriter]): WeekdayWriter = {

  //So if we know that w is injectable into WeekdayWriter...
  w.inject[WeekdayWriter] //Let's inject it

we could define a helper for making it even prettier though:

implicit class AnyWeekdayWriter[D](
  day: D)(
  implicit w: Writer[D],
  ev: Cop.Inject[Writer[D], WeekdayWriter]){

  def write: String =
    weekdayWriter(day).value match {
      case w: Writer[D@unchecked] => w.write(day)

If we try it, we’ll notice that:

Monday.write //"monday"
Tuesday.write //"TUESDAY"
GroundhogDay.write //NOPE! It doesn't compile

…even though there’s an implicit Writer[GroundhogDay.type], as there’s no evidence that proves that it’s injectable into the WeekdayWriter co-product, it’s not serializable as a Weekday.

So what does this provide?

Let’s suppose the initial model:

sealed trait Weekday
case object Monday extends Weekday
case object Tuesday extends Weekday
case object Wednesday extends Weekday

implicit lazy val mondayW: Writer[Monday.type] = _ => "monday"
implicit lazy val tuesdayW: Writer[Tuesday.type] = _ => "TUES"
implicit lazy val wednesdayW: Writer[Wednesday.type] = _ => "wed"

How would you define a serializer for Weekday? Something logical would be:

implicit def weekdayWriter: Writer[Weekday] = {
  case Monday => mondayW.write(Monday)
  case Tuesday => tuesdayW.write(Tuesday)
  case Wednesday => wednesdayW.write(Wednesday)

If we decided to add a new day to the week we’d have to:

  • add the case object
  • make it extend from Weekday
  • add the concrete serializer
  • modify the generic serializer

Whereas the focus we’ve used so far would involve:

  • adding the case object
  • modifying Weekday definition
  • adding the concrete serializer

…okay, that’s not a big deal re-factoring but, what would it happen if we wanted to group those days in another way, for example, by odd days?

With the co-product focus would be as simple as defining the new co-product that stands for the type union of the odd days, as well as the function for getting the implicit Writer[T]:

type OddDay = Cop[Monday.type :: Wednesday.type :: TNil]

type OddDayWriter = Cop[Map[Writer, OddDay#L]]
def odddayWriter[D](
  oddday: D)(
  implicit w: Writer[D],
  ev: Cop.Inject[Writer[D], OddDayWriter]): OddDayWriter = {

And in the inheritance world, where there’s suffering and death…

sealed trait Weekday
sealed trait OddDay
case object Monday extends Weekday with OddDay
case object Tuesday extends Weekday
case object Wednesday extends Weekday with OddDay

implicit def weekdayWriter: Writer[OddDay] = {
  case Monday => mondayW.write(Monday)
  case Wednesday => wednesdayW.write(Wednesday)

Although this is heavy metal, we hope we’ve helped you having a better understanding about the fascinating coproduct world.

See you next post.
Peace out!

Iota coproducts (or how to make weeks shorter) – part 1

You may (or may not) remember that we occasionally mentioned co-products when we spoke about algebraic data types. We defined them as the natural way of expressing type union(Wine = White U Red U Espumoso). In this post we’ll try to define new enumerations expressed as co-products, for example, weekdays….

Intro: product vs. co-product

Just to sum up and to better understand the example, imagine you have a triplet of certain type elements:

(Int, String, Double)

If the data that stands for a student may be expressed as a triplet of her age AND name AND average score, we could say that a student may be expressed as the product of these three types:

case class Student(
  age: Int,
  name: String,
  avg: Double)

(Surprisingly case classes extend from something called scala.Product, ehem …)

On the other hand, if we’re told that the result of some web request may return the number of error rows OR the value we wanted to retrieve OR the amount of seconds to wait until next request try, we would be talking about a co-product.

Intro: helpless co-products in Scala

In Scala, defining an enumeration as a co-product can be as easy as:

sealed trait Color
case object Blue extends Color
case object Red extends Color

But, what happens when the co-product former types are not related between them (Int, Animal, …)?

Well, we could use Either type:

type Or[A, B] = Either[A, B]
val v1: Int Or String = Left(2)
val v2: Int Or String = Right("hi")

Easy, right? But, what happens now if we want to point that the value could be an Int or String or Boolean? Things become more complicated:

type Or[A, B] = Either[A, B]
val v1: Or[String, Or[Int, Boolean]] = Left("hi")
val v2: Or[String, Or[Int, Boolean]] = Right(Left(2))
val v2: Or[String, Or[Int, Boolean]] = Right(Right(true))

iota co-products

One of the alternatives for avoiding this headache is iota, a library developed by 47deg for defining co-products in an awesome way.
It both supports scalaz and cats. In this post, we’ll see how it’s applicable to cats (because reasons…)


In order to start compiling this, we’ll start by adding some cats-core and iota-core dependencies to our project:

scalacOptions += "-Ypartial-unification" // Needed if you're using Scala 2.11+
libraryDependencies ++= Seq(
  "org.typelevel" %% "cats-core" % "1.0.1",
  "io.frees" %% "iota-core" % "0.3.4"

Start point

Let’s suppose we have to define an enumeration.
One of the most common ways to achieve it in Scala, as we mentioned somewhere before, would be with:

sealed trait Weekday
case object Monday extends Weekday
case object Tuesday extends Weekday
case object Wednesday extends Weekday
case object Thursday extends Weekday
case object Friday extends Weekday
case object Saturday extends Weekday
case object Sunday extends Weekday

Nevertheless, let’s skip some extra days (for making it simpler) and let’s remove the inheritance relationship (for making it more interesting):

case object Monday
case object Tuesday
case object Wednesday
case object GroundhogDay //Just for messing things up...

For expressing now the type union ( Weekday = Monday U Tuesday U Wednesday) we define with iota the co-product this way:

// Let's import some iota core stuff (including syntax)
import iota._
import iota.syntax.all._

// ...and also import TList (which it's something really similar to a Shapeless HList)
// it keeps info about the contained element types.
import TList.::

type Weekday = Cop[Monday.type :: Tuesday.type :: Wednesday.type :: TNil]

And after these wonderful mayan glyphs, how do we use the Weekday type?
Because the following definitively doesn’t work:

val day: Weekday = Monday //NOPE! It doesn't fit

For being able to use it, we’ll have to check how to inject Monday.type into our co-product.
If your very first reaction to the previous sentence was ‘eing?’, take a look at the following section about injection and projection concepts. Otherwise, jump onto page 30 for killing the troll skip next section.

Inject & Project

Without giving a full-detail view about injective and projective modules, let’s see an easy example for better understanding these concepts.
Let’s imagine I have defined the weekdays co-product as a case class with all possible values as Options so only one of these can be fulfilled:

// Crazy stuff BTW,
// defining a co-product as a product of Option's
case class Weekday(
  monday: Option[Monday.type] = None,
  tuesday: Option[Tuesday.type] = None,
  wednesday: Option[Wednesday.type] = None){

    val defined =
      List(monday, tuesday, wednesday)
    defined <= 1
  }, "A Weekday can only be one of the options")

object Weekday {
  def inject(day: Monday.type): Weekday =

  def inject(day: Tuesday.type): Weekday =

  def inject(day: Wednesday.type): Weekday =

With this definition we try to illustrate that Monday.type is not actually a Weekday sub-type, but there’s a function (inject) that makes us able to create a Weekday from a Monday.type: this function injects the value into the co-product.

The projection, on the other hand, stands for the reverse process.
Within the same example previously showed we can say that, from a Weekday we can project its ‘tuesday’ part. As this field might be empty, we return it as an Option value:

object Weekday {

  // ... all previously defined stuff goes here ...

  def projectM(wd: Weekday): Option[Monday.type] =

  def projectT(wd: Weekday): Option[Tuesday.type] =

  def projectW(wd: Weekday): Option[Wednesday.type] = 


And how can you do this with iota?

Easy peasy! Just by using the Cop.Inject type class, which is used for establishing the relationship between one of the types that composes the co-product and the co-product itself.
In our case, for injecting a Monday into a Weekday, we need the implicit evidence that it’s injectable:

type Weekday = Cop[Monday.type :: Tuesday.type :: Wednesday.type :: TNil]

implicitly[Cop.Inject[Monday.type, Weekday]]

Thanks to this evidence, we’ll be able of doing:

val wd: Weekday = Monday.inject[Weekday]

and also of retrieving the Monday projection from any Weekday:

val wd: Weekday = Tuesday.inject[Weekday]
val monday: Option[Monday.type] =
  Cop.Inject[Monday.type, Weekday].prj(wd)
assert(monday.isEmpty, "It's actually a wednesday!")

At next post, we’ll see how to generate serializers for these co-products: pure gold…

Peace out!

Scalera tip: Uncle SAM

Today’s Scalera tip (and it’s been a while since last published tip) is about one of the Scala 2.12 version features that we fancy the most regarding the possibility of avoiding too much boilerplate.

Uncle SAM

Let’s suppose we’ve defined a type class that gathers certain amount of common implemented functionality like:

trait Comparisson[T]{

  def compare(t1: T, t2: T): Int

  def greaterThan(t1: T, t2: T): Boolean =
    compare(t1, t2) > 0

  def greaterEqualThan(t1: T, t2: T): Boolean =
    compare(t1, t2) >= 0

  def equalTo(t1: T, t2: T): Boolean =
    compare(t1, t2) == 0

  def lowerThan(t1: T, t2: T): Boolean =
    compare(t1, t2) < 0

  def lowerEqualThan(t1: T, t2: T): Boolean =
    compare(t1, t2) <= 0


…in that case the remaining job would consist on defining the compare method.
For creating the different instances of Comparisson we could either create implicit vals or implicit objects (nothing new about type classes so far):

object Comparisson {

  implicit val intComparisson: Comparisson[Int] =
    new Comparisson[Int]{
      def compare(t1: Int, t2: Int): Int = t1 - t2

  implicit val booleanComparisson: Comparisson[Boolean] =
    new Comparisson[Boolean] {
      def compare(t1: Boolean, t2: Boolean): Int = {
        List(t1, t2)
          .map(b => if (b) 1 else 0)
          .reduce(_ - _)


Defining anonymous Comparisson instances (or extending from that trait in case of objects) was the only way of defining these instances so far.

With Scala’s 2.12 version a new concept known as SAM (Single Abstract Method) comes up. It basically allows defining an anonymous instance by providing a function equivalent to the only abstract method of the trait/abstract class.

When applying to the proposed example:

object Comparisson {

  implicit val intComparisson: Comparisson[Int] =
    (t1: Int, t2: Int) => t1 - t2

  implicit val booleanComparisson: Comparisson[Boolean] =
    (t1: Boolean, t2: Boolean) =>
      List(t1, t2)
        .map(b => if (b) 1 else 0)
        .reduce(_ - _)


Cute, right? Just as a reminder, do have in mind that if we don’t explicitly type the expression, the compiler won’t understand that it has to do its magic and it will assume that what we’ve just implicitly defined is a mere function:

object Comparisson {
  implicit val intComparisson =
    (t1: Int, t2: Int) => t1 - t2

  //  The previous inferred type will be (Int, Int) => Int


And we’re not telling this because it already happened to us…

Peace out!

Abstract alge… what? Functors and cucumbers

Category mania! Are we paid for speaking about it? I’m afraid we don’t. Would we like to? Very likely. In previous posts we spoke about monoids and monads, but now it’s functor’s time. Functors are everywhere and we can prove it. Before reviewing its different kinds, let’s focus on key concepts.

What’s a morphism?

It’s just a transformation between two structures, a change between spaces, a mutation.
In Scala? A simple function:

val f: A => B

What’s a functor?

Quick and simple answer: the behavior that defines, for a certain F[A] type constructor, the map method.

trait Functor[F[_]]{
  def map[A, B](fA: F[A])(f: A => B): F[B]

There are functors for List, Option, Future, Try, …

object ListFunctor extends Functor[List]{
  def map[A, B](fA: List[A])(f: A => B): List[B] =
    fA match {
      case Nil => Nil
      case (head :: rest) =>
        f(head) +:
object OptionFunctor extends Functor[Option]{
  def map[A, B](fA: Option[A])(f: A => B): Option[B] =
    fA match {
      case None => None
      case Option(a) => Option(f(a))

Actually, apart from the famous map method, they should fit into a couple of properties:

  • Identity morphism: F[Id[A]] = Id[F[A]]. For example, being identity the identity function defined in Scala, Option(identity(1)) == identity(Option(1))
  • Morphism composition: If we have two morphisms f: A => B and g: B => C, it must be checked that F[f o g] = F[f] o F[g]. It’s not as complicated as it seems:
    val f: Int => String = _.toString
    val g: String => Boolean = _.length > 1
    val l: List[Int] = List(1,20,3) == andThen g) == => g(f(n)))
    //List(false, true, false)

Even though, we can describe functors (in the context of a F[_] production chain) as the instructions for transforming some given A input value into some B output value within the same F[_] production chain, by using a morphism (a transformation function) A => B.

Functor types

Ordinary functors are also known as co-variant functors (in order to differentiate itself from contravariant and invariant functors). Let’s se what makes the difference between these different kinds of functor:

Contravariant Functor

Formal definition says that a F[_] functor is contravariant if, instead of having the map method, it has a contramap method defined:

trait Contravariant[F[_]]{
  def contramap[A, B](fA: F[A])(f: B => A): F[B]

That’s it: if it exists a function B => A, the contramap method defines F[A] => F[B].

…ok, let’s stop being so hardcore. We’ll illustrate it with an example.

Imagine a type class that knows how to compare certain type elements:

type Comparison = Int
val Greater = 1
val Equal = 0
val Lower = -1

trait Comparator[T]{
  def compare(t1: T, t2: T): Comparison

Imagine as well, that I know how to compare integer numbers (and here comes the tricky tip):

if I know how to compare integers and I know how to convert ‘cucumbers’ into integer numbers, I do know how to compare ‘cucumbers’

object ComparatorF extends Contravariant[Comparator]{
  def contramap[A, B]
    (fA: Comparator[A])
    (f: B => A): Comparator[B] =
    new Comparator[B]{
      def compare(t1: B, t2: B): Comparison =, f(t2))

And now, the so-expected example about how to generate a contravariant functor for cucumbers:

trait Cucumber
val intC: Comparator[Int] = ???
val cucumberToInt: Cucumber => Int = ???
val cucumberC: Comparator[Cucumber] =
  ComparatorF.contramap(intC)(cucumberToInt) Cucumber{}, new Cucumber{})


Invariant functors

Invariant functors for F[_] are determined by the imap method:

trait Invariant[F[_]] {
  def imap[A, B](fA: F[A])(f: A => B)(g: B => A): F[B]

…once again the doubt is killing you: I know and I beg you for some time to explain properly. Let’s see some example.

Imagine a type class that knows how to store stuff in some database (MongoDB, for example):

case class ObjectId(hash: String)

trait DataStorage[T]{
  def store(t: T): ObjectId
  def get(id: ObjectId): T

If we forget about possible effects (exceptions, timeouts and so) for not messing up the example, we could define an invariant functor for DataStorage that allows storing any-kind elements:

object DataStorageF extends Invariant[DataStorage]{
  def invariant[A, B]
    (fA: DataStorage[A])
    (f: A => B)
    (g: B => A): DataStorage[B] = {

    new DataStorage[B]{
      def store(b: B): Option[ObjectId] =
      def get(id: ObjectId): B =


If I know how to store integers and I know how to convert integers into cucumbers (and the other way round), I know how to store cucumbers!

val intDS: DataStorage[Int] = ???
val cucumberToInt: Cucumber => Int = ???
val intToCucumber: Int => Cucumber = ???
val cucumberDS: DataStorage[Cucumber] =

val id = Cucumber{})
val originalCucumber = cucumberDS.get(id)

We couldn’t say this is all, but it may be a good introduction to the wonderful functor world. See you in the next poxt. ‘Like’ and share if you like storing cucumbers.
Peace out!

[1] Advanced Scala with Cats – Noel Welsh & Dave Gurnell
[2] Variance and functors – Typelevel blog

Monoids are not demode and thursdays are actually the new fridays

No, it’s not the latest Coixet’s movie title. When we talk about cathegories like monoids, we tend to think they just remain on the edge as something merely experimental (even though purely functional) and there’s no direct application at the real world. Something similar happened when you learnt square roots at school and there was no proper moment to start using them at real life…

The use case

This morning, ah naïve me, I tried to make this work:

type Passengers = Int
type MaxCapacity = Passengers
type Plane = (Passengers, MaxCapacity)

val planes: List[Plane] =
  List(1 -> 1, 2 -> 3, 3 -> 3)

val (totalPassengers, totalCapacity) = 
//  ERROR: Could not find implicit value 
//  for parameter num: Numeric[(Int, Int)]

Ok, fair enough, Scala needs something, an evidence, for adding integer tuples.
Before we start fighting with the ‘evidence’, let’s try to make it work in a more mechanical way:

val sum = ((0,0) /: planes){
    case ((totalPas,totalCap), (passengers, capacity)) => 
      (totalPas + passengers, totalCap + capacity)

Okay, it works. But it should be simpler, so let’s get back to the idea of Numeric[N] evidence.

Implementing Numeric[N]

We need a Numeric[(A,B)] but before implementing it (it has a lot of abstract methods) let’s sweep under the rug all those methods we don’t really want to focus on in this example. For doing so, let’s create an intermediate layer that keeps all those method without an implementation (which doesn’t mean ‘abstract’):

trait LeanNumeric[T] extends Numeric[T] {
  override def fromInt(x: Int): T = ???
  override def toInt(x: T): Int = ???
  override def minus(x: T, y: T): T = ???
  override def times(x: T, y: T): T = ???
  override def negate(x: T): T = ???
  override def toLong(x: T): Long = ???
  override def toFloat(x: T): Float = ???
  override def toDouble(x: T): Double = ???
  override def compare(x: T, y: T): Int = ???

Let’s call this abomination LeanNumeric (it only contains the essentials to develop our example). And now, we can define the method that generates the evidence for any Tuple2:

implicit def numeric[A, B](
  implicit nA: Numeric[A],
  nB: Numeric[B]): Numeric[(A, B)] = {
  new LeanNumeric[(A, B)]{
    override def zero = (,
    override def plus(x: (A, B), y: (A, B)): (A, B) = {
      val (a1, b1) = x
      val (a2, b2) = y
      (, a2),, b2))

If we put the implicit into scope and we run again planes.sum…boom! Magic.


We don’t have to master category theory to realize that Numeric[N] may be a thousand of things, but it satisfies at least two properties:

  • The append operation: The sum operation – given n1 and n2 of type N, it return a new N element. Only because of this feature(and the closure, associativity, commutative, …) we can consider it a Semigroup.

  • And additionally the zero element

Seriously? Isn’t it obvious enough? My dear friends, monoid is back in town!

Implementation with scalaz.Monoid

Having in mind that Numeric has (at least) these two properties, let’s re-implement the implicit by using scalaz Monoid. We first define the monoid for integers and the tuple monoid which requires a monoid for each type that compounds the tuple (easy peasy):

import scalaz._

implicit object IntMonoid extends Monoid[Int]{
  override def zero: Int = 0
  override def append(f1: Int, f2: => Int): Int = f1 + f2

implicit def tupleMonoid[A,B](
  implicit mA: Monoid[A],
  mB: Monoid[B]): Monoid[(A,B)] = {
  new Monoid[(A, B)] {
    override def zero: (A, B) = (,
    override def append(f1: (A, B), f2: => (A, B)): (A, B) = {
      val (a1, b1) = f1
      lazy val (a2, b2) = f2
      (mA.append(a1,a2), mB.append(b1, b2))

So good so far, right?

After that, we implement the implicit that will provide a Numeric as long as there’s a Monoid for the type

implicit def numeric[T](
  implicit m: Monoid[T]): Numeric[T] = {
  new LeanNumeric[T]{
    override def zero =
    override def plus(x: T, y: T): T = m.append(x, y)

planes.sum //(6,7)

And it’s awesomely easy to get abstract of whatever T means (a tuple? a dog? …). As long as it’s a monoid, you can define a LeanNumeric.

You can find here the gist.

See you in the next functional madness.

Peace out!

Scalera tip: Handling sticky implicit contexts

A couple of days ago (translation for the masses: like a month ago) I noticed Viktor Klang was tweeting about removing the annoying implicit evidences from methods. And some things I read seemed so elegant to me that I was forced to share some related ideas with all of you that don’t follow him at Twitter (@viktorklang).

Setting some context

Imagine the typical polymorphic method where we need an execution context for evaluating some Future:

import scala.concurrent.{ExecutionContext, Future}

def myMethod[T]
  (element: T)
  (implicit ev: ExecutionContext): Future[Boolean] = ???

You could say it’s as typical as disgusting, having to repeat the same exact words in the following 10 method definitions: (implicit ev: ExecutionContext).

Playing with type alias

The happy idea that is being proposed is to define a type alias like the following one:

type EC[_] = ExecutionContext

This way, by adding some syntax sugar, we would re-define the method signature:

def myMethod[T:EC](element: T): Future[Boolean] = ???

Beautiful, isn’t it?

Some other possibilities

Non-polymorphic methods

In case our method isn’t parameterized, we would have to add some boilerplate (by adding a wildcard for the type that parameterizes the method). In essence, it should be working the same principle:

def myMethod[_:EC](element: Int): Future[Boolean] = ???

Multiple implicit contexts

The not-so-crazy case in which we needed several implicit parameters of different natures, we would have to define as many type alias as different type parameters we required:

type EC[_] = ExecutionContext
type MongoDB[_] = MongoDBDatabase

def myMethod[_:EC:MongoDB](element: Int): Future[Boolean] = ???

But what if …?

Multiple implicit parameters with same type

In case we have several implicit parameters that share the same type,

def myMethod
  (element: Int)
  (implicit ev1: ExecutionContext, ev2: ExecutionContext): Future[Boolean] = ???

it turns out that …

Well, by definition that’s impossible given that it would incur in some ambiguity issue when resolving implicits. It’s true that Scala allows having these kind of signatures, but we could only invoke them by making explicit the arguments contained in the second parameter group.:


which is kind of…

Type-constructor implicit contexts

When we have implicit parameters that are also type constructors like List[T], Future[T], Option[T]

…well, it actually depends.

Case 1

If the type that parameterizes the method and the one that parameterizes the evidence are not related, there’s no big deal: we define another type alias and move on:

type EC[_] = ExecutionContext
type MongoDB[_] = MongoDBDatabase
type IntOpt[_] = Option[Int]
type StrList[_] = List[String]

def myMethod[_:EC:MongoDB:IntOpt:StrList](
  element: Int): Future[Boolean] = ???

Which would be equivalent to:

def myMethod(
  element: Int)(
  implicit ev1: ExecutionContext,
  ev2: MongoDBDatabase,
  ev3: Option[Int],
  ev4: List[String]): Future[Boolean] = ???

Case 2

If the type that parameterizes the method and the one that parameterizes the evidence have to match …

Well, it’s not possible. The syntax sugar we’re using here implies that both types have to match. Maybe it was too pretty for our bodies 🙂

See you in the next post. Peace out!

Scalera tip: Keep your actor’s state with no VAR at all!

It’s pretty well known that using VARs is, apart from unethical, the evil itself, some kind of hell, it make kitties die and many other stuff you might probably heard before and that could eventually be the cause of a painfull slowly dead.

The essence of functional programming is therefore the immutability: every time I mutate an element, I actually generate a new one.

What about Akka actors?

When we talk about actors, we can define them as stateful computation units that sequentially process a message queue by reacting(or not) to each of these messages.

It’s always been said that, in order to keep state within some actor’s logic, it was ok to use VARs:

It’s impossible that concurrency problems happen: it’s the actor itself and nobody else who access that var and will only process one message at a time.

But maybe, we could renounce to this premise if we look for some way to redefine the actor’s behavior based on a new state.

Mortal approach

If we follow the previously described philosophy, the very first (and more straight forward) approach for keeping some actor’s state would be pretty similar to the following:

class Foo extends Actor{
  var state: Int = 0
  override def receive = {
    case Increase => state += 1

Every time an Increase arrives, we modify the state value by adding 1.
So easy so far, right?

Immutable approach

Nevertheless, we could define a receive function parameterized by certain state, so when a message arrives, this parameter is the state to take into account.

If the circumstances to mutate the state took place, we would just invoke the become method that would modify the actor’s behavior. In our case, that behavior mutation would consist on changing the state value.

If we use the previously defined example:

class Foo extends Actor{
  def receive(state: Int): Receive = {
    case Increase =>
        receive(state + 1),
        discardOld = true)
  override def receive = receive(0)

we can notice that the function defined by receive is parameterized by some state argument. When some Increase message arrives, what we perform is an invocation to become for modifying the actor’s behavior, passing as an argument the new state to handle.

If we wanted some extra legibility, we could even get abstract from every updatabe-state actor:

trait SActor[State] extends Actor {
  val initialState: State
  def receive(state: State): Receive
  def update(state: State): Receive =
      discardold = true)
  override def receive =

this way, we just have to define the initial state of some actor, a new parameterized receive function and a new update function that takes care of performing the proper become call as explained before.
With all these in mind, we now have some cuter brand new Foo actor:

class Foo extends SActor[Int] {
  val initialState = 0
  def receive(state: Int): Receive = {
    case Increase => update(state +1)

Potential hazardous issues

Please, do notice that in the featuring example, we’ve used a second argument for become: discardOld = true. This argument settles whether the new behavior should be stashed on the top of the older one, or ‘au contraire’ it should completely substitute the previous behavior.

Let’s suppose we used discardOld = false. If every single time a new Increase message arrived we had to stash a new behavior, we could obtain a wonderful overflow issue.

See you in the next tip.

Peace out 🙂