After digging through the spec I'm not really sure whether this is even 
intentional.

There are an explicit CriteriaBuilder#parameter methods. And if I use those 
then I get a perfectly fine
"SELECT * FROM Department d WHERE d.name <> :x"

Using setParameter("x", "bla") on the resulting TypedQuery yields perfect 
results.

Happy to get some feedback!

LieGrue,
strub




> On Tuesday, 8 November 2016, 23:30, Mark Struberg <[email protected]> 
> wrote:
> > Hi folks!
> 
> 
> I think I found something smelly in our CriteriaQuery implementation. This is 
> related to OPENJPA-2668.
> 
> Currently EntityManager#createQuery(CriteriaQuery cq) returns the fully 
> 'interpreted' string. And no parameters. 
> 
> 
> Example:
> 
> CriteriaBuilder cb = em.getCriteriaBuilder();
> CriteriaQuery<Department> q = cb.createQuery(Department.class);
> Root<Department> book = q.from(Department.class);
> q.where(cb.notEqual(book.get(Department_.name), "X"));
> TypedQuery<Department> dept = em.createQuery(q);
> 
> 
> This creates the TypedQuery with 
> 
> "SELECT * FROM Department d WHERE d.name <> 'X'"
> And no parameter at all.
> 
> But imo it should use
> "SELECT * FROM Department d WHERE d.name <> ?"
> with dept.getParameters() returning a Parameter with pos 1 and value 
> 'X'.
> Wdyt?
> 
> 
> Not quite sure though how it should behave in Expression.In. 
> 
> 
> CriteriaBuilder cb = em.getCriteriaBuilder();
> CriteriaQuery<Customer> cq = this.cb.createQuery(Customer.class);
> Root<Customer> customerRoot = cq.from(Customer.class);
> cq.select(customerRoot)
>              .where(cb.and(cb.equal(customerRoot.get(Customer_.lastName), 
> "Hans"),
>                                         
> customerRoot.get(Customer_.name).in(Arrays.asList("A", "B", 
> "C"))));
> String queryString = cq.toString();
> 
> 
> Currently this returns 
> 
> "SELECT c FROM Customer c WHERE c.lastname = 'Hans' and c.name IN 
> ('A','B', 'C')"
> 
> This is imo wrong.
> But the question is whether it should return
> 
> "SELECT c FROM Customer c WHERE c.lastname = ? and c.name IN (?)"
>   or whether it already need to 'extend' the parameters 
> 
> "SELECT c FROM Customer c WHERE c.lastname = ? and c.name IN (?, ?, 
> ?)"
> 
> Of course the later is what will be used for the prepared statement.
> But the one parameter version might be easier to reuse with different 
> parameters?
> 
> LieGrue,
> strub
> 

Reply via email to