title: SQL DSL for Scala
body: <p>I am struggling to create a SQL DSL for Scala. The DSL is an extension to <a href="http://www.querydsl.com/" rel="noreferrer">Querydsl</a>, which is a popular Query abstraction layer for Java.</p>
  
  <p>I am struggling now with really simple expressions like the following</p>
  
  <pre><code>user.firstName == "Bob" || user.firstName == "Ann"
  </code></pre>
  
  <p>As Querydsl supports already an expression model which can be used here I decided to provide conversions from Proxy objects to Querydsl expressions. In order to use the proxies I create an instance like this</p>
  
  <pre><code>import com.mysema.query.alias.Alias._
  
  var user = alias(classOf[User])
  </code></pre>
  
  <p>With the following implicit conversions I can convert proxy instances and proxy property call chains into Querydsl expressions </p>
  
  <pre><code>import com.mysema.query.alias.Alias._
  import com.mysema.query.types.expr._
  import com.mysema.query.types.path._
  
  object Conversions {        
      def not(b: EBoolean): EBoolean = b.not()        
      implicit def booleanPath(b: Boolean): PBoolean = $(b);        
      implicit def stringPath(s: String): PString = $(s);        
      implicit def datePath(d: java.sql.Date): PDate[java.sql.Date] = $(d);        
      implicit def dateTimePath(d: java.util.Date): PDateTime[java.util.Date] = $(d);        
      implicit def timePath(t: java.sql.Time): PTime[java.sql.Time] = $(t);            
      implicit def comparablePath(c: Comparable[_]): PComparable[_] = $(c);        
      implicit def simplePath(s: Object): PSimple[_] = $(s);        
  }
  </code></pre>
  
  <p>Now I can construct expressions like this</p>
  
  <pre><code>import com.mysema.query.alias.Alias._
  import com.mysema.query.scala.Conversions._
  
  var user = alias(classOf[User])
  var predicate = (user.firstName like "Bob") or (user.firstName like "Ann")
  </code></pre>
  
  <p>I am struggling with the following problem.</p>
  
  <p><code>eq</code> and <code>ne</code> are already available as methods in Scala, so the conversions aren't triggered when they are used</p>
  
  <p>This problem can be generalized as the following. When using method names that are already available in Scala types such as eq, ne, startsWith etc one needs to use some kind of escaping to trigger the implicit conversions.</p>
  
  <p>I am considering the following</p>
  
  <p><strong>Uppercase</strong> </p>
  
  <pre><code>var predicate = (user.firstName LIKE "Bob") OR (user.firstName LIKE "Ann")
  </code></pre>
  
  <p>This is for example the approach in <a href="http://circumflex.ru/orm.html" rel="noreferrer">Circumflex ORM</a>, a very powerful ORM framework for Scala with similar DSL aims. But this approach would be inconsistent with the query keywords (select, from, where etc), which are lowercase in Querydsl.</p>
  
  <p><strong>Some prefix</strong></p>
  
  <pre><code>var predicate = (user.firstName :like "Bob") :or (user.firstName :like "Ann")
  </code></pre>
  
  <p>The context of the predicate usage is something like this</p>
  
  <pre><code>var user = alias(classOf[User])
  
  query().from(user)
      .where( 
        (user.firstName like "Bob") or (user.firstName like "Ann"))
      .orderBy(user.firstName asc)
      .list(user);
  </code></pre>
  
  <p>Do you see better options or a different approach for SQL DSL construction for Scala?</p>
  
  <p>So the question basically boils down to two cases </p>
  
  <ul>
  <li><p>Is it possible to trigger an implicit type conversion when using a method that exists in the super class (e.g. <code>eq</code>)</p></li>
  <li><p>If it is not possible, what would be the most Scalaesque syntax to use for methods like <code>eq</code>, <code>ne</code>. </p></li>
  </ul>
  
  <p><strong>EDIT</strong></p>
  
  <p>We got Scala support in Querydsl working by using alias instances and a $-prefix based escape syntax. Here is a blog post on the results : <a href="http://blog.mysema.com/2010/09/querying-with-scala.html" rel="noreferrer">http://blog.mysema.com/2010/09/querying-with-scala.html</a></p>