Самостоятельное присоединение JPA с использованием JoinTable

У меня есть 1 элемент вызова объекта, в котором я хочу иметь возможность связать родительские элементы с дочерними элементами. использовать таблицу соединений для создания отношения родитель/потомок. Я не смог получить хорошую документацию. Так что, если у кого-то есть какие-либо мысли, я весь внимание.

Вот что у меня есть... что работает большую часть времени.

public class Item implements java.io.Serializable {
     @Id
     private Long id;

     @ManyToOne(optional = true, fetch = FetchType.LAZY)
     @JoinTable(name = "ITEMTOITEM", joinColumns = { @JoinColumn(name = "ITEMID") }, inverseJoinColumns = { @JoinColumn(name = "PARENTITEMID") } )
     private Item parent;

     @OneToMany(mappedBy = "parent", fetch = FetchType.LAZY)
     private List<Item> children;
}

Иногда, когда я хочу вернуть объекты, привязанные к этой таблице элементов, я получаю следующее сообщение об ошибке:

org.springframework.web.util.NestedServletException: Request processing failed; nested exception is org.springframework.webflow.engine.ActionExecutionException: Exception thrown executing [AnnotatedAction@6669ff5 targetAction = com.assisted.movein.web.common.nav.NavAction@6edf74b7, attributes = map['method' -> 'handleEntry']] in state 'oneTimeChargesAndFeesView' of flow 'in-flow' -- action execution attributes were 'map['method' -> 'handleEntry']'; nested exception is Exception [TOPLINK-4002] (Oracle TopLink Essentials - 2.0.1 (Build b04-fcs (04/11/2008))): oracle.toplink.essentials.exceptions.DatabaseException
Internal Exception: java.sql.SQLException: ORA-00904: "PARENTITEM_ITEMID": invalid identifier

 Error Code: 904
 Call: SELECT ITEMID, ITEMSHORTDESC, EFFENDDATE, ITEMDESC, PARENTITEM_ITEMID,  ITEMTYPECODE FROM ITEM WHERE (ITEMID = ?)
    bind => [1250]
Query: ReadObjectQuery(com.domain.Item)

Любая помощь будет оценена по достоинству.


person jtoepfer    schedule 05.03.2013    source источник
comment
Здесь я собрал табличную диаграмму здесь.   -  person jtoepfer    schedule 05.03.2013
comment
Последнее небольшое предостережение: мне нужно, чтобы это работало с eclipselink и toplink-essentials. Поэтому я ограничен использованием сопоставлений JPA 1.0.   -  person jtoepfer    schedule 05.03.2013


Ответы (3)


Попробуйте использовать @JoinColumnвместо этого:

 @ManyToOne(optional = true, fetch = FetchType.LAZY)
 @JoinColumn(name = "PARENTITEMID", referencedColumnName = "ITEMID")
 private Item parent;

 @OneToMany(
        cascade = {CascadeType.ALL},
        orphanRemoval = true,
        fetch = FetchType.LAZY
 )
 @JoinColumn(name = "PARENTITEMID")
 private List<Item> children;
person Michail Nikolaev    schedule 05.03.2013
comment
Я хочу использовать таблицу соединений между родительским и дочерним объектом. Я считаю, что ваше сопоставление допускает только одно сопоставление самого себя. - person jtoepfer; 05.03.2013
comment
Это сопоставление без дополнительной таблицы. Каждый потомок имеет ссылку на родителя. - person Michail Nikolaev; 05.03.2013

После большого чтения JPA 2.0 я понял, что мне нужна более новая версия Eclipselink 2.3+, чтобы поддерживать то, что я пытался сделать. Вот код, который действительно работал в моем случае, но он не будет работать из-за нашей зависимости от более старой версии [EclipseLink 2.0.2]. Кроме того, в другом проекте все еще используется Toplink-essentials JPA 1.0, который снова соответствует этой нотации.

public class Item {

@ManyToOne(optional = true, fetch = FetchType.LAZY)
@JoinTable(name = "ITEMINCENTIVESMAPPING", 
        joinColumns = { @JoinColumn(name = "INCENTIVEITEMID", referencedColumnName = "ITEMID", insertable = false, updatable = false) }, 
        inverseJoinColumns = { @JoinColumn(name = "ITEMID", referencedColumnName = "ITEMID", insertable = false, updatable = false) } )
private Item parentItem;

@OneToMany(fetch = FetchType.LAZY)
@JoinTable(name = "ITEMINCENTIVESMAPPING", 
        joinColumns = { @JoinColumn(name = "INCENTIVEITEMID", referencedColumnName = "ITEMID") }, 
        inverseJoinColumns = { @JoinColumn(name = "ITEMID", referencedColumnName = "ITEMID") } )
private List<Item> items;

}
person jtoepfer    schedule 21.03.2013
comment
Мне кажется, что вы сопоставили два отдельных отношения: однонаправленное «многие к одному» и однонаправленное «один ко многим». Почему бы не отобразить единую двунаправленную связь? Это решение было предложено для самоссылающихся отношений «многие ко многим» (использовалось двунаправленное отображение): drag0sd0g.blogspot.com/2010/03/ - person scottb; 08.06.2016
comment
Как вы можете выполнить пользовательскую операцию CRUD для этого типа модели? например получить с помощью parentItem(). Любая помощь приветствуется. Спасибо!!! - person Musa; 21.04.2017

Я считаю, что @JoinTable разрешено только для @OneToOne, @OneToMany или @ManyToMany, я не думаю, что это имеет смысл для @ManyToOne. Используйте @JoinColumn или @OneToOne.

Также ваш @OneToMany не имеет смысла, mappedBy должен быть атрибутом, и у вас нет parentItem, он должен быть родительским, а родительский должен использовать @JoinColumn.

person James    schedule 05.03.2013
comment
Джеймс, спасибо за внимание, mappedBy был ошибкой CAP. Я исправил в оригинале. - person jtoepfer; 05.03.2013