Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/j5ik2o/scala-ddd-base
scala-ddd-base provides traits to support for ddd repositories and aggregates.
https://github.com/j5ik2o/scala-ddd-base
ddd scala
Last synced: about 2 months ago
JSON representation
scala-ddd-base provides traits to support for ddd repositories and aggregates.
- Host: GitHub
- URL: https://github.com/j5ik2o/scala-ddd-base
- Owner: j5ik2o
- License: mit
- Created: 2017-06-20T13:06:37.000Z (over 7 years ago)
- Default Branch: master
- Last Pushed: 2023-12-15T05:14:29.000Z (about 1 year ago)
- Last Synced: 2024-05-02T01:17:16.517Z (8 months ago)
- Topics: ddd, scala
- Language: Scala
- Homepage:
- Size: 2.54 MB
- Stars: 42
- Watchers: 5
- Forks: 8
- Open Issues: 1
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# scala-ddd-base
[![CircleCI](https://circleci.com/gh/j5ik2o/scala-ddd-base/tree/master.svg?style=shield&circle-token=77d5ba85babad56b6a3fdd0f5be9e140ec12a4ae)](https://circleci.com/gh/j5ik2o/scala-ddd-base/tree/master)
[![Maven Central](https://maven-badges.herokuapp.com/maven-central/com.github.j5ik2o/scala-ddd-base-core_2.12/badge.svg)](https://maven-badges.herokuapp.com/maven-central/com.github.j5ik2o/scala-ddd-base-core_2.12)
[![Scaladoc](http://javadoc-badge.appspot.com/com.github.j5ik2o/scala-ddd-base-core_2.12.svg?label=scaladoc)](http://javadoc-badge.appspot.com/com.github.j5ik2o/scala-ddd-base-core_2.12/com/github/j5ik2o/dddbase/index.html?javadocio=true)
[![License: MIT](http://img.shields.io/badge/license-MIT-orange.svg)](LICENSE)`scala-ddd-base` provides traits to support for ddd repositories and aggregates.
## Installation
Add the following to your sbt build (Scala 2.11.x, 2.12.x):
```scala
resolvers += "Sonatype OSS Release Repository" at "https://oss.sonatype.org/content/repositories/releases/"val scalaDddBaseVersion = "..."
libraryDependencies ++= Seq(
"com.github.j5ik2o" %% "scala-ddd-base-core" % scalaDddBaseVersion,
// Please set as necessary
// "com.github.j5ik2o" %% "scala-ddd-base-slick" % scalaDddBaseVersion,
// "com.github.j5ik2o" %% "scala-ddd-base-skinny" % scalaDddBaseVersion,
// "com.github.j5ik2o" %% "scala-ddd-base-redis" % scalaDddBaseVersion,
// "com.github.j5ik2o" %% "scala-ddd-base-memcached" % scalaDddBaseVersion,
// "com.github.j5ik2o" %% "scala-ddd-base-dynamodb" % scalaDddBaseVersion,
// "com.github.j5ik2o" %% "scala-ddd-base-memory" % scalaDddBaseVersion
)
```## Core traits
The following provides basic abstract methods.
- AggregateSingleReader
- AggregateSingleWriter
- AggregateMultiReader
- AggregateMultiWriter
- AggregateSingleSoftDeletable
- AggregateSingleHardDeletable
- AggregateMultiSoftDeletable
- AggregateMultiHardDeletable## Support traits
The following provides an implementation for each ORM/KVS.
- AggregateSingleReadFeature
- AggregateSingleWriteFeature
- AggregateMultiReadFeature
- AggregateMultiWriteFeature
- AggregateSingleSoftDeleteFeature
- AggregateSingleHardDeleteFeature
- AggregateMultiSoftDeleteFeature
- AggregateMultiHardDeleteFeatureThe supported ORM/KVS/Cache is below.
- Slick(JDBC)
- SkinnyORM(JDBC)
- Redis([reactive-redis](https://github.com/j5ik2o/reactive-redis))
- Memcached([reactive-memcached](https://github.com/j5ik2o/reactive-memcached))
- DynamoDB([reactive-aws-dynamodb](https://github.com/j5ik2o/reactive-aws-client/tree/master/reactive-aws-dynamodb))
- Memory([Guava Cache](https://github.com/google/guava))## Example
Please mix in the core and support traits to your implementation.
Slick, SkinnyORM, Memcached, Redis, Memory etc. You can also choose the implementation as you like.```scala
trait UserAccountRepository[M[_]]
extends AggregateSingleReader[M]
with AggregateMultiReader[M]
with AggregateSingleWriter[M]
with AggregateMultiWriter[M]
with AggregateSingleSoftDeletable[M]
with AggregateMultiSoftDeletable[M] {
override type IdType = UserAccountId
override type AggregateType = UserAccount
}object UserAccountRepository {
type OnRedis[A] = ReaderT[Task, RedisConnection, A]
type OnMemcached[A] = ReaderT[Task, MemcachedConnection, A]
type OnDynamoDB[A] = Task[A]
type OnMemory[A] = Task[A]
type BySlick[A] = Task[A]
type BySkinny[A] = ReaderT[Task, DBSession, A]
type ByFree[A] = Free[UserRepositoryDSL, A]def bySlick(profile: JdbcProfile, db: JdbcProfile#Backend#Database): UserAccountRepository[BySlick] =
new UserAccountRepositoryBySlick(profile, db)def bySkinny: UserAccountRepository[BySkinny] = new UserAccountRepositoryBySkinny
def onRedis(
expireDuration: Duration
)(implicit actorSystem: ActorSystem): UserAccountRepository[OnRedis] =
new UserAccountRepositoryOnRedis(expireDuration)def onMemcached(
expireDuration: Duration
)(implicit actorSystem: ActorSystem): UserAccountRepository[OnMemcached] =
new UserAccountRepositoryOnMemcached(expireDuration)
def onDynamoDB(dynamoDbAsyncClient: DynamoDbAsyncClient): UserAccountRepository[OnDynamoDB] =
new UserAccountRepositoryOnDynamoDB(DynamoDBTaskClientV2(DynamoDBAsyncClientV2(underlying))def onMemory(minSize: Option[Int] = None,
maxSize: Option[Int] = None,
expireDuration: Option[Duration] = None,
concurrencyLevel: Option[Int] = None,
maxWeight: Option[Int] = None): UserAccountRepository[OnMemory] =
new UserAccountRepositoryOnMemory(minSize, maxSize, expireDuration, concurrencyLevel, maxWeight)
}
```- [for Slick3](example/src/main/scala/com/github/j5ik2o/dddbase/example/repository/slick/UserAccountRepositoryBySlick.scala)
- [for SkinnyORM](example/src/main/scala/com/github/j5ik2o/dddbase/example/repository/skinny/UserAccountRepositoryBySkinny.scala)
- [for Memcached](example/src/main/scala/com/github/j5ik2o/dddbase/example/repository/memcached/UserAccountRepositoryOnMemcached.scala)
- [for Redis](example/src/main/scala/com/github/j5ik2o/dddbase/example/repository/redis/UserAccountRepositoryOnRedis.scala)
- [for DynamoDB](example/src/main/scala/com/github/j5ik2o/dddbase/example/repository/dynamodb/UserAccountRepositoryOnDynamoDB.scala)
- [for Memory(Guava Cache)](example/src/main/scala/com/github/j5ik2o/dddbase/example/repository/memory/UserAccountRepositoryOnMemory.scala)
- [for Free](example/src/main/scala/com/github/j5ik2o/dddbase/example/repository/free/UserAccountRepositoryByFree.scala)### Usage
- for Slick3
```scala
val userAccountRepository: UserAccountRepository[BySlick] = UserAccountRepository.bySlick(dbConfig.profile, dbConfig.db)
val resultTask: Task[UserAccount] = for {
_ <- userAccountRepository.store(userAccount)
result <- userAccountRepository.resolveBy(userAccount.id)
} yield resultval resultFuture: Future[UserAccount] = resultTask.runToFuture
```- for SkinnyORM
```scala
val userAccountRepository: UserAccountRepository[BySkinny] = UserAccountRepository.bySkinny
val resultTask: Task[UserAccount] = for {
_ <- userAccountRepository.store(userAccount)
result <- userAccountRepository.resolveBy(userAccount.id)
} yield resultval resultFuture: Future[UserAccount] = resultTask.run(AutoSession).runToFuture
```- for Memcached
```scala
val userAccountRepository: UserAccountRepository[OnMemcached] = UserAccountRepository.onMemcached(expireDuration = 5 minutes)
val resultFuture: Future[UserAccount] = connectionPool
.withConnectionF { con =>
(for {
_ <- userAccountRepository.store(userAccount)
r <- userAccountRepository.resolveById(userAccount.id)
} yield r).run(con)
}
.runToFuture
```- for Redis
```scala
val userAccountRepository: UserAccountRepository[OnRedis] = UserAccountRepository.onRedis(expireDuration = 5 minutes)
val resultFuture: Future[UserAccount] = connectionPool
.withConnectionF { con =>
(for {
_ <- userAccountRepository.store(userAccount)
r <- userAccountRepository.resolveById(userAccount.id)
} yield r).run(con)
}
.runToFuture
```- for DynamoDB
```scala
val userAccountRepository: UserAccountRepository[OnDynamoDB] = UserAccountRepository.onDynamoDB(dynamoDbAsyncClient)
val resultFuture: Future[UserAccount] = (for {
_ <- userAccountRepository.store(userAccount)
r <- userAccountRepository.resolveById(userAccount.id)
} yield r).runToFuture
```- for Memory(Guava Cache)
```scala
val userAccountRepository: UserAccountRepository[OnMemory] = UserAccountRepository.onMemory(expireAfterWrite = Some(5 minutes))
val resultFuture: Future[UserAccount] = (for {
_ <- repository.store(userAccount)
r <- repository.resolveById(userAccount.id)
} yield r).runToFuture
```- for Free
```scala
val free: UserAccountRepository[ByFree] = UserAccountRepositoryByFree
val program: Free[UserRepositoryDSL, UserAccount] = for {
_ <- free.store(userAccount)
result <- free.resolveById(userAccount.id)
} yield resultval slick = UserAccountRepository.bySlick(dbConfig.profile, dbConfig.db)
val resultTask: Task[UserAccount] = UserAccountRepositoryOnFree.evaluate(slick)(program)
val resultFuture: Future[UserAccount] = evalResult.runToFuture// if evaluation by skinny
// val skinny = UserAccountRepository.bySkinny
// val resultTask: Task[UserAccount] = UserAccountRepositoryOnFree.evaluate(skinny)(program)
// val resultFuture: Future[UserAccount] = evalResult.run(AutoSession).runToFuture
```