Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ConstructorExpression with joined boolean parameter causes IllegalArgumentException #679

Closed
wrungel opened this issue Mar 13, 2014 · 20 comments
Closed
Labels
bug
Milestone

Comments

@wrungel
Copy link

@wrungel wrungel commented Mar 13, 2014

(Left-)Joining two entities with JPAQuery and using boolean property from the right joined entity causes IllegalArgumentException.

See test cases in https://github.com/wrungel/qdsl-bugs/tree/master/constructor-expression-boolean-bug
The following tests fails:

  • constructor_expression_with_joined_boolean_parameter()
  • nested_constructor_expression_with_joined_string_and_boolean_parameter()

Querydsl version: 3.3.1, 3.2.2
JPA Provider: Hibernate 4.2.8.Final, 4.1.5.Final
Database: h2, Oracle

@timowest
Copy link
Member

@timowest timowest commented Mar 13, 2014

Could you provide the full stacktrace?

@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 13, 2014

there is none, the JUnit runner catches the exception.

I think the argument count at construstor.newinstance() is mismatched, but I am not sure?

also, the exception has no stacktrace available, but I am looking into it.

@wrungel
Copy link
Author

@wrungel wrungel commented Mar 13, 2014

This is the output of the test method constructor_expression_with_joined_boolean_parameter:

10:24:22,195 DEBUG SQL:104 - insert into Video (id, book_id) values (null, ?)
10:24:22,364 DEBUG SQL:104 - select video0_.id as col_0_0_, book1_.good as col_1_0_ from Video video0_ left outer join Book book1_ on video0_.book_id=book1_.id

java.lang.IllegalArgumentException
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:57)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:526)
    at com.mysema.query.types.ConstructorExpression.newInstance(ConstructorExpression.java:173)
    at com.mysema.query.jpa.FactoryExpressionTransformer.transformTuple(FactoryExpressionTransformer.java:50)
    at org.hibernate.hql.internal.HolderInstantiator.instantiate(HolderInstantiator.java:95)
    at org.hibernate.loader.hql.QueryLoader.getResultList(QueryLoader.java:463)
    at org.hibernate.loader.Loader.listIgnoreQueryCache(Loader.java:2364)
    at org.hibernate.loader.Loader.list(Loader.java:2359)
    at org.hibernate.loader.hql.QueryLoader.list(QueryLoader.java:495)
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.list(QueryTranslatorImpl.java:357)
    at org.hibernate.engine.query.spi.HQLQueryPlan.performList(HQLQueryPlan.java:195)
    at org.hibernate.internal.SessionImpl.list(SessionImpl.java:1194)
    at org.hibernate.internal.QueryImpl.list(QueryImpl.java:101)
    at org.hibernate.ejb.QueryImpl.getResultList(QueryImpl.java:268)
    at com.mysema.query.jpa.impl.AbstractJPAQuery.getResultList(AbstractJPAQuery.java:196)
    at com.mysema.query.jpa.impl.AbstractJPAQuery.list(AbstractJPAQuery.java:244)
    at frol.querydsl.ConstructorExpressionWithJoinedBooleanTest.constructor_expression_with_joined_boolean_parameter(ConstructorExpressionWithJoinedBooleanTest.java:52)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:47)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:44)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
    at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:27)
    at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:271)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:70)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:238)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:63)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:236)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:53)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:229)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:309)
    at org.junit.runner.JUnitCore.run(JUnitCore.java:160)
    at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:74)
    at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:202)
    at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:65)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:120)
@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 13, 2014

the book.good argument is null. with a book entity attached to the video it is resolved.

@wrungel can you confirm this? ( see my pull request (edit, my fork)

@wrungel
Copy link
Author

@wrungel wrungel commented Mar 13, 2014

@Shredder121 The argument count is OK. The problem is the type of the argument. It fails if the type is boolean and it comes from the right table,

@wrungel
Copy link
Author

@wrungel wrungel commented Mar 13, 2014

@Shredder121 I confirm, that attaching a book to the videoresolves the problem.
I added a new test method for this case: book_attached_to_video_and_constructor_expr_with_joined_boolean_param, see:
https://github.com/wrungel/qdsl-bugs/blob/master/constructor-expression-boolean-bug/src/test/java/frol/querydsl/ConstructorExpressionWithJoinedBooleanTest.java

@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 13, 2014

According to the javadoc:
http://docs.oracle.com/javase/7/docs/api/java/lang/reflect/Constructor.html#newInstance(java.lang.Object...)

in the exceptions list it explicitly mentions if unwrapping of a primitive argument fails it throws an illegalargumentexception.
this is true with null values.
how should we overcome this?

@timowest
Copy link
Member

@timowest timowest commented Mar 13, 2014

@wrungel @Shredder121 Maybe for the constructor invocation an array with default parameters for primitive arguments could be merged into the array for the call. Do you have better ideas?

@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 13, 2014

what default parameters were you thinking of?

@timowest
Copy link
Member

@timowest timowest commented Mar 13, 2014

Zero values for numbers and false for boolean
On 13 Mar 2014 17:05, "Ruben Dijkstra" notifications@github.com wrote:

what default parameters were you thinking of?

Reply to this email directly or view it on GitHubhttps://github.com//issues/679#issuecomment-37543545
.

@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 13, 2014

What about String literals? Are they affected?(just wondering)

(edit: nevermind the complex objects, they initially are a collection of primitives.
but don't you think that there should be a null placeholder?
nested objects that are created with data that is not quite right might be strange.)

@timowest
Copy link
Member

@timowest timowest commented Mar 13, 2014

What about String literals? Are they affected?(just wondering)

String literals are not primitives, so no problem with them.

(edit: nevermind the complex objects, they initially are a collection of primitives. but don't you think that there should be a null placeholder? nested objects that are created with data that is not quite right might be strange.)

That is a good question. Maybe for both bean population and constructor invocation there could be variants that return null if all the arguments are null?

@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 13, 2014

the only thing I can think of right now is one constructor that is null-aware and accepts a map of member names mapped to the value.
but that doesn't sound pretty.

@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 15, 2014

what if the codegen module uses the boxed version of the primitives?

@timowest
Copy link
Member

@timowest timowest commented Mar 15, 2014

The codegen module will always use the boxed version of the primitives, the types are taken via reflection from the constructor.

@timowest timowest added fixed and removed fixed labels Mar 20, 2014
@timowest
Copy link
Member

@timowest timowest commented Mar 20, 2014

@wrungel or @Shredder121 would you be interested to provide a pull request? The change would be local to ConstructorExpression.

@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 20, 2014

yes, I'll at least look into it

@Shredder121
Copy link
Member

@Shredder121 Shredder121 commented Mar 20, 2014

#681 I submitted a pull request, I'll hear from you considering feedback or tweaking.

I might have some ideas for smoothening the primitive type capturing (at creation time of the constructorexpression), but this should work for now, I think?
Let me know your opinion.

@timowest timowest added this to the 3.3.4 milestone May 2, 2014
@timowest timowest added the fixed label May 10, 2014
@timowest timowest modified the milestone: 3.3.4 May 10, 2014
@timowest
Copy link
Member

@timowest timowest commented May 20, 2014

Released in 3.3.4

@timowest timowest closed this May 20, 2014
@axelosorio
Copy link

@axelosorio axelosorio commented Sep 14, 2017

I have similar problem when I was working in a Join with no values in the other table to join. The problem in hibernate is that it causes illegalArgumentException and tupleTransform problem in the join.
The thing was that in my constructor of the entity I have a type as double and it must be Double.
BAD CODE:

public DetalleFacturaEmbarqueEB(Integer idDetalleFacturaEmbarque,
									Integer idFacturaEmbarque,
									double descuento
				  					){

GOOD CODE

public DetalleFacturaEmbarqueEB(Integer idDetalleFacturaEmbarque,
									Integer idFacturaEmbarque,
									Double descuento
				  					){

As you see "descuento" was as double and not as Double.
It works for me, I hope it helps someone else.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Linked pull requests

Successfully merging a pull request may close this issue.

None yet
4 participants
You can’t perform that action at this time.