notInSubQuery functionality (#791)

This commit is contained in:
dolgopolovwork
2020-02-13 22:27:17 +07:00
committed by GitHub
parent f95c040ee6
commit 21e354d865
3 changed files with 33 additions and 1 deletions

View File

@@ -122,6 +122,14 @@ class InSubQueryOp<T>(val expr: Expression<T>, val query: Query): Op<Boolean>()
}
}
class NotInSubQueryOp<T>(val expr: Expression<T>, val query: Query) : Op<Boolean>() {
override fun toQueryBuilder(queryBuilder: QueryBuilder) = queryBuilder {
append(expr, " NOT IN (")
query.prepareSQL(this)
+")"
}
}
class QueryParameter<T>(val value: T, val sqlType: IColumnType) : Expression<T>() {
override fun toQueryBuilder(queryBuilder: QueryBuilder) = queryBuilder { registerArgument(sqlType, value) }
}

View File

@@ -190,6 +190,8 @@ object SqlExpressionBuilder {
infix fun<T> ExpressionWithColumnType<T>.inSubQuery(query: Query): Op<Boolean> = InSubQueryOp(this, query)
infix fun <T> ExpressionWithColumnType<T>.notInSubQuery(query: Query): Op<Boolean> = NotInSubQueryOp(this, query)
@Suppress("UNCHECKED_CAST")
fun<T, S: T?> ExpressionWithColumnType<S>.asLiteral(value: T) = when (value) {
is Boolean -> booleanLiteral(value)

View File

@@ -5,6 +5,7 @@ import org.jetbrains.exposed.sql.*
import org.jetbrains.exposed.sql.tests.DatabaseTestsBase
import org.jetbrains.exposed.sql.tests.shared.assertEquals
import org.junit.Test
import kotlin.test.assertNull
class SelectTests : DatabaseTestsBase() {
// select expressions
@@ -74,7 +75,6 @@ class SelectTests : DatabaseTestsBase() {
}
@Test
fun testInList01() {
withCitiesAndUsers { cities, users, userData ->
@@ -104,6 +104,28 @@ class SelectTests : DatabaseTestsBase() {
}
}
@Test
fun testNotInSubQueryNoData() {
withCitiesAndUsers { cities, _, _ ->
val r = cities.select { cities.id notInSubQuery cities.slice(cities.id).selectAll() }
// no data since all ids are selected
assertEquals(0, r.count())
}
}
@Test
fun testNotInSubQuery() {
withCitiesAndUsers { cities, _, _ ->
val cityId = 2
val r = cities.select { cities.id notInSubQuery cities.slice(cities.id).select { cities.id eq cityId } }.map { it[cities.id] }.sorted()
assertEquals(2, r.size)
// only 2 cities with id 1 and 2 respectively
assertEquals(1, r[0])
assertEquals(3, r[1])
//there is no city with id=2
assertNull(r.find { it == cityId })
}
}
@Test
fun testSelectDistinct() {