简体   繁体   English

JPA中的双向关系

[英]Two-way relation in JPA

I have the two entity classes, User and MyCharacter. 我有两个实体类,User和MyCharacter。 User has a list of MyCharacters and each MyCharacter has a reference back to the User (owner). 用户有一个MyCharacters列表,每个MyCharacter都有一个对用户(所有者)的引用。 What I'd like to accomplish is, that I use the same join table for both relations, meaning, that the owner relation found in MyCharacter would automatically use the same join table as from User=>MyCharacter. 我要完成的是,我对两个关系使用相同的联接表,这意味着在MyCharacter中找到的所有者关系将自动使用与User => MyCharacter相同的联接表。 This means that the getOwner() method in MyCharacter should work without me having to explicitly at some point call setOwner(user). 这意味着MyCharacter中的getOwner()方法应该可以正常工作,而无需我显式地调用setOwner(user)。

To clear this a bit more, here's my unit test which currently fails (last assert fails) 为了更清楚一点,这是我当前失败的单元测试(最后一个断言失败)


@Test
public void testTwoWayRelation() {
    User user = new User();
    MyCharacter character = new MyCharacter();
    List<MyCharacter> chars = new ArrayList<MyCharacter>();
    chars.add(character);
    user.setCharacters(chars);

    facade.store(user);
    assertNotNull(character.getId());

    character = facade.find(MyCharacter.class, character.getId());

    assertNotNull(character.getOwner());
}

My entity classes are listed below. 我的实体类别如下。


@Entity
@Table(name = "myuser")
public class User {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    protected Long id;

    @OneToMany(cascade = { CascadeType.PERSIST })
    protected List<MyCharacter> characters;

    public User() {

    }

    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }


    public List<MyCharacter> getCharacters() {
        return characters;
    }

    public void setCharacters(List<MyCharacter> characters) {
        this.characters = characters;
    }

}


@Entity
public class MyCharacter{
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    protected Long id;

    @ManyToOne
    @JoinTable(name = "myuser_mycharacter", joinColumns = @JoinColumn(name = "characters_id"), inverseJoinColumns = { @JoinColumn(name = "user_id") })
    protected User owner;

    public MyCharacter() {

    }

    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }


    public User getOwner() {
        return owner;
    }

    public void setOwner(User owner) {
        this.owner = owner;
    }
}

That's how we join two entities with jpa in our project: 这就是我们在项目中使用jpa将两个实体结合在一起的方式:

    @Entity
    @Table(name = "Period")
    public class Period implements Serializable {
      private List<Delay> delays = new ArrayList<Delay>();

      @OneToMany(mappedBy="period") //name of the field in joined entity
      public List<Delay> getDelays() {
        return delays;
      }
    }

   @Entity
   @Table(name = "Delay")
   public class Delay implements Serializable {

    private Period period;

    @ManyToOne
    @JoinColumn(name = "PERIODID")
    public Period getPeriod() {
       return period;
    }   
}

我不确定我是否正确理解了您的问题,但是您可以尝试在MyCharacter.owner上设置mappingBy:

@ManyToOne(mappedBy="characters")

Here is an article from Oracle which explains how to map such relations. 这是 Oracle 的一篇文章 ,解释了如何映射这种关系。

When you use this in Java, depending on your JPA framework, you will need to add the MyCharacter to the list in User and set the user field in MyCharacter or only one of the two (because the framework will manage the other side for you). 当您使用此在Java中,这取决于您的JPA框架,你将需要添加MyCharacter到列表中的User ,并设置user领域MyCharacter或仅两个中的一个(因为框架将管理对方对你) 。 I suggest to write a small test to figure out what works (and you should write test cases for all the way in which you use your objects, anyway). 我建议编写一个小型测试来弄清楚什么可行(无论如何,您都应该为使用对象的所有方式编写测试用例)。

When objects are loaded from the database, you won't need to do that since all frameworks handle this case correctly. 从数据库加载对象时,您不需要这样做,因为所有框架都可以正确处理这种情况。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM