Skip to content

Instantly share code, notes, and snippets.

@manjuraj
Last active December 30, 2015 02:39
Show Gist options
  • Save manjuraj/7763661 to your computer and use it in GitHub Desktop.
Save manjuraj/7763661 to your computer and use it in GitHub Desktop.
DI using cake
// from: http://jonasboner.com/2008/10/06/real-world-scala-dependency-injection-di
// (1).
case class User(username: String, password: String)
trait UserRepositoryComponent {
val userRepository: UserRepository
class UserRepository {
def create(user: User): Unit = println(s"create $user")
}
}
trait UserServiceComponent {
self: UserRepositoryComponent =>
val userService: UserService
class UserService {
def create(username: String, password: String): Unit =
userRepository.create(User(username, password))
}
}
object ComponentRegistry extends UserServiceComponent with UserRepositoryComponent {
val userRepository = new UserRepository
val userService = new UserService
}
// (2). same as (1) but separating interface from implementation
case class User(username: String, password: String)
trait UserRepositoryComponent {
val userRepository: UserRepository
trait UserRepository {
def create(user: User): Unit
}
}
trait UserRepositoryComponentImpl extends UserRepositoryComponent {
override val userRepository: UserRepository = new UserRepositoryImpl
private class UserRepositoryImpl extends UserRepository {
override def create(user: User) = println(s"create $user")
}
}
trait UserServiceComponent {
val userService: UserService
trait UserService {
def create(username: String, password: String): Unit
}
}
trait UserServiceComponentImpl extends UserServiceComponent {
self: UserRepositoryComponent =>
override val userService: UserService = new UserServiceImpl
private class UserServiceImpl extends UserService {
override def create(username: String, password: String) =
userRepository.create(User(username, password))
}
}
trait ComponentRegistry extends UserServiceComponent with UserRepositoryComponent
trait ComponentRegistryImpl extends ComponentRegistry with UserServiceComponentImpl with UserRepositoryComponentImpl
// (3). di using partial application & currying
case class User(username: String, password: String)
trait UserRepository {
def create(user: User): Unit
}
trait UserService {
def create: UserRepository => User => Unit =
repo => user => repo.create(user)
}
object MyRepository extends UserRepository {
def create(user: User) = println(s"create $user")
}
object MyService extends UserService {
def create_c = create(MyRepository)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment