Гость
Целевая тема:
Создать новую тему:
Автор:
Форумы / Java [игнор отключен] [закрыт для гостей] / JPA: OneToOne relation owner / 17 сообщений из 17, страница 1 из 1
15.05.2017, 08:31
    #39452891
Hett
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Хочу добавить связь OneToOne, делаю так:
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
@Entity()
@Table(name = "user")
public class User {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;

    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "id", referencedColumnName = "user_id")
    private Address address;

    public int getId() {
        return id;
    }

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

    public Address getAddress() {
        return address;
    }

    public void setAddress(Address address) {
        this.address = address;
    }

}



@Entity
@Table(name = "address")
public class Address extends com.mezoline.domain.common.Entity {

    @Id
    @GeneratedValue
    private int id;

    @OneToOne(mappedBy = "address")
    private User user;

    public int getId() {
        return id;
    }

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

    public User getUser() {
        return user;
    }

    public void setUser(User user) {
        this.user = user;
    }

}



Пытаюсь сохранить:

Код: java
1.
2.
3.
4.
Address address = createAddress();
address.setUser(user);
user.setAddress(address);
user = entityManager.merge(user);





В проекте включена автогенерация схемы СУБД.
При вышеуказанном конфиге JPA не создает столбец Address.user_id ну и естественно связь между данными не устанавливается.
Никаких предупреждений и ошибок при деплое нет.

При всем этом, если изменить владельца связи:

Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
public class User { 
    ...
    @OneToOne(cascade = CascadeType.ALL, mappedBy = "user")
    private Address address;
    ...
}

public class Address {
    ....
    @OneToOne()
    @JoinColumn(name = "user_id")
    private User user;
    ....
}




То все начинает работать ожидаемо.
В чем соль?
...
Рейтинг: 0 / 0
15.05.2017, 10:34
    #39452951
Petro123
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
HettВ проекте включена автогенерация схемы СУБД.
а как же ОРМ узнает какой вам вариант из трёх надо?
19133239
В жизни в СУБД бывает 3 варианта один ко многим.
...
Рейтинг: 0 / 0
15.05.2017, 10:42
    #39452962
Hett
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Petro123HettВ проекте включена автогенерация схемы СУБД.
а как же ОРМ узнает какой вам вариант из трёх надо?
19133239
В жизни в СУБД бывает 3 варианта один ко многим.

У меня OneToOne, какие тут варианты могут быть? Да и оба конфига равнозначные (по крайней мере в моем понимании).
...
Рейтинг: 0 / 0
15.05.2017, 10:45
    #39452964
Petro123
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
HettУ меня OneToOne, какие тут варианты могут быть?
Ты не читаешь что тебе пишут?
Выше по ссылке даны 3 варианта бизнес-маппинга и 2 варианта реализации табличек в БД.
Какая строчка непонятна?
Я бы не писал их тебе, если бы ты не генерировал БД по маппингу.
Это мало кто делает.
Все делают наоборот.
...
Рейтинг: 0 / 0
15.05.2017, 10:53
    #39452970
Petro123
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
HettДа и оба конфига равнозначные (по крайней мере в моем понимании).
у тебя 2 варианта:
- запомнить тот что у тебя рабочий и идти дальше
- разбираться с конфигом @Embedded\ Not @Embedded \...
И там будут видны различия.
Легче запомнить и идти дальше.
...
Рейтинг: 0 / 0
15.05.2017, 11:11
    #39452980
Hett
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Petro123,

я не спрашивал какие существуют варианты реализации табличек, я реализовал так как мне удобно. В твоем списке это третий вариант и у меня по нему конкретный вопрос, если не можешь на него ответить, не разводи флуд. Embedded тут вообще не причем.
...
Рейтинг: 0 / 0
15.05.2017, 11:31
    #39452994
Petro123
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Hett,
OK
HettТо все начинает работать ожидаемо.
В чем соль?
Это Helo World для JPA в 3-м варианте.
Надо просто запомнить. В этом соль.
Удачи!
...
Рейтинг: 0 / 0
15.05.2017, 13:40
    #39453118
Hett
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Единственная мысль, которая приходит в голову:
Владелец связи в данном случае определяет, какая на таблицу будет ссылаться (т.е. в какой таблице будет находиться констрейнт).
Если рассматривать мой пример, то таблица User не может содержать констрейт с поля id на поле Address.user_id, так как поле id - PK. Странно, что хибер не генерит никаких ошибок или предупреждений по этому поводу.
Видимо решением остается располагать констрейнт в таблице Address, а в User указывать mapped.
...
Рейтинг: 0 / 0
15.05.2017, 13:59
    #39453140
Petro123
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
HettСтранно, что хибер не генерит никаких ошибок или предупреждений по этому поводу.
основная задача ОРМ - маппинг _существующей_ схемы БД.
Остальное только фичи и "синтаксический сахар".
...
Рейтинг: 0 / 0
15.05.2017, 14:08
    #39453147
Hett
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Petro123HettСтранно, что хибер не генерит никаких ошибок или предупреждений по этому поводу.
основная задача ОРМ - маппинг _существующей_ схемы БД.
Остальное только фичи и "синтаксический сахар".

Хватит тут прибибикивать.
В любом случае ОРМ могла бы хотя бы возмутиться такому факту.
...
Рейтинг: 0 / 0
15.05.2017, 14:26
    #39453166
Petro123
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
HettХватит тут прибибикивать.
угу.
Так все свитчевавшиеся в Java из PHP\Делфи говорят)).
Начинают делать тут революцию (JSF\EE) и негодовать). LOL
Где спека что тебе должны? (с)
...
Рейтинг: 0 / 0
15.05.2017, 17:07
    #39453312
Usman
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
HettВ чем соль?Возможно необходимо указать явно, что поле уникальное:
Hett
Код: java
1.
2.
3.
    @Column(unique = true)
    @OneToOne(mappedBy = "address")
    private User user;
...
Рейтинг: 0 / 0
15.05.2017, 17:14
    #39453322
Hett
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Usman,

неа, говорит

Код: plaintext
org.hibernate.AnnotationException: @Column(s) not allowed on a @OneToOne property
...
Рейтинг: 0 / 0
15.05.2017, 17:19
    #39453333
Usman
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Hett
Код: plaintext
@Column(s) not allowed on a @OneToOne property
Ой! Все правильно. Не с той стороны (:
Hett
Код: java
1.
2.
3.
    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "id", referencedColumnName = "user_id", unique = true)
    private Address address;
...
Рейтинг: 0 / 0
15.05.2017, 17:34
    #39453347
Hett
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Неа, все так же.
Если в схеме есть колонка, то он туда null вставляет.
Если удалить таблицу, то hibernate создает новую без колонки user_id
Он и ограничение не создает, видимо как-то "не видит связи", или видит ее как-то не так.
Может быть он смотрит на колонку id, видит так ограничение в виде PK и на этом успокаивается? Откуда ему знать, что надо создавать ограничение с Address.user_id на User.id а не наоборот, если овнером связи является User ?
...
Рейтинг: 0 / 0
17.05.2017, 12:42
    #39454554
Юрий321
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Hett,

у тебя в обеих сущностях простые id с именем "id", плюс ты генеришь базу из сущностей.
вопрос - зачем @JoinColumn?

сделай
Код: java
1.
2.
@OneToOne(cascade = CascadeType.ALL)
private Address address;



и в обратную сторону (от адреса к юзеру) тоже самое
...
Рейтинг: 0 / 0
17.05.2017, 13:04
    #39454574
Hett
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
JPA: OneToOne relation owner
Юрий321,

Гммм, спасибо.
Если не указывать JoinColumn, то он в общем-то и одностороннюю связь делает нормально.

Код: java
1.
2.
    @OneToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL)
    private Address address;



Код: java
1.
2.
    @OneToOne(mappedBy = "address")
    private User user;



Конфиг там идентичный следующему будет:

Код: java
1.
2.
3.
    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "address_id", referencedColumnName = "id")
    private Address address;



Если mappedBy не указывать, то получается 2 разные связи.
Вроде разобрался.
...
Рейтинг: 0 / 0
Форумы / Java [игнор отключен] [закрыт для гостей] / JPA: OneToOne relation owner / 17 сообщений из 17, страница 1 из 1
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]