Создание ORMapping с использованием отношений OneToMany для 3 таблиц - PullRequest
1 голос
/ 28 февраля 2011

У меня есть 3 таблицы: проект, пользователь и роль. Теперь я хотел бы иметь таблицу Project2User2Role со встроенным ключом id_project, id_user,.

Я попробовал это, используя отношения @OneToMany во всех трех объектах, но я думаю, что не могу построить это так.

И я также попытался создать класс сущности Project2User2Role самостоятельно, но затем мне нужно создать idclass без отношений @ManyToOne.

Как может выглядеть решение?

Ответы [ 2 ]

1 голос
/ 28 февраля 2011

Для JPA 1 нельзя использовать сущности в качестве идентификатора. Из JPA 1 Spec (2.1.14)

Первичный ключ (или поле или свойство составного первичного ключа) должен быть один из следующих типов: любой Java примитивный тип; любая примитивная обертка тип; java.lang.String; java.util.Date; java.sql.Date.

Если вы используете JPA 1, у вас есть две альтернативы:

A. Вам потребуется создать Project2User2Role с автоматически сгенерированным полем идентификатора, и вы должны указать его в качестве своего идентификатора сущности. Затем вы можете добавить свои отношения в Project, User и Role и указать их соответствующие сопоставления аннотаций (ManyToOne). Пример:

@Entity
public class Project2User2Role {

    private Long id;

    private Project project;

    private User user;

    private Role role;

    @Id
    @GeneratedValue(strategy=GenerationType.SEQUENCE, generator="SEQPRUSROLID")
    @SequenceGenerator(name="SEQPRUSROLID", sequenceName="SEQPRUSROLID", allocationSize=1)
    public Long getId() {
        return id;
    }

    @ManyToOne
    public Project getProject() {
        return project;
    }

    @ManyToOne
    public User getUser() {
        return user;
    }

    @ManyToOne
    public Role getRole() {
        return role;
    }
    //the setters
}

B. Вы можете создать свой класс сущностей и продолжать использовать составной идентификатор, но в качестве JPA 1 Spec вы не можете указывать сущности в качестве идентификатора, поэтому вам нужно будет использовать базовые столбцы для этого примера:

@Entity
public class Project2User2Role {

    @EmbeddedId
    private Project2User2RoleId project2User2RoleId;

    @ManyToOne
    @JoinColumn(insertable=false, updatable = false)
    private Project project;
    @ManyToOne
    @JoinColumn(insertable=false, updatable = false)
    private User user;
    @ManyToOne
    @JoinColumn(insertable=false, updatable = false)
    private Role role;

    //getters/setters
}

    @Embeddable
    class Project2User2RoleId {
        private Long projectId;
        private Long userId;
        private Long roleId;

    }

Для JPA 2 :

C. Вы можете указать сущности в качестве своего идентификатора для примеров и определений, пожалуйста, прочтите 2.4 спецификации JPA 2.0: http://jcp.org/aboutJava/communityprocess/final/jsr317/index.html 2.2.3 из документации Hibernate: http://docs.jboss.org/hibernate/stable/annotations/reference/en/html_single/#entity-mapping-identifier

1 голос
/ 28 февраля 2011

Справочное руководство говорит о том, что вы можете встроить связь во встроенный идентификатор:

Хотя Hibernate не поддерживается в JPA, вы можете поместить свою связь непосредственно во встроенный идентификатор.component

Таким образом, вы должны определить сущность Project2User2Role с идентификатором типа Project2User2RoleId:

@Entity
public class Project2User2Role {
    @EmbeddedId
    private Project2User2RoleId id;

    public User getUser() {
        return this.id.getUser();
    }

    public Project getProject() {
        return this.id.getProject();
    }

    // ...
}

Класс Project2User2RoleId будет выглядеть следующим образом:

@Embeddable 
public class Project2User2RoleId {
    @ManyToOne(optional = false)
    @JoinColumn(name = "project_id")
    private Project project;

    @ManyToOne(optional = false)
    @JoinColumn(name = "user_id")
    private User user;

    @ManyToOne(optional = false)
    @JoinColumn(name = "role_id")
    private Role role;

    // constructor
    // getters
    // equals and hashCode
}
...