Scala Play Framework Slick session not working

I am trying to use a simple test program with Slick and Play2 Framework, but the compiler continues to complain about the implicit session cannot be output.

Here is my Build.scala :

 import sbt._ import Keys._ import play.Project._ object ApplicationBuild extends Build { val appName = "dummy" val appVersion = "1.0" val appDependencies = Seq( jdbc, "mysql" % "mysql-connector-java" % "5.1.26", "com.typesafe.slick" %% "slick" % "1.0.1" ) val main = play.Project(appName, appVersion, appDependencies).settings( // Add your own project settings here ) } 

And this is my global singleton that supports my database connections:

 package models import play.api.Play.current import play.api.db.DB import slick.session.Session import slick.driver.MySQLDriver.simple._ import scala.slick.session.Database.threadLocalSession object Global { lazy val database = Database.forDataSource(DB.getDataSource()) lazy val session = database.createSession() } 

And my controller:

 package controllers import scala.language.implicitConversions import play.api._ import play.api.mvc._ import models.Global.session import slick.driver.MySQLDriver.simple._ object Application extends Controller { def index = Action { /*slick.driver.MySQLDriver.simple.*/Query(Foo).foreach( _ => () ) // Do nothing for now Ok(views.html.index("hola")) } object Foo extends Table[(Long, String, String)]("Foo") { def * = column[Long]("id") ~ column[String]("bar1") ~ column[String]("bar2") } } 

As you can see, my val Global.session imported, but it continues to say that no implicit session was detected.

+4
source share
1 answer

To create queries, you need two things: a database connection and a session, so your problem is how you define and use them. With Database.threadLocalSession in scope, you can do your queries as follows:

 Database.forURL("jdbc:h2:mem:play", driver = "org.h2.Driver") withSession { //create table Foo.ddl.create //insert data Foo.insert((1.toLong,"foo","bar")) //get data val data : (Long,String,String) = (for{f<-Foo}yield(f)).first } 

or you can do it like this:

 val database = Database.forDataSource(DB.getDataSource()) database.withSession{ implicit session : Session => Foo.ddl.create Foo.insert((1.toLong,"foo","bar")) val data : (Long,String,String) = (for{f<-Foo}yield(f)).first } 

I created a test and it works great, you can play with it:

 "Foo should be creatable " in { running(FakeApplication(additionalConfiguration = inMemoryDatabase())) { val database = Database.forDataSource(DB.getDataSource()) database.withSession{ implicit session : Session => Foo.ddl.create Foo.insert((1.toLong,"foo","bar")) val data : (Long,String,String) = (for{f<-Foo}yield(f)).first data._1 must equalTo(1) } } } 

You can also look here.

+4
source

Source: https://habr.com/ru/post/1502637/


All Articles