spring-projects / spring-projects/spring-data-jpa
HQL does not support the modulo operator (%)
Nobody has claimed this yet.
- Dominant language
- Java
- Stars
- 3.3k
- Forks
- 1.6k
- PR merge metrics
- No merged PRs in 30d
Description
The HQL parser rejects the % (modulo) operator, although Hibernate accepts it.
@Query("select c from Call c where c.duration % 2 = 0")
List<Call> findEvenDurations();
fails with:
org.springframework.data.jpa.repository.query.BadJpqlGrammarException:
At 1:38, token recognition error at: '%';
Bad HQL grammar [select c from Call c where c.duration % 2 = 0]
Hql.g4 only allows * and / as multiplicative operators, while Hibernate's grammar also includes %:
// Hql.g4
expression
| expression op=('*' | '/') expression # MultiplicationExpression
// Hibernate HqlParser.g4
multiplicativeOperator
: SLASH
| PERCENT_OP
| ASTERISK
;
Running the same queries through Hibernate's own HqlParser and through JpaQueryEnhancer.HqlQueryParser:
| query | Hibernate 7.4 | Spring Data JPA |
|---|---|---|
select b.a % b.b from B b |
parses | rejected |
select b from B b where b.n % 2 = 0 |
parses | rejected |
select mod(b.a, b.b) from B b |
parses | parses |
The same applies to JpaSort.unsafe("age % 2"), which is parsed with the HQL grammar as well. Note that HqlOrderExpressionVisitor.visitMultiplicationExpression currently maps every operator other than * to CriteriaBuilder.quot(…),
so it needs to map % to CriteriaBuilder.mod(…) once the grammar accepts it.
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start with Hql.g4 and JpaQueryEnhancer.HqlQueryParser to trace how multiplicative operators are parsed, then inspect HqlOrderExpressionVisitor.visitMultiplicationExpression for unsafe sort handling. Compare behavior with Hibernate's HqlParser and run the existing parser and sorting tests. Done means % works in HQL expressions and JpaSort.unsafe expressions, with modulo mapped to CriteriaBuilder.mod rather than division.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- java, spring
- Domain
- databases
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Active
- Clarity
- Clearly specified
- Newbie friendliness
- 76/100