2015-09-30 6 views
6

Non riesco ad aggiungere ulteriori condizioni alla mia query. Nella sua forma più semplice, quello che mi serve è qualcosa di simile di seguito:Semplice query SQL con condizioni dinamiche

def findPeople(name: String, maybeSurname: Option[String]) = { 
    val sql1 = sql"select * from my_table where name = $name" 
    val sql2 = maybeSurname.map(surname => sql"and col2 = $surname").getOrElse(sql"") 
    val finalSql = sql1 + sql2 // I need this kind of feature 
    ... 
    ... 
} 

Utilizzando #$ potrebbe essere un'opzione, ma poi il cognome non sarebbe una variabile di legatura, che è un grande problema.

risposta

0

Penso che le variabili di binding non siano interpretate dalla funzione map. Sono interpretati dall'interpolatore sql di Slick. Ecco perché il tuo sql2 non otterrà il valore del cognome.

Se è necessario scrivere istruzioni SQL, è possibile considerare di non utilizzare la funzione Plain SQL. Puoi semplicemente fare .filter (.name ==== nome) .filter ( .col2 === cognome)?

+0

La mia domanda è molto più complessa di questo, è per questo che sto usando Plain SQL. – Feyyaz

+0

Ho pensato che 'sql2' è una query parziale, che non è possibile in slick in questo momento. Se intendi 'maybeSurname.map', vale per' Option', non per bind variable. – Feyyaz

4

qui è un test di esempio su 3.1.x chiazza di petrolio

import slick.jdbc.{SQLActionBuilder, SetParameter, PositionedParameters} 

object SlickKit { 

    implicit class SQLActionBuilderConcat (a: SQLActionBuilder) { 
    def concat (b: SQLActionBuilder): SQLActionBuilder = { 
     SQLActionBuilder(a.queryParts ++ b.queryParts, new SetParameter[Unit] { 
     def apply(p: Unit, pp: PositionedParameters): Unit = { 
      a.unitPConv.apply(p, pp) 
      b.unitPConv.apply(p, pp) 
     } 
     }) 
    } 
    } 
} 

e poi

import SlickKit._ 
val sql1 = 
    sql""" 
    select count(*) from idinfo_#$i 
    """ 

val sql2 = 
    sql""" 
     where source=$source 
    """ 

val sql = sql1 concat sql2 

sql.as[Int].head