I HAVE THESE 2 MODELS:
@Entity
public class Prod extends Model {
@OneToOne(fetch = FetchType.LAZY)
public ProdDetail prodDetail;
@Transient
public String descr;
public Prod() {
super();
this.prodDetail = new ProdDetail();
}
public String getDescr() {
ProdDetail detail = this.prodDetail;
return detail.descr;
}
}
@Entity
public class ProdDetail extends Model {
@Required
public String descr;
public ProdDetail() {
super();
}
}
FIRST CASE:
public static void index() {
Prod prod = Prod.find("").first();
ProdDetail detail = prod.prodDetail;
Logger.info(detail.descr);
}
SECOND CASE:
public static void index2() {
Prod prod = Prod.find("").first();
OR THIS QUERY
Prod prod = Prod.find("select p FROM Prod p JOIN p.prodDetail
pd").first();
ProdDetail detail = prod.prodDetail;
Logger.info(prod.descr); // RETURNS NULL - WHY ??
}
in 1:
It returns the right content of ProdDetail.
In 2:
ProductDetail is set but descr field is null.
Any help is appreciated.
Thanks
Daniel
Nicolas
> --
> You received this message because you are subscribed to the Google Groups "play-framework" group.
> To post to this group, send email to play-fr...@googlegroups.com.
> To unsubscribe from this group, send email to play-framewor...@googlegroups.com.
> For more options, visit this group at http://groups.google.com/group/play-framework?hl=en.
>
Logger.info(prod.getDescr());
Works?
> --
> You received this message because you are subscribed to the Google Groups "play-framework" group.
> To post to this group, send email to play-fr...@googlegroups.com.
> To unsubscribe from this group, send email to play-framewor...@googlegroups.com.
> For more options, visit this group at http://groups.google.com/group/play-framework?hl=en.
>
>
--
Guillaume Bort, http://guillaume.bort.fr
For anything work-related, use g...@zenexity.fr; for everything else,
write guillau...@gmail.com
Daniel
Just a bit of curiosity : why do you hide the descr attribute with the
Transient getter ?
Else the answer to your question is that if you declare a public
method name "getDescr"
on your Entity Prod, then it cannot be enriched at runtime by
Hibernate to perform the lazy-loading.
Try to rename-it to getMyDescription and it should work.
A simplier and better approach would be to stick to the Active Record pattern.
On your Prod entity, do not hide the "descr" attribute from Prod with
an error-prone getter.
You could rename attribute descr to description on ProdDetail, then
use directly the statement below
on the groovy side in your view.
My product description = ${prod?.prodDetail?.description}
Nicolas
2010/10/4 Guillaume Bort <guillau...@gmail.com>:
Daniel
On Mon, Oct 4, 2010 at 1:41 PM, Nicolas Martignole
<nic...@martignole.net> wrote:
> Hi Daniel
>
> Just a bit of curiosity : why do you hide the descr attribute with the
> Transient getter ?
Because in my real application descr field is a blob which can be even
100kB large. So I want to fetch it lazily via OneToOne.
>
> Else the answer to your question is that if you declare a public
> method name "getDescr"
> on your Entity Prod, then it cannot be enriched at runtime by
> Hibernate to perform the lazy-loading.
> Try to rename-it to getMyDescription and it should work.
>
> A simplier and better approach would be to stick to the Active Record pattern.
>
> On your Prod entity, do not hide the "descr" attribute from Prod with
> an error-prone getter.
> You could rename attribute descr to description on ProdDetail, then
> use directly the statement below
> on the groovy side in your view.
>
> My product description = ${prod?.prodDetail?.description}
Yes I know I can use it this way in groovy but I use these methods in
java since in my real application I have descrDe, descrEn, ... and
descr is just a transient field which calls getDescr() method (because
of nice Play magic).
Daniel
Any other idea ?
Thank you
Daniel
I completely removed transient field descr since it's not the core of a problem.
Problem is a descr field in a ProdDetail model and a getDescr() method
in a Prod model.
If I rename descr field in a ProdDetail model to description
everything starts to work as expected.
What the hell is going on ?
If field name (description located in a ProdDetail model) is same with
name of a method located in a Prod model it stops working !!
I really do not uderstand what's wrong. Method is and should be
totally independant of a field which is located in other model.
index and index2 actions should give same result "test".
Just my complete controller + models:
public class Prods extends Controller {
private static Prod createOrGet() {
Prod prod = Prod.find("").first();
if(prod == null) {
Prod p = new Prod();
p.prodDetail.description = "test";
p.save();
prod = Prod.find("").first();
}
return prod;
}
public static void index() {
Prod prod = createOrGet();
ProdDetail detail = prod.prodDetail;
String descr = detail.description;
renderText(descr);
}
public static void index2() {
Prod prod = createOrGet();
String descr = prod.getDescription();
renderText(descr);
}
}
@Entity
public class Prod extends Model {
@OneToOne(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
@JoinColumn(name = "fk_prodDetail")
public ProdDetail prodDetail;
public Prod() {
super();
this.prodDetail = new ProdDetail();
}
public String getDescription() {
ProdDetail detail = this.prodDetail;
return detail.description;
}
}
@Entity
public class ProdDetail extends Model {
@Required
public String description;
public ProdDetail() {
super();
}
}
NOT WORKING VERSION:
public class Prods extends Controller {
private static Prod createOrGet() {
Prod prod = Prod.find("").first();
if(prod == null) {
Prod p = new Prod();
p.prodDetail.description = "test";
p.save();
prod = Prod.find("").first();
}
return prod;
}
public static void index() {
Prod prod = createOrGet();
ProdDetail detail = prod.prodDetail;
String descr = detail.description;
renderText(descr);
}
public static void index2() {
Prod prod = createOrGet();
String descr = prod.getDescription();
renderText(descr);
}
}
@Entity
public class Prod extends Model {
@OneToOne(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
@JoinColumn(name = "fk_prodDetail")
public ProdDetail prodDetail;
public Prod() {
super();
this.prodDetail = new ProdDetail();
}
public String getDescription() {
ProdDetail detail = this.prodDetail;
return detail.description;
}
}
@Entity
public class ProdDetail extends Model {
@Required
public String description;
public ProdDetail() {
super();
A WORKING VERSION:
public class Prods extends Controller {
private static Prod createOrGet() {
Prod prod = Prod.find("").first();
if(prod == null) {
Prod p = new Prod();
p.prodDetail.description = "test";
p.save();
prod = Prod.find("").first();
}
return prod;
}
public static void index() {
Prod prod = createOrGet();
ProdDetail detail = prod.prodDetail;
String descr = detail.description;
renderText(descr);
}
public static void index2() {
Prod prod = createOrGet();
String descr = prod.getDescriptionCHANGED();
renderText(descr);
}
}
@Entity
public class Prod extends Model {
@OneToOne(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
@JoinColumn(name = "fk_prodDetail")
public ProdDetail prodDetail;
public Prod() {
super();
this.prodDetail = new ProdDetail();
}
public String getDescriptionCHANGED() {
--