Java 使用额外列映射@ManyToMany关联表

Java 使用额外列映射@ManyToMany关联表,java,hibernate,jpa,mapping,Java,Hibernate,Jpa,Mapping,我的数据库包含3个表:person、document和peson\u document。Person和Document具有多对多关系,并与包含添加列的Person\u Document表连接。 这是我的映射: class Person { @Cascade(CascadeType.ALL) @OneToMany(mappedBy = "compositePK.person", orphanRemoval = true) Set<PersonDocument>

我的数据库包含3个表:
person
document
peson\u document
。Person和Document具有多对多关系,并与包含添加列的
Person\u Document
表连接。 这是我的映射:

class Person {
    @Cascade(CascadeType.ALL)
    @OneToMany(mappedBy = "compositePK.person", orphanRemoval = true)
    Set<PersonDocument> personDocuments;
}

class Document {
    @OneToMany(mappedBy = "compositePK.document")
    Set<PersonDocument> personDocuments;
}

class PersonDocument {

    @EmbeddedId
    private CompositePK compositePK;

    @Column(name = "person_origin_id")
    private String personID;

    @ManyToOne(fetch = FetchType.LAZY)
    private Provider provider;    

    @Embeddable
    public static class CompositePK implements Serializable {

        @ManyToOne(fetch = FetchType.LAZY)
        private Person person;

        @ManyToOne(fetch = FetchType.LAZY)
        @JoinColumn(name = "documents_guid")
        private Document document;
    }
班级人员{
@级联(级联类型.ALL)
@OneToMany(mappedBy=“compositePK.person”,orphan=true)
设置个人文档;
}
类文档{
@OneToMany(mappedBy=“compositePK.document”)
设置个人文档;
}
班级个人文件{
@嵌入ID
私人复印机复印机复印机;
@列(name=“person\u origin\u id”)
私人字符串人形;
@manytone(fetch=FetchType.LAZY)
私人供应商;
@可嵌入
公共静态类CompositePK实现可序列化{
@manytone(fetch=FetchType.LAZY)
私人;
@manytone(fetch=FetchType.LAZY)
@JoinColumn(name=“documents\u guid”)
私人文件;
}
在我的代码中,我尝试如下方式保存此实体:

Set<PersonDocument> pds = new HashSet<>();
Document doc = new Document();
//set doc, set person to new PersonDocument and add once on pds set.
person.getPersonDocuments().addAll(pds);
personRepository.save(person);
Set pds=new HashSet();
单据单据=新单据();
//设置文档,将人员设置为新人员文档,并在pds集合中添加一次。
person.getPersonDocuments().addAll(pds);
personRepository.save(person);
问题是hibernate没有保存它并抛出异常:
在表上插入或更新违反了外键约束
-因为在
文档
表中没有记录。那么为什么hibernate在保存
个人文档
之前不保存
文档
,以及如何解决此问题?

尝试以下操作:

public class Person {
    @OneToMany(mappedBy = "person", orphanRemoval = true, cascade= CascadeType.ALL)
    Set<PersonDocument> personDocuments;
}



向上投票。就我个人而言,我总是用2
OneToMany
替换我的
ManyToMany
。它给了你更多的控制权,例如通过级联,它允许你通过更改person文档上的引用将文档从一个人移动到另一个人。我认为
ManyToMany
不应该实现d、 Alan,谢谢你的回答,但现在我有另一个问题-当我试图保存
PersonDocument
时,我遇到了异常:
无法通过model.entity.PersonDocument$CompositePK.document的反射setter设置字段值,无法理解为什么会这样?它在自己的类中吗定义文件?原始代码将其作为PersonDocument中的嵌套类。正如JPA规范所指出的,“实体[和可嵌入]类必须是顶级类。”JPA规范第2.1节和第2节。5@AlanHay,我更改了我的代码,现在它在自己的类定义中,但我仍然得到相同的异常:
无法通过model.entity.PersonDocumentPK.document的反射setter设置字段值
添加get/set方法?
class Document {
    @OneToMany(mappedBy = "document")
    Set<PersonDocument> personDocuments;
}
public class PersonDocument {

    @EmbeddedId
    private CompositePK compositePK;

    @MapsId("person")
    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = "person_origin_id")
    private Person person;

    @MapsId("document")
    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = "documents_guid")
    private Document document;

    @ManyToOne(fetch = FetchType.LAZY)
    private Provider provider;    
}
@Embeddable
public class CompositePK implements Serializable {

    //these fields should have the same type as the ID field of the corresponding entities
    //assuming Long but you have ommitted the ID fields

    private Long person;

    private Long document;

    //implement equals() and hashcode() as per the JPA spec
}
//you must always set both side of the relationship
Person person = new Person();
Document document = new Document();
PersonDocument pd = new PersonDocument();
pd.setPerson(person);
pd.setDocument(document);
person.getPersonDocuments.add(pd);//assumes initialized