Алтернативен дизайнерски подход към @OneToMany еднопосочно картографиране не работи в OpenJPA

Здравейте експерти по бази данни,

Разгледайте следните таблици:

CREATE TABLE customers (
    id INTEGER NOT NULL PRIMARY KEY,
    name VARCHAR(100) NOT NULL,
    order_id INTEGER NOT NULL,
    CONSTRAINT customers_ibfk_1 FOREIGN KEY (order_id) REFERENCES   orders (id) ON DELETE CASCADE,
);

CREATE TABLE orders (
    id INTEGER NOT NULL PRIMARY KEY,
    date VARCHAR(100) NOT NULL,
    ...
);

Тъй като повечето от моите заявки и нужди в приложението просто изискват достъп до поръчките, свързани с клиент, реших да избера еднопосочно съпоставяне „един към много“ от клиенти към поръчки, тъй като множество поръчки могат да бъдат свързани с клиент. Подредих класовете обекти, както следва:

public class Customer implements Serializable {
...
    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
    @JoinColumn(name = "id", referencedColumnName = "order_id")
    private Set<Order>   orders;
....
}

Той се компилира добре с помощта на JPA 2.0 и OpenJPA 2.4.0. Въпреки това хвърля следното изключение по време на изпълнение:

 ...
 nested exception is <openjpa-2.4.0-r422266:1674604 fatal general error> org.apache.openjpa.persistence.PersistenceException: The transaction has been rolled back.  See the nested exceptions for details on the errors that occurred.] with root cause
 org.apache.openjpa.persistence.ArgumentException: You cannot join on column "customers.order_id".  It is not managed by a mapping that supports joins.

Когато се огледах, изглежда, че е известна грешка: https://issues.apache.org/jira/browse/OPENJPA-1607 .

Пропуснах ли нещо тук или това картографиране изглежда добре? За да преодолея този проблем, имам 2 подхода, доколкото виждам:

  1. Направете картографирането двупосочно. Въпреки това, както прочетох, в двупосочното картографиране OneToMany, ManyToOne е собственикът. Така че в този случай таблицата с поръчки ще бъде собственикът, което наистина не е така от гледна точка на дизайна. Няма да има поръчки, без клиент.
  2. Добавете многопосочно картографиране на ManyToOne от таблицата с поръчки към клиенти и за всякакви заявки за всички поръчки за конкретен клиент, просто направете заявка в таблицата с поръчки с идентификатора на клиента. Разбира се, това ще означава множество заявки за това, което трябваше да бъде една заявка.

Така че въпросът ми относно дизайна е: кой подход смятате, че е по-чист и по-ефективен? Има ли изобщо по-добър различен подход? Има ли някаква производителност или някакви други предимства от използването на еднопосочно картографиране вместо двупосочно картографиране? Огледах се, но не можах да намеря много статии за него. Не съм сигурен дали съм го пропуснал. Ако няма много ползи, тогава може да съм по-добре с подход 1.

Извинявам се ако съм пропуснал нещо. Всички указания са високо оценени. Благодаря ви за отделеното време предварително.

Благодаря,

Алис


person Alice    schedule 11.07.2015    source източник


Отговори (1)


Това работи, публикувам отговора, тъй като може да помогне на някой друг.

Оказва се, че еднопосочното съпоставяне работи в OpenJPA, стига да посочите таблица за свързване. Аз също виждах проблема, както е посочено в грешката: https://issues.apache.org/jira/browse/OPENJPA-1607 . Въпреки това, след като добавих таблица за присъединяване, тя работи като чар. Разбира се, това означава, че ще трябва да добавя допълнителна таблица, но това значително намалява количеството код и грешки при актуализации и изтривания. След като стигнем до изпълнението, ще видя как ще се представи. Но засега това е за мен. По-долу е фрагментът:

public class Customer implements Serializable {
    ...
    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
    @JoinTable(name = "customers_orders", 
        joinColumns = { @JoinColumn(name = "customer_id", referencedColumnName = "id") }, 
        inverseJoinColumns = { @JoinColumn(name = "order_id", referencedColumnName = "id") })
    private Set<Order>   orders;
    ....
}
person Alice    schedule 16.07.2015