Skip to content

Instantly share code, notes, and snippets.

View adamw's full-sized avatar

Adam Warski adamw

View GitHub Profile
@adamw
adamw / t8.scala
Last active September 20, 2019 06:18
val insertUserInTx: IO[Int] = insertUser.transact(transactor)
// (2) BEGIN; INSERT; COMMIT; sendEmail();
val result2: IO[Unit] = insertUserInTx.flatMap(_ => sendEmail)
// (3) sendEmail(); BEGIN; INSERT; COMMIT;
val result3: IO[Int] = sendEmail.flatMap(_ => insertUserInTx)
@adamw
adamw / t7.scala
Last active September 20, 2019 06:19
// Re-useable effect descriptions
val sendEmail: IO[Unit] = IO(println("Sending email"))
val insertUser: ConnectionIO[Int] =
sql"INSERT INTO users(name, email) VALUES('Emily', 'emily@email.com')"
.update.run
// (1) BEGIN; INSERT; sendEmail(); COMMIT;
val insertThenSend: ConnectionIO[Unit] =
insertUser.flatMap(_ => sendEmail.to[ConnectionIO])
@adamw
adamw / t6.scala
Last active September 20, 2019 06:18
val sendEmail: IO[Unit] = IO(println("Sending email"))
val sendEmailWithConnection: ConnectionIO[Unit] =
sendEmail.to[ConnectionIO]
val sendEmailInTx: IO[Unit] = sendEmailWithConnection.transact(transactor)
@adamw
adamw / t5.sql
Last active September 20, 2019 07:21
(1) BEGIN; INSERT; sendEmail(); COMMIT;
(2) BEGIN; INSERT; COMMIT; sendEmail();
(3) sendEmail(); BEGIN; INSERT; COMMIT;
(4) BEGIN; sendEmail(); INSERT; COMMIT;
@adamw
adamw / t4.scala
Created September 19, 2019 16:11
def insertPerson(p: Person): ConnectionIO[Int] =
sql"INSERT INTO persons(name, age) VALUES(${p.name}, ${p.age})".update.run
def countPersons: ConnectionIO[Int] =
sql"SELECT COUNT(*) FROM persons".query[Int].unique
val insertAndCount =
insertPerson(Person("Pedro", 81)).flatMap(_ => countPersons)
@adamw
adamw / t3.scala
Last active September 20, 2019 06:16
val transactor: Transactor[IO] = ???
val result: IO[List[Person]] = personsQuery.transact(transactor)
val persons: List[Person] = result.unsafeRunSync()
@adamw
adamw / t2.scala
Last active September 20, 2019 06:16
// details on creating a transactor are omitted
val transactor: Transactor[IO] = ???
val result: IO[List[Person]] = personsQuery.transact(transactor)
@adamw
adamw / t1.scala
Last active September 19, 2019 16:10
import doobie._
import doobie.implicits._
case class Person(name: String, age: Int)
val personsQuery: ConnectionIO[List[Person]] =
sql"SELECT p.name, p.age FROM persons p".query[Person].to[List]
@adamw
adamw / workshop.md
Last active October 11, 2020 07:57

Functional Scala CRUD

We'll be adding a feature to Bootzooka, a skeleton Scala microservice/web application project.

This will involve using doobie, monix, tapir, http4s, circe and compile-time dependency injection.

If you'd like to follow along:

  1. make sure you have Java & sbt installed. You can use sdkman for Java and popular package manages for sbt (e.g. brew)
  2. git clone https://github.com/softwaremill/bootzooka.git
val TestConfig: Config = DefaultConfig
.modify(_.email.emailSendInterval)
.setTo(100.milliseconds)