0

2つのリストを含むUser-classを永続化しようとしています。1つは特定のユーザーをフォローしているユーザーを確認するユーザー、もう1つは特定のユーザーがフォローしているユーザーを確認するユーザーです。

User.java:

@Entity
@XmlRootElement
@Table(name="Users")
public class User implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;
    private String name;
    private String web;
    private String bio;
    @OneToMany(cascade=CascadeType.ALL)
    private Collection<User> followers = new ArrayList();
    @OneToMany(cascade=CascadeType.ALL)
    private Collection<User> following = new ArrayList();

UserDAOJPA.javaユーザーを作成および変更するという名前のクラスがあります。

@Alternative
@Stateless
public class UserDAOJPA implements Serializable, IUserDAO {

    @PersistenceContext(unitName = "KwetterSOAPPU")
    private EntityManager em;

    @Override
    public void create(User user) {
        em.persist(user);
    }
@Override
    public List<User> getFollowers(User user) {
        List<User> followers;
        followers = (List<User>) user.getFollowers();
        return followers;
    }

    @Override
    public void addFollower(User user, User follower)
    {
        user.addFollower(follower);
        em.merge(user);
    }

    @Override
    public List<User> getFollowing(User user) {
        List<User> following;
        following = (List<User>) user.getFollowing();
        return following;
    }

    @Override
    public void addFollowing(User user, User following) {
        user.addFollower(following);
        em.merge(user);
    }
    @PostConstruct
    private void initUsers() {
        User u1 = new User("Hans", "http", "geboren 1");
        User u2 = new User("Frank", "httpF", "geboren 2");
        User u3 = new User("Tom", "httpT", "geboren 3");
        User u4 = new User("Sjaak", "httpS", "geboren 4");

        this.create(u1);
        this.create(u2);
        this.create(u3);
        this.create(u4);

        this.addFollowing(u1, u2);
        this.addFollower(u2, u1);
        this.addFollowing(u1, u3);
        this.addFollower(u3, u1);
        this.addFollowing(u1, u4);
        this.addFollower(u4, u1);

私自身の推測では、ユーザーのコレクションを見ると、User.javaクラスに正しいアノテーションがありません。

エラーメッセージ:

Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.3.2.v20111125-r10461): org.eclipse.persistence.exceptions.DatabaseException
Internal Exception: java.sql.SQLIntegrityConstraintViolationException: Column 'FOLLOWING_ID'  cannot accept a NULL value.
Error Code: -1
Call: INSERT INTO Users_Users (followers_ID, User_ID) VALUES (?, ?)
    bind => [2 parameters bound]
Query: DataModifyQuery(name="followers" sql="INSERT INTO Users_Users (followers_ID, User_ID) VALUES (?, ?)")
4

2 に答える 2

2

ユーザーとそのフォロワーの関係は、2つの1対多の関係ではなく、双方向の多対多の関係であるため、次のようにマップする必要があります。

@ManyToMany(mappedBy = "following")
private Collection<User> followers = new ArrayList<>();

@ManyToMany
@JoinTable(name = "followers",
    joinColumn = @Column(name = "follower_id"),
    inverseJoinColumn = @Column(name = "following_id"))
private Collection<User> following = new ArrayList<>();

また、論理的に「所有されている」エンティティを参照する場合は、通常、カスケードを使用する必要があることに注意してください。あなたの場合、Usersはお互いを「所有」していないので、それは意味がありません。

于 2013-01-24T11:29:16.577 に答える
1

コードをテストする環境がないため、推測しますが、createメソッドを変更して、EntityManager.mergeクラスからの戻り値を返し、次のように結果を使用する必要があると思います。

...

public User create(User user) {
    return em.merge(user);
}

...

User user = this.create(new User(...));
User follower = this.create(new User(...));
this.addFollower(user, follower);

エラーの理由は、永続化したマージ済みオブジェクトの状態を返さないため、フォロワーのIDへの参照が未定義であるためです。

于 2013-01-24T11:35:01.953 に答える