Scala 测试光滑会话/事务代码的最佳方法

Scala 测试光滑会话/事务代码的最佳方法,scala,slick,scalatest,Scala,Slick,Scalatest,对于创建数据源我有 object MyDataSource { priavte lazy val dataSource: javax.sql.DataSource = { val ds = new BasicDataSource val conf = ConfigFactory.load() val url = conf.getString("jdbc-url") val driver = conf.getString("jdbc-driver") val username = c

对于创建
数据源
我有

object MyDataSource {
 priavte lazy val dataSource: javax.sql.DataSource = {
 val ds = new BasicDataSource
 val conf = ConfigFactory.load()

 val url = conf.getString("jdbc-url")
 val driver = conf.getString("jdbc-driver")
 val username = conf.getString("db-username")
 val password = conf.getString("db-password")
 val port = conf.getString("db-port")

 val maxActive = conf.getInt("max-active")

 val maxIdle = conf.getInt("max-idle")
 val initSize = conf.getInt("init-size")

 ds.setDriverClassName(driver)
 ds.setUsername(username)
 ds.setPassword(password)
 ds.setMaxActive(maxActive)
 ds.setMaxIdle(maxIdle)
 ds.setInitialSize(initSize)

 ds.setUrl(url)
 ds
 } 

lazy val database = Database.forDataSource(dataSource)
}
MyDataSource
的使用方法如下

def insertCompany = {    
   MyDataSource.database.withSession{ implicit session =>
   company.insert(companyRow)

   }
}
现在,对于测试,我有
trait-DatabaseSpec
,它加载测试数据库(指向测试数据库)配置,并具有以下夹具

def withSession(testCode: Session => Any) {
val session = postgres.createSession()
session.conn.setAutoCommit(false)
try {
  testCode(session)
} finally {
  session.rollback()
  session.close()
}
}

然后,测试代码可以混入
DatabaseSpec
,并使用
with session
测试事务代码


现在的问题是,在
insertCompany
中将
MyDataSource.database.with session
DataSource
中抽象出来,这样就可以使用
DatabaseSpec
并指向test db来测试该方法的最佳实践是什么

交换一个值的最佳方法。例如,对于prod和testing,就是在该值中参数化您的代码。例如

def insertCompany(db: Database) = db.withSession(company.insert(companyRow)(_))

保持简单。为此避免不必要的复杂性,如蛋糕模式、DI框架或mixin组合

如果需要传递多个值。。。将它们聚合到一个“config”类中。如果您不想随着内容的积累而编写一个庞大的配置类,那么就可以编写多个具有不同目的的配置类来针对不同的内容

如果您发现自己将配置对象传递给所有函数,则可以将它们标记为隐式,这样至少可以节省调用站点代码开销。或者您可以使用scalaz的一元函数组合之类的东西来避免传递配置时的调用站点和定义站点代码开销。它有时被称为Reader monad,但它只是用于单参数函数的理解合成

Slick 2.2将提供类似的开箱即用的东西,让你想要的东西变得非常简单


另外,这里是我目前正在使用的一种方法,一个可组合的配置对象“TMap”。这个代码示例一步一步地展示了如何通过参数化函数从全局导入中获取数据,并使它们隐式地用于使用TMap和删除大多数样板文件:

Acolyte框架可以通过独立连接模型来测试基于JDBC的任何持久性代码:。下面是一个使用Slick的示例:。
class DAO(db:Database){
    def insertCompany = db.withSession(company.insert(companyRow)(_))
}