Scala 在slick中显式关闭db连接

Scala 在slick中显式关闭db连接,scala,slick,slick-3.0,play-slick,Scala,Slick,Slick 3.0,Play Slick,以下是我试图优化的代码: object UserRepo { val users = TableQuery[Users] val dbName = "db" lazy val queryAllUsers = for (user <- users) yield user type UserRow = (Int, String, String, String) def getAll() : Future[ Seq[UserRow] ] = { val

以下是我试图优化的代码:

object UserRepo
{
  val users = TableQuery[Users]

  val dbName = "db"

  lazy val queryAllUsers = for (user <- users) yield user

  type UserRow =  (Int, String, String, String)

  def getAll() : Future[ Seq[UserRow] ] =
  {
    val db = Database.forConfig( dbName )

    val f: Future[Seq[UserRow]] = db.run( queryAllUsers.result )

    f.onComplete {
      case Success(_) => { db.close() }
      case Failure(_) => { db.close() }
    }

    f
  }

}
我将有一个对数据库的查询数,我正在尝试删除创建数据库连接的字符串。是否有任何执行上下文可用于显式关闭连接??那么代码看起来会更简洁

在Future.onComplete范围内是否有使用db连接的选项

感谢您的评论。通常,您要做的是在应用程序启动时创建连接,或者在第一次使用时创建连接,然后在应用程序端关闭连接

这显然取决于您运行的应用程序类型:

如果您使用的是DI容器,那么您可能会在DI机制中管理其中一些,比如Guice中的模块

如果您使用的是web应用程序,特别是Play,您可能会使用Play slick来为您进行初始化/关闭

大路一号

假设您不使用DI或play slick,最简单的一般方法可能是这样:

object DbManager {
  lazy val db = createDb

  private def createDb = {
      Database.forConfig("db")
  }

  def close {
      db.close
  }
}
那么您的代码将是:

object UserRepo
{
  val users = TableQuery[Users]

  lazy val queryAllUsers = for (user <- users) yield user

  type UserRow =  (Int, String, String, String)

  def getAll() : Future[ Seq[UserRow] ] =
  {
    DbManager.db.run( queryAllUsers.result )
  }   
}
class UserRepo @Inject() (dbConfigProvider: DatabaseConfigProvider) extends HasDatabaseConfigProvider[JdbcProfile])
{
  import driver.api._

  val users = TableQuery[Users]

  lazy val queryAllUsers = for (user <- users) yield user

  type UserRow =  (Int, String, String, String)

  def getAll() : Future[ Seq[UserRow] ] =
  {
    db.run( queryAllUsers.result )
  }   
}
在这种情况下,您不会调用:

UserRepo.getAll
但您更愿意将其注入:

class MyClientCode @Inject() (userRepo: UserRepo) {
  ...
  userRepo.getAll
  ...
}
显然,您需要在配置中对其进行配置,但对于上面提供的示例,这应该非常简单

因此,简而言之,您的Play应用程序将具有数据库连接配置,并将执行所有初始化/清理。您的外部模块(如您在评论中所述)只需将DatabaseConfigProvider作为Guice管理的依赖项,如上所示。

对于您的评论,通常您要做的是在应用程序启动时创建连接,或者在首次使用时创建连接,然后在应用程序端关闭连接

这显然取决于您运行的应用程序类型:

如果您使用的是DI容器,那么您可能会在DI机制中管理其中一些,比如Guice中的模块

如果您使用的是web应用程序,特别是Play,您可能会使用Play slick来为您进行初始化/关闭

大路一号

假设您不使用DI或play slick,最简单的一般方法可能是这样:

object DbManager {
  lazy val db = createDb

  private def createDb = {
      Database.forConfig("db")
  }

  def close {
      db.close
  }
}
那么您的代码将是:

object UserRepo
{
  val users = TableQuery[Users]

  lazy val queryAllUsers = for (user <- users) yield user

  type UserRow =  (Int, String, String, String)

  def getAll() : Future[ Seq[UserRow] ] =
  {
    DbManager.db.run( queryAllUsers.result )
  }   
}
class UserRepo @Inject() (dbConfigProvider: DatabaseConfigProvider) extends HasDatabaseConfigProvider[JdbcProfile])
{
  import driver.api._

  val users = TableQuery[Users]

  lazy val queryAllUsers = for (user <- users) yield user

  type UserRow =  (Int, String, String, String)

  def getAll() : Future[ Seq[UserRow] ] =
  {
    db.run( queryAllUsers.result )
  }   
}
在这种情况下,您不会调用:

UserRepo.getAll
但您更愿意将其注入:

class MyClientCode @Inject() (userRepo: UserRepo) {
  ...
  userRepo.getAll
  ...
}
显然,您需要在配置中对其进行配置,但对于上面提供的示例,这应该非常简单


因此,简而言之,您的Play应用程序将具有数据库连接配置,并将执行所有初始化/清理。您在评论中描述的外部模块只是将DatabaseConfigProvider作为Guice管理的依赖项拉入,如上所示。

那么您想说的是,您想为这个操作创建并稍后关闭db连接吗?您不应该在应用程序启动/关闭时打开/关闭连接,并在执行查询时恢复连接吗?很好,您的意思是在应用程序级别管理db连接吗?是的,这可能很好,但据我所知,我将不得不手动创建此代码?slick中是否有内置内容?您是否使用Play?我已经创建了一个单独的项目来管理与数据库/数据相关的所有工作,并计划将此项目和数据处理服务一样重用。如果您使用Play,那么查看Play slick并简单地使用DI可能会很有用。让我用Play-style-DI更新答案。那么您的意思是您想为这个操作创建并稍后关闭db连接?您不应该在应用程序启动/关闭时打开/关闭连接,并在执行查询时恢复连接吗?很好,您的意思是在应用程序级别管理db连接吗?是的,这可能很好,但据我所知,我将不得不手动创建此代码?slick中是否有内置内容?您是否使用Play?我已经创建了一个单独的项目来管理与数据库/数据相关的所有工作,并计划将此项目和数据处理服务一样重用。如果您使用Play,那么查看Play slick并简单地使用DI可能会很有用。让我用Play-style-DI更新答案。考虑到scala代码的简洁性,我正在考虑在我的项目中使用Play-slick:Play-project+Akk-processing-services。因此,我将有一个单独的项目用于数据模型/表映射等。谢谢,考虑到scala代码的简洁性,我正在考虑在我的项目中使用play slick:play project+Akk processing services。因此,我将有单独的项目用于数据模型/表映射等。谢谢,