Сопоставление: таблица содержит имя физического столбца, на которое ссылаются несколько имен логических столбцов.

У меня есть 3 класса - Issue, Sprint и EmbeddableId class SprintId.

Я не знаю, как добиться наличия поля jiraInstance как в классе Issue, так и в классе Sprint. Поскольку Issue не может быть подключен ни к какому Sprint, я хочу иметь поле jiraInstance java на Issue, чтобы отслеживать, в каком экземпляре jira была создана эта конкретная проблема. Когда он подключен к Sprint, я хочу просто иметь jiraInstance как часть его составного ключа. Но ниже сопоставление дает мне:

Caused by: org.hibernate.DuplicateMappingException: Table [issue] contains physical column name [jira_instance] referred to by multiple logical column names: [jira_instance], [jiraInstance]

классы:

class Issue {
    @ManyToOne()
    @JoinColumns({
            @JoinColumn(
                    name = "sprint_id",
                    referencedColumnName = "sprint_id"),
            @JoinColumn(
                    name = "jira_instance",
                    referencedColumnName = "jira_instance")
    })
    private Sprint lastSprint;

    //this field causes clash with 'jira_instance' in @JoinColumn
    private String jiraInstance;
}

class Sprint {
    @EmbeddedId
    private SprintId id;
}
class SprintId implements Serializable {

    @Column(name = "sprint_id")
    private String sprintId;

    @Column(name = "jira_instance")
    private String jiraInstance;
}

Добавление @Column как:

@Column(name="jira_instance")
private String jiraInstance;

заставить hibernate утверждать, что он должен быть insertable = true, updatable = false, но мне нужно иметь возможность добавить jiraInstance в Issue, когда он не подключен к какому-либо спринту.


person freakman    schedule 16.02.2021    source источник


Ответы (2)


Чтобы уточнить - поскольку на этот вопрос пока нет отмеченного ответа:

Когда вы каким-либо образом используете ссылку на именованный столбец в одном поле класса, убедитесь, что ВСЕ ссылки используют одно и то же имя. Особенно, когда они называются по-разному (в вашем примере jira_instance против jiraInstance).

Следующий пример должен работать:

class Issue {
    @ManyToOne()
    @JoinColumns({
            @JoinColumn(
                    name = "sprint_id",
                    referencedColumnName = "sprint_id"),
            @JoinColumn(
                    name = "jira_instance",
                    referencedColumnName = "jira_instance") // make sure you use the same name
    })
    private Sprint lastSprint;

    @Column(name = "jira_instance") // make sure you use the same name
    private String jiraInstance;
}

class Sprint {
    @EmbeddedId
    private SprintId id;
}
class SprintId implements Serializable {

    @Column(name = "sprint_id")
    private String sprintId;

    @Column(name = "jira_instance") // make sure you use the same name
    private String jiraInstance;
}

Это означает: insertable = false, updatable = false не требуется для решения этой проблемы.

person Someone    schedule 24.06.2021

Вы должны понимать, что для записи столбца можно использовать только одно свойство/поле, иначе могут возникнуть конфликты. Используйте следующее сопоставление:

class Issue {
    @ManyToOne()
    @JoinColumns({
            @JoinColumn(
                    name = "sprint_id",
                    referencedColumnName = "sprint_id"),
            @JoinColumn(
                    name = "jira_instance",
                    referencedColumnName = "jira_instance", insertable = false, updatable = false)
    })
    private Sprint lastSprint;

    private String jiraInstance;
}

Вам просто нужно убедиться, что при установке lastSprint вы также устанавливаете jiraInstance в значение Sprint#jiraInstance.

person Christian Beikov    schedule 18.02.2021