Page、ProfileSection、および PageComponents との 3 つの多対多マッピングを持つロール エンティティがあります。Role ページをロードすると、適切にロードされますが、profileSection と PageComponents は 1 つのレコードしかロードしません。
以下は私のモデルです。
@Entity
@Table(name = "role", uniqueConstraints = {@UniqueConstraint(columnNames={"authority"})})
public class Role extends AbstractBaseModel implements GrantedAuthority {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@BusinessKey(include = MethodType.TO_STRING)
private int id;
@BusinessKey
private String authority;
@ManyToMany(cascade=CascadeType.ALL, fetch = FetchType.LAZY)
//@Fetch(value = FetchMode.SUBSELECT)
private Set<Page> pages;
@ManyToMany(cascade=CascadeType.ALL, fetch = FetchType.LAZY)
//@Fetch(value = FetchMode.SUBSELECT)
private Set<PageComponent> pageComponents;
@ManyToMany(cascade=CascadeType.ALL, fetch = FetchType.LAZY)
@Fetch(value = FetchMode.SELECT)
private Set<ProfileSection> profileSections;
}
Page.java
@XmlRootElement(name="page")
@Entity
@Table(name = "page", catalog = "public", uniqueConstraints = {@UniqueConstraint(columnNames = {"page_id", "page_title"})})
public class Page extends OrderedModel {
private static final long serialVersionUID = 1L;
@BusinessKey(include = MethodType.TO_STRING)
@Column(name = "page_id")
private String pageId;
@BusinessKey(include = MethodType.TO_STRING)
@Column(name = "page_title")
private String pageTitle;
@BusinessKey
@OneToMany(mappedBy="page", cascade = CascadeType.ALL, fetch = FetchType.LAZY)
private List<PageComponent> pageComponents;
}
ProfileSection.java
@Entity
@Table(name = "profile_section", catalog = "public", uniqueConstraints = {@UniqueConstraint(columnNames = "section_id")})
public class ProfileSection extends OrderedModel {
private static final long serialVersionUID = 1L;
@BusinessKey(include = MethodType.TO_STRING)
@Column(name = "section_id")
private String sectionId;
@BusinessKey(include = MethodType.TO_STRING)
@Column(name = "section_title")
private String sectionTitle;
}
PageComponent.java
@Entity
@Table(name = "page_component", catalog = "public", uniqueConstraints = {@UniqueConstraint(columnNames = "component_id")})
public class PageComponent extends BaseModel {
private static final long serialVersionUID = 1L;
@BusinessKey
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name="page_id")
private Page page;
@BusinessKey(include = MethodType.TO_STRING)
@Column(name = "component_id")
private String componentId;
@BusinessKey(include = MethodType.TO_STRING)
@Column(name = "component_title")
private String componentTitle;
@BusinessKey(include = MethodType.TO_STRING)
@Column(name = "component_type")
private String componentType;
}
そして、私のdaoの次のコード
List<Person> list = c.list();
for(Person p: list){
System.out.println("Roles size is:: "+p.getRoles().size());
Role r = p.getRoles().iterator().next();
System.out.println("Page Size is: "+r.getPages().size());
System.out.println("ProfileSection Size is: "+r.getProfileSections().size());
System.out.println("Page Components Size is: "+r.getPageComponents().size());
for(ProfileSection s : r.getProfileSections()) {
System.out.println(s.getSectionId());
}
}
結果は次のとおりです。
Roles size is:: 1 - Expected 1
Page Size is: 6 - Expected 6
ProfileSection Size is: 1 - Expected 3
Page Components Size is: 1 - Expected 4
あなたが提供したリンクに従って Role.java を変更しました。以下は変更されたエンティティです
@Entity
@Table(name = "role", uniqueConstraints = {@UniqueConstraint(columnNames={"authority"})})
public class Role extends AbstractBaseModel implements GrantedAuthority{
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@BusinessKey(include = MethodType.TO_STRING)
private int id;
@BusinessKey
private String authority;
@ManyToMany(cascade=CascadeType.ALL, fetch = FetchType.LAZY)
@JoinTable(name="role_page",
joinColumns={@JoinColumn(name="role_id", referencedColumnName="id")},
inverseJoinColumns={@JoinColumn(name="pages_id", referencedColumnName="id")})
private Set<Page> pages;
@ManyToMany(cascade=CascadeType.ALL, fetch = FetchType.LAZY)
@JoinTable(name="role_page_component",
joinColumns={@JoinColumn(name="role_id", referencedColumnName="id")},
inverseJoinColumns={@JoinColumn(name="pagecomponents_id", referencedColumnName="id")})
private Set<PageComponent> pageComponents;
@ManyToMany(cascade=CascadeType.ALL, fetch = FetchType.LAZY)
@JoinTable(name="role_profile_section",
joinColumns={@JoinColumn(name="role_id", referencedColumnName="id")},
inverseJoinColumns={@JoinColumn(name="profilesections_id", referencedColumnName="id")})
private Set<ProfileSection> profileSections;
}
以下はdaoコードです:
/**
* For Depth > 1, better use this method method.
* Example: Person person = personDAO.findByProperty("email", email, lazyOptions, true);
*/
@SuppressWarnings("unchecked")
public T findByProperty(String propertyName, Object value, HibernateCriteriaLazyOptions lazyOptions, boolean uniqueResult) {
JoinCriteriaHelper joiner = JoinCriteriaHelper.forClass(getGenericClass(), lazyOptions.getPaths());
Criteria c;
if(lazyOptions.getDepth() != null){
// this would only fetch properties a, b and e
c = joiner.getExecutableCriteria(getSession(), lazyOptions.getDepth());
//DetachedCriteria dc = joiner.getDetachedCriteria(Preload.DEPTH_2);
}else{
// this would fetch all properties a, b, c, d and e
c = joiner.getExecutableCriteria(getSession());
}
c.add(Restrictions.eq(propertyName, value));
if(getGenericClass().equals(Person.class)){
List<Person> list = c.list();
for(Person p: list){
System.out.println("Roles size is:: "+p.getRoles().size());
Role r = p.getRoles().iterator().next();
System.out.println("Page Size is: "+r.getPages().size());
System.out.println("ProfileSection Size is: "+r.getProfileSections().size());
System.out.println("Page Components Size is: "+r.getPageComponents().size());
for(ProfileSection s : r.getProfileSections()){
System.out.println(s.getSectionId());
}
}
}
return (T)UnproxyUtility.unproxy((T)c.uniqueResult());
}
以下は私のテーブルです:
CREATE TABLE "role"
(
id integer NOT NULL,
authority character varying(255),
CONSTRAINT role_pkey PRIMARY KEY (id),
CONSTRAINT role_authority_key UNIQUE (authority)
)
CREATE TABLE page
(
id bigserial NOT NULL,
created_date timestamp without time zone,
last_updated timestamp without time zone,
page_id character varying(255),
page_title character varying(255),
order_number bigint,
CONSTRAINT page_pkey PRIMARY KEY (id),
CONSTRAINT page_page_id_key UNIQUE (page_id),
CONSTRAINT page_page_id_key1 UNIQUE (page_id),
CONSTRAINT page_page_title_key UNIQUE (page_title)
)
CREATE TABLE role_page
(
role_id integer NOT NULL,
pages_id bigint NOT NULL,
CONSTRAINT role_page_pkey PRIMARY KEY (role_id, pages_id),
CONSTRAINT fk140574b8dc0483c9 FOREIGN KEY (pages_id)
REFERENCES page (id) MATCH SIMPLE
ON UPDATE NO ACTION ON DELETE NO ACTION,
CONSTRAINT fk140574b8facefbbe FOREIGN KEY (role_id)
REFERENCES "role" (id) MATCH SIMPLE
ON UPDATE NO ACTION ON DELETE NO ACTION
)
CREATE TABLE page_component
(
id bigserial NOT NULL,
created_date timestamp without time zone,
last_updated timestamp without time zone,
component_id character varying(255),
component_title character varying(255),
component_type character varying(255),
page_id bigint,
CONSTRAINT page_component_pkey PRIMARY KEY (id),
CONSTRAINT fk5b31d34d78d7191e FOREIGN KEY (page_id)
REFERENCES page (id) MATCH SIMPLE
ON UPDATE NO ACTION ON DELETE NO ACTION,
CONSTRAINT page_component_component_id_key UNIQUE (component_id)
)
CREATE TABLE role_page_component
(
role_id integer NOT NULL,
pagecomponents_id bigint NOT NULL,
CONSTRAINT role_page_component_pkey PRIMARY KEY (role_id, pagecomponents_id),
CONSTRAINT fk8af50636d6882e9f FOREIGN KEY (pagecomponents_id)
REFERENCES page_component (id) MATCH SIMPLE
ON UPDATE NO ACTION ON DELETE NO ACTION,
CONSTRAINT fk8af50636facefbbe FOREIGN KEY (role_id)
REFERENCES "role" (id) MATCH SIMPLE
ON UPDATE NO ACTION ON DELETE NO ACTION
)
CREATE TABLE profile_section
(
id bigserial NOT NULL,
created_date timestamp without time zone,
last_updated timestamp without time zone,
order_number bigint,
section_id character varying(255),
section_title character varying(255),
CONSTRAINT profile_section_pkey PRIMARY KEY (id),
CONSTRAINT profile_section_section_id_key UNIQUE (section_id),
CONSTRAINT profile_section_section_id_key1 UNIQUE (section_id)
)
CREATE TABLE role_profile_section
(
role_id integer NOT NULL,
profilesections_id bigint NOT NULL,
CONSTRAINT role_profile_section_pkey PRIMARY KEY (role_id, profilesections_id),
CONSTRAINT fkcac52086b893cd43 FOREIGN KEY (profilesections_id)
REFERENCES profile_section (id) MATCH SIMPLE
ON UPDATE NO ACTION ON DELETE NO ACTION,
CONSTRAINT fkcac52086facefbbe FOREIGN KEY (role_id)
REFERENCES "role" (id) MATCH SIMPLE
ON UPDATE NO ACTION ON DELETE NO ACTION
)
以下は、Hibernate によって実行されるクエリです。
Hibernate: select pages0_.role_id as role1_22_1_, pages0_.pages_id as pages2_1_, page1_.ID as ID17_0_, page1_.created_date as created2_17_0_, page1_.last_updated as last3_17_0_, page1_.order_number as order4_17_0_, page1_.page_id as page5_17_0_, page1_.page_title as page6_17_0_ from role_page pages0_ inner join public.page page1_ on pages0_.pages_id=page1_.ID where pages0_.role_id=?
Page Size is: 6
Hibernate: select profilesec0_.role_id as role1_22_1_, profilesec0_.profilesections_id as profiles2_1_, profilesec1_.ID as ID19_0_, profilesec1_.created_date as created2_19_0_, profilesec1_.last_updated as last3_19_0_, profilesec1_.order_number as order4_19_0_, profilesec1_.section_id as section5_19_0_, profilesec1_.section_title as section6_19_0_ from role_profile_section profilesec0_ inner join public.profile_section profilesec1_ on profilesec0_.profilesections_id=profilesec1_.ID where profilesec0_.role_id=?
ProfileSection Size is: 1
Hibernate: select pagecompon0_.role_id as role1_22_1_, pagecompon0_.pagecomponents_id as pagecomp2_1_, pagecompon1_.ID as ID18_0_, pagecompon1_.created_date as created2_18_0_, pagecompon1_.last_updated as last3_18_0_, pagecompon1_.component_id as component4_18_0_, pagecompon1_.component_title as component5_18_0_, pagecompon1_.component_type as component6_18_0_, pagecompon1_.page_id as page7_18_0_ from role_page_component pagecompon0_ inner join public.page_component pagecompon1_ on pagecompon0_.pagecomponents_id=pagecompon1_.ID where pagecompon0_.role_id=?
Page Components Size is: 1
結果を確認する場合:
Pages are getting 6 - This is expected as the rows are 6 for that particular role id
PageComponents 1 - This is wrong as the rows matching for that role id are 4
ProfileSections 1 - This is also wrong matching rows are 4.
どこが間違っているのか理解できません。提案に従ってエンティティを更新しましたが、それでも結果は期待どおりではありません。多対多に取り組むのはこれが初めてではありません。これまで、この種の問題は発生していません。Role.javaでjoinTableをマッピングしなくても、期待どおりの結果が得られました。
私が間違っているときは教えてください。