Scala 在Play Slick中分配动态注入的数据库名称

Scala 在Play Slick中分配动态注入的数据库名称,scala,playframework,slick,slick-3.0,play-slick,Scala,Playframework,Slick,Slick 3.0,Play Slick,我有下面的打滑刀课。请注意,数据库配置是一个常量control0001。DAO有一个函数readUser,它根据用户id读取用户: class UsersDAO @Inject()(@NamedDatabase("control0001") protected val dbConfigProvider: DatabaseConfigProvider) extends HasDatabaseConfigProvider[JdbcProfile] {

我有下面的打滑刀课。请注意,数据库配置是一个常量
control0001
。DAO有一个函数
readUser
,它根据用户id读取用户:

class UsersDAO @Inject()(@NamedDatabase("control0001") 
    protected val dbConfigProvider: DatabaseConfigProvider) 
                  extends HasDatabaseConfigProvider[JdbcProfile] {

   import driver.api._

   def readUser (userid: String) = {
      val users = TableQuery[UserDB]
      val action = users.filter(_.userid === userid).result
      val future = db.run(action.asTry)
      future.map{
        case Success(s) => 
          if (s.length>0)
            Some(s(0))
          else
            None
        case Failure(e) => throw new Exception ("Failure in readUser: " + e.getMessage)
      }
   }
}
我不需要在
@namedatabase(“control0001”)
中使用常量,而是需要将数据库设置为变量。在应用程序中,我在
application.conf
中配置了多个数据库(
control0001
control002
等等)。根据变量值,我需要确定DAO中要使用的数据库。所有数据库都相似,并且具有相同的表(每个数据库中的数据不同)

下面的Play类调用DAO函数,但首先需要确定要注入的数据库名称:

class TestSlick  @Inject()(dao: UsersDAO) extends Controller  {

  def test(someCode: Int, userId: String) = Action { request =>

    val databaseName = if (someCode == 1) "control0001" else "control0002"

    // Run the method in UsersDAO accessing the database set by databaseName

    val future = dao.readUser(userId) 
    future.map { result =>
      result match {
        case Some(user) => Ok(user.firstName)
        case _ => Ok("user not found")
      }
    }
  }        
}

如何在Play Slick中实现这一点?

您可以尝试初始化Slick db对象,覆盖默认配置:

val db=Database.forURL(“jdbc:mysql://localhost/“+databaseName,driver=“org.h2.driver”)


slick docs中的更多信息在本例中,不要尝试使用Play的运行时依赖项注入实用程序,而是直接在DAO中使用,并将数据源名称传递给该方法。要获得
SlickApi
,请混合以下特征:

然后在控制器中:

def test(someCode: Int, userId: String) = Action { request =>

  val databaseName = if (someCode == 1) "control0001" else "control0002"
  val future = dao.readUser(userId, databaseName)
  ...
}

我最终使用了您的想法,但我使用的是JNDI,而不是JDBC。使用连接后是否需要断开连接?我想不需要,但请记住,您使用的是普通的slick,而不是play slick插件,请检查这个示例,我在这个示例中没有看到是否需要断开JNDI连接
def test(someCode: Int, userId: String) = Action { request =>

  val databaseName = if (someCode == 1) "control0001" else "control0002"
  val future = dao.readUser(userId, databaseName)
  ...
}