2012-12-09 3 views
1

저는 수업 메뉴를 가지고 있습니다. 그것은 manytoone과 onetomany relational을 가진 자기 자신입니다. 컨트롤러 코드에서목록을 serialize하십시오 <object> manytoone & onetomay with json

package models; 

import java.util.*; 
import javax.persistence.*; 
import play.db.ebean.*; 
import play.data.format.*; 
import play.data.validation.*; 
import static play.data.validation.Constraints.*; 
import javax.validation.*; 

import org.codehaus.jackson.annotate.JsonBackReference; 
import org.codehaus.jackson.annotate.JsonIgnore; 
import org.codehaus.jackson.annotate.JsonManagedReference; 

import com.avaje.ebean.*; 
import play.i18n.Messages; 
@Entity 
public class Menu extends Model { 

@Id 
@GeneratedValue(strategy = GenerationType.AUTO) 
public Long id; 

@Required 
@MinLength(4) 
@MaxLength(30) 
public String name; 

public String url; 

@Transient 
public boolean hasChild() { 
    return url.isEmpty(); 
} 

public Integer idx; 

@Temporal(TemporalType.TIMESTAMP) 
@Formats.DateTime(pattern = "yyyy/MM/dd hh:mm:ss") 
public Date created; 

@Required 
public boolean enabled; 

@ManyToOne 
     @JsonBackReference 
public Menu parent; 

@OneToMany 
@JsonManagedReference("parent") 
public List<Menu> children; 

public static Model.Finder<Long, Menu> find = new Model.Finder<Long, Menu>(Long.class, Menu.class); 

public static List<Menu> findTops() { 
    return find.where().eq("parent_id", null).eq("enabled", true).orderBy("idx asc").findList(); 
} 


public static List<Menu> findChildsByParent(Menu parent) { 
    return findChildsByParent(parent, true); 
} 

public static List<Menu> findChildsByParent(Menu parent, boolean enabled) { 
    return find.where().eq("parent_id", parent.id).eq("enabled", enabled).orderBy("idx asc").findList(); 
} 

public static boolean hasChilds(Menu parent) { 
    return hasChilds(parent, true); 
} 

public static boolean hasChilds(Menu parent, boolean enabled) { 
    return find.where().eq("parent_id", parent.id).eq("enabled", enabled).findList().size() > 0; 
} 

public static Page<Menu> findPage(int page, int size) { 
    return find.findPagingList(size).getPage(page - 1); 
} 


public Menu() { 
} 
} 

은 다음과 같습니다

@BodyParser.Of(BodyParser.Json.class) 
public static Result menuJson() { 
    if (menus == null) { 
     menus = Menu.find.all(); 
    } 

    JsonNode json = new ObjectMapper().valueToTree(menus); 

    return ok(json); 
} 

오류 정보는 다음과 같습니다

[RuntimeException: java.lang.IllegalArgumentException: Query threw SQLException:Unknown column 't1.menu_id' in 'on clause' Bind values:[1] Query was: select t0.id c0 , t1.id c1, t1.name c2, t1.url c3, t1.idx c4, t1.created c5, t1.enabled c6, t1.parent_id c7 from menu t0 left outer join menu t1 on t1.menu_id = t0.id where t0.id = ? order by t0.id (through reference chain: com.avaje.ebean.common.BeanList[0]->models.Menu["children"])] 

그것은 거기에이 방법 또는 사용자 정의 직렬화 선언하는 방법을 해결하는 좋은 해결책이? 트리 모델에는 클래스 디자인에 좋은 객체가 없으므로이 환경에 더 좋은 디자인이 없을 것입니다.

+0

오류가 직렬화되지 않았기 때문에 쿼리 자체에서 오류가 발생합니다. 쿼리 던져 SQLException : 알 수없는 열 't1.menu_id' – Subin

+0

당신의 right.i 대답 있어요. 감사합니다. – sjbwylbs

답변

1

해결했습니다.

매핑을 추가하면 OneToMany가 작동합니다.

package models; 

import java.util.*; 
import javax.persistence.*; 
import play.db.ebean.*; 
import play.data.format.*; 
import play.data.validation.*; 
import static play.data.validation.Constraints.*; 
import javax.validation.*; 

import org.codehaus.jackson.annotate.JsonBackReference; 
import org.codehaus.jackson.annotate.JsonIgnore; 
import org.codehaus.jackson.annotate.JsonManagedReference; 

import com.avaje.ebean.*; 
import play.i18n.Messages; 

@Entity 
public class Menu extends Model { 

    @Id 
    @GeneratedValue(strategy = GenerationType.AUTO) 
    public Long id; 

    @Required 
    @MinLength(4) 
    @MaxLength(30) 
    public String name; 

    public String url; 

    @Transient 
    public boolean hasChild() { 
     return url.isEmpty(); 
    } 

    public Integer idx; 

    @Temporal(TemporalType.TIMESTAMP) 
    @Formats.DateTime(pattern = "yyyy/MM/dd hh:mm:ss") 
    public Date created; 

    @Required 
    public boolean enabled; 

    @ManyToOne 
    @JsonBackReference 
    public Menu parent; 

    @OneToMany(mappedBy = "parent", cascade = CascadeType.PERSIST) 
    @JsonManagedReference 
    public List<Menu> children; 

    public static Model.Finder<Long, Menu> find = new Model.Finder<Long, Menu>(Long.class, Menu.class); 

    public static List<Menu> findTops() { 
     return find.where().eq("parent_id", null).eq("enabled", true).orderBy("idx asc").findList(); 
    } 


    public static List<Menu> findChildsByParent(Menu parent) { 
     return findChildsByParent(parent, true); 
    } 

    public static List<Menu> findChildsByParent(Menu parent, boolean enabled) { 
     return find.where().eq("parent_id", parent.id).eq("enabled", enabled).orderBy("idx asc").findList(); 
    } 

    public static boolean hasChilds(Menu parent) { 
     return hasChilds(parent, true); 
    } 

    public static boolean hasChilds(Menu parent, boolean enabled) { 
     return find.where().eq("parent_id", parent.id).eq("enabled", enabled).findList().size() > 0; 
    } 

    public static Page<Menu> findPage(int page, int size) { 
     return find.findPagingList(size).getPage(page - 1); 
    } 


    public Menu() { 
    } 
}