From e9fb5215661bf2d0d7b4900acdde53fb8b319d9b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Timo=20Westk=C3=A4mper?= Date: Sun, 27 Nov 2011 23:58:31 +0200 Subject: [PATCH] #57 : worked on DSL --- .../com/mysema/query/scala/sql/Queries.scala | 37 ++++++++++++++---- .../com/mysema/query/scala/sql/SQL.scala | 31 ++++++++------- .../query/scala/sql/JDBCIntegrationTest.scala | 39 ++++++++++++++++++- .../mysema/query/scala/sql/QueriesTest.scala | 23 +++++------ 4 files changed, 94 insertions(+), 36 deletions(-) diff --git a/querydsl-scala/src/main/scala/com/mysema/query/scala/sql/Queries.scala b/querydsl-scala/src/main/scala/com/mysema/query/scala/sql/Queries.scala index 31f5dd191..bcc1492da 100644 --- a/querydsl-scala/src/main/scala/com/mysema/query/scala/sql/Queries.scala +++ b/querydsl-scala/src/main/scala/com/mysema/query/scala/sql/Queries.scala @@ -29,9 +29,19 @@ object RichSimpleQuery { } +// TODO : define both callback (RelationalPath[_]) and projection expression (Ex[_]) + class RichSimpleQuery[T, E <: Ex[T]](expr: E, qry: SQLQuery) extends RichProjectable(qry) { def query = this + + def join[T2, R2 <: RelationalPath[T2], T3, E3 <: Ex[T3]](f : E => ForeignKey[T2], rp: R2) + (implicit e2t: ExprToTarget[T,E,T2,R2,T3,E3]): RichSimpleQuery[T3,E3] = join(f(expr), rp) + + def join[T2, R2 <: RelationalPath[T2], T3, E3 <: Ex[T3]](fk: ForeignKey[T2], rp: R2) + (implicit e2t: ExprToTarget[T,E,T2,R2,T3,E3]): RichSimpleQuery[T3,E3] = { + new RichSimpleQuery[T3,E3](e2t.toTarget(expr, rp), qry.innerJoin(fk, rp)) + } def limit(l: Long) = { qry.limit(l); this } @@ -53,17 +63,28 @@ class RichSimpleQuery[T, E <: Ex[T]](expr: E, qry: SQLQuery) extends RichProject def select[T](f: E => Ex[T]): List[T] = select(f(expr)) + def select[T,U](f1: E => Ex[T], f2: E => Ex[U]): List[(T,U)] = select(f1(expr), f2(expr)) + + def select[T,U,V](f1: E => Ex[T], f2: E => Ex[U], f3:E => Ex[V]): List[(T,U,V)] = { + select(f1(expr), f2(expr), f3(expr)) + } + + def select[T,U,V,W](f1: E => Ex[T], f2: E => Ex[U], f3: E => Ex[V], f4: E => Ex[W]): List[(T,U,V,W)] = { + select(f1(expr), f2(expr), f3(expr), f4(expr)) + } + + def select[T,U,V,W,X](f1: E => Ex[T], f2: E => Ex[U], f3: E => Ex[V], f4: E => Ex[W], f5: E => Ex[X]): List[(T,U,V,W,X)] = { + select(f1(expr), f2(expr), f3(expr), f4(expr), f5(expr)) + } + def single: Option[T] = single(expr) - def unique: Option[T] = unique(expr) - - def join[T2, R2 <: RelationalPath[T2], T3, E3 <: Ex[T3]](f : E => ForeignKey[T2], rp: R2) - (implicit e2t: ExprToTarget[T,E,T2,R2,T3,E3]): RichSimpleQuery[T3,E3] = join(f(expr), rp) + def single[T](f: E => Ex[T]): Option[T] = single(f(expr)) + + def unique: Option[T] = unique(expr) + + def unique[T](f: E => Ex[T]): Option[T] = unique(f(expr)) - def join[T2, R2 <: RelationalPath[T2], T3, E3 <: Ex[T3]](fk: ForeignKey[T2], rp: R2) - (implicit e2t: ExprToTarget[T,E,T2,R2,T3,E3]): RichSimpleQuery[T3,E3] = { - new RichSimpleQuery[T3,E3](e2t.toTarget(expr, rp), qry.innerJoin(fk, rp)) - } } // combine E1 and E2 into E3 diff --git a/querydsl-scala/src/main/scala/com/mysema/query/scala/sql/SQL.scala b/querydsl-scala/src/main/scala/com/mysema/query/scala/sql/SQL.scala index fba9ed975..e4df2068c 100644 --- a/querydsl-scala/src/main/scala/com/mysema/query/scala/sql/SQL.scala +++ b/querydsl-scala/src/main/scala/com/mysema/query/scala/sql/SQL.scala @@ -6,26 +6,27 @@ import com.mysema.query.sql._ import com.mysema.query.sql.dml._ import com.mysema.query.types._ -/** - * Convenience trait for injection into service implementations - * - * @author tiwe - * - */ -trait SQL { +trait SQLHelpers { + + def connection: Connection + + def templates: SQLTemplates + + implicit def toRichSimpleQuery[T, R <: RelationalPath[T]](p: RelationalPath[T] with R) = { + new RichSimpleQuery[T, R](p, new SQLQueryImpl(connection, templates).from(p) ) + } + +} + + +trait SQL extends SQLHelpers { private val connectionHolder = new ThreadLocal[Connection] val dataSource: DataSource - val templates : SQLTemplates - - private def connection = connectionHolder.get() - - implicit def toRichSimpleQuery[T, R <: RelationalPath[T]](p: RelationalPath[T] with R) = { - new RichSimpleQuery[T, R](p, new SQLQueryImpl(connection, templates).from(p) ) - } - + def connection = connectionHolder.get() + def query() = new SQLQueryImpl(connection, templates) def from(expr: Expression[_]*) = query.from(expr:_*) diff --git a/querydsl-scala/src/test/scala/com/mysema/query/scala/sql/JDBCIntegrationTest.scala b/querydsl-scala/src/test/scala/com/mysema/query/scala/sql/JDBCIntegrationTest.scala index c8c003734..05e765c83 100644 --- a/querydsl-scala/src/test/scala/com/mysema/query/scala/sql/JDBCIntegrationTest.scala +++ b/querydsl-scala/src/test/scala/com/mysema/query/scala/sql/JDBCIntegrationTest.scala @@ -23,7 +23,7 @@ import com.mysema.query.scala.ScalaTypeMappings import com.mysema.query.sql.dml._ import com.mysema.query.scala.Helpers._ -class JDBCIntegrationTest extends CompileTestUtils { +class JDBCIntegrationTest extends CompileTestUtils with SQLHelpers { val survey = QSurvey val employee = QEmployee @@ -33,7 +33,7 @@ class JDBCIntegrationTest extends CompileTestUtils { var connection: Connection = _ var statement: Statement = _ - + @Before def setUp() { Class.forName("org.h2.Driver") @@ -114,27 +114,54 @@ class JDBCIntegrationTest extends CompileTestUtils { assertEquals(2, query.from(employee).list(employee.firstname) size ()) } + @Test + def List_2 { + assertEquals(2, survey.select(_.id) size) + assertEquals(2, employee.select(_.firstname) size) + } + @Test def Select2 { assertEquals(2, query.from(survey).select(survey.id, survey.name).size) } + @Test + def Select2_2 { + assertEquals(2, survey.select(_.id, _.name) size) + } + @Test def Select3 { assertEquals(2, query.from(survey).select(survey.id, survey.name, survey.name.substring(0,1)).size) } + @Test + def Select3_2 { + assertEquals(2, survey.select(_.id, _.name, _.name.substring(0,1)) size) + } + @Test def Select4 { assertEquals(2, query.from(survey).select(survey.id, survey.name, survey.name + "X", survey.name + "Y").size) } + @Test + def Select4_2 { + assertEquals(2, survey.select(_.id, _.name, _.name + "X", _.name + "Y") size) + } + @Test def Count { assertEquals(2, query.from(survey).count) assertEquals(2, query.from(employee).count) } + @Test + def Count_2 { + assertEquals(2, survey.query.count) + assertEquals(2, employee.query.count) + } + @Test def Unique_Result { assertEquals("abc", query.from(survey).where(survey.id eq 1).uniqueResult(survey.name)) @@ -143,6 +170,14 @@ class JDBCIntegrationTest extends CompileTestUtils { assertEquals("John", query.from(employee).where(employee.lastname eq "Doe").uniqueResult(employee.firstname)) } + @Test + def Unique { + assertEquals("abc", survey.where(_.id eq 1).unique(_.name).get) + assertEquals("def", survey.where(_.id eq 2).unique(_.name).get) + assertEquals("Bob", employee.where(_.lastname eq "Smith").unique(_.firstname).get) + assertEquals("John", employee.where(_.lastname eq "Doe").unique(_.firstname).get) + } + @Test def Insert { val s = new Survey() diff --git a/querydsl-scala/src/test/scala/com/mysema/query/scala/sql/QueriesTest.scala b/querydsl-scala/src/test/scala/com/mysema/query/scala/sql/QueriesTest.scala index 4c05cfa1c..430d838f9 100644 --- a/querydsl-scala/src/test/scala/com/mysema/query/scala/sql/QueriesTest.scala +++ b/querydsl-scala/src/test/scala/com/mysema/query/scala/sql/QueriesTest.scala @@ -3,27 +3,21 @@ package com.mysema.query.scala.sql import org.junit._ import org.junit.Assert._ import com.mysema.query.sql._ - +import java.sql.Connection import test._ -class QueriesTest { +class QueriesTest extends SQLHelpers { import RichSimpleQuery._ - val sup = QEmployee as "sup" + val templates = new H2Templates() - val sup2 = QEmployee as "sup2" - - private val templates = new H2Templates() - - implicit def toRichSimpleQuery[T, R <: RelationalPath[T]](p: RelationalPath[T] with R) = { - new RichSimpleQuery[T, R](p, new SQLQueryImpl(null, templates).from(p) ) - } + def connection: Connection = null @Test def From { - assertEquals("from EMPLOYEE employee", QEmployee.query.toString) + assertEquals("from EMPLOYEE employee", Employee.query.toString) } @Test @@ -40,6 +34,7 @@ class QueriesTest { @Test def From_Join { + val sup = Employee as "sup" assertEquals( "from EMPLOYEE employee\ninner join EMPLOYEE sup\non employee.SUPERIOR_ID = sup.ID", Employee.join(_.superiorFk, sup).toString) @@ -47,6 +42,8 @@ class QueriesTest { @Test def From_Join_2x { + val sup = Employee as "sup" + val sup2 = Employee as "sup2" assertEquals( "from EMPLOYEE employee\ninner join EMPLOYEE sup\non employee.SUPERIOR_ID = sup.ID\ninner join EMPLOYEE sup2\non sup.SUPERIOR_ID = sup2.ID", Employee.join(_.superiorFk, sup).join(_._2.superiorFk, sup2).toString) @@ -54,6 +51,8 @@ class QueriesTest { @Test def From_Join_Where { + val sup = Employee as "sup" + val sup2 = Employee as "sup2" assertEquals( "from EMPLOYEE employee\ninner join EMPLOYEE sup\non employee.SUPERIOR_ID = sup.ID\nwhere employee.ID = ?", Employee.join(_.superiorFk, sup).where( _._1.id eq 1).toString) @@ -61,6 +60,8 @@ class QueriesTest { @Test def From_Join_Where2 { + val sup = Employee as "sup" + val sup2 = Employee as "sup2" assertEquals( "from EMPLOYEE employee\ninner join EMPLOYEE sup\non employee.SUPERIOR_ID = sup.ID\nwhere employee.ID = sup.ID", Employee.join(_.superiorFk, sup).where(e => e._1.id eq e._2.id).toString)