Skip to content

Instantly share code, notes, and snippets.

@4gus71n
Created April 23, 2020 22:41
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save 4gus71n/2c0b0fe131cc14f365dbf0d1dd0ed1db to your computer and use it in GitHub Desktop.
Save 4gus71n/2c0b0fe131cc14f365dbf0d1dd0ed1db to your computer and use it in GitHub Desktop.
// You could call this somewhere in your ViewModel
insertUserWithAddressUseCase.execute(this, user, address)
// .........
// The Interface of the Use Case.
interface InsertUserWithAddressUseCase {
interface Callback {
fun onUserSuccessfullyInserted(insertedUser: User)
fun onErrorWhileTryingToInsertUser(e: Throwable)
}
fun execute(callbakc: Callback, user: User, address: Address)
}
// .........
// The actual implementation.
class InsertUserWithAddressUseCaseImpl(
private val dbAddressRepository: DbAddressRepository,
private val dbUserRepository: DbUserRepository
) : InsertUserWithAddressUseCase {
override fun execute(callback: InsertUserWithAddressUseCase.Callback, user: User, address: Address) {
dbAddressRepository.insertAddress(address).flatMap { addressId ->
dbUserRepository.insertUser(user, addressId)
}
// Add the observeOn, subscribeOn...
.subscribe(
{
// You can send back the same user that you just inserted, or the id of the inserted user, etc.
callback.onUserSuccessfullyInserted(user)
},
{
callback.onErrorWhileTryingToInsertUser(it)
}
)
}
}
// .........
// The Repositories interfaces
interface DbAddressRepository {
// Notice that for simplicity sake, I'm not using any wrapper around the rx.Observable. It just returns the id from the
// inserted record.
fun insertAddress(address: Address): rx.Observable<Int>
}
interface DbUserRepository {
fun insertUser(user: User, addressId: Int): rx.Observable<Int>
}
// .........
// The actual implementation
class DbAddressRepositoryImpl(
private val addressDao: AddressDao
) : DbAddressRepository {
override fun insertAddress(address: Address): rx.Observable<Int> {
return addressDao.insertAddress(address)
// Do whatever mapping you want. Here I'm using just plain Address and User classes but you should probably use
// DTO classes to map your DB records. You don't want to mix your model classes, the db model classes and whatever backend
// model classes you have to model the server-side responses.
.toObservable()
}
}
class DbUserRepositoryImpl(
private val userDao: UserDao
) : DbUserRepository {
override fun insertUser(user: User, addressId: Int): rx.Observable<Int> {
return userDao.insertUser(user.copy(foreginAddresId = addressId))
// Do whatever mapping you want. Here I'm using just plain Address and User classes but you should probably use
// DTO classes to map your DB records. You don't want to mix your model classes, the db model classes and whatever backend
// model classes you have to model the server-side responses.
.toObservable()
}
}
// The DAOs
@Dao
abstract class AddressDao {
@Insert(onConflict = OnConflictStrategy.IGNORE)
abstract fun insertAddress(address: Address): rx.Single<Int>
}
@Dao
abstract class UserDao {
@Insert(onConflict = OnConflictStrategy.IGNORE)
abstract fun insertUser(user: User): rx.Single<Int>
}
// The "Model" classes
@Entity
data User(
@PrimaryKey
val id: Int,
val foreginAddresId: Int,
val name: String
)
@Entity
data Address(
@PrimaryKey
val id: Int,
val streetName: String,
val streetNumber: Int
)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment