Postgres UUID и Hibernate → столбец не найден - PullRequest
0 голосов
/ 15 июня 2019

У меня проблемы с использованием Postgres UUID type, java.util.UUID и Hibernate.

Все отлично работает с нативными запросами, но когда я пытаюсь использовать HQL, он сообщает, что не может найти столбец идентификатора: column huser0_.id does not exist.

Вот код для хранилища:

import com.xobotun.common.HUser;
import java.util.UUID;

@org.springframework.stereotype.Repository
public interface ReadOnlyUserRepository extends Repository<HUser, UUID> {
    // @Query("select u from HUser u where u.id = :id")
    @Query(value = "select * from \"user\" where id = :id", nativeQuery = true)
    HUser getById(@Param("id") UUID id);

}

Таким образом он печатает ожидаемый

HUser(id=fbd3c9e2-8fa4-11e9-bc42-526af7764f64, name=test, about=test, isPermabanned=false, created=2019-06-15T19:37:30.503, lastActive=2019-06-15T19:37:33.512)

Но когда закомментирует собственный запрос и использует HQL, он неожиданно перестает работать:

org.postgresql.util.PSQLException: ERROR: column huser0_.id does not exist

Кто-нибудь сталкивался?такая проблема?Спасибо.


Еще немного информации, чтобы понять вопрос и проверить, нет ли у меня опечаток.:)

Таблица DDL:

CREATE TABLE "user" (
  id             UUID                    NOT NULL PRIMARY KEY,
  name           TEXT                    NOT NULL,
  is_permabanned BOOLEAN DEFAULT FALSE   NOT NULL,
  created        TIMESTAMP DEFAULT now() NOT NULL,
  last_active    TIMESTAMP,
  about          TEXT
);

Класс сущности:

package com.xobotun.common;

import lombok.Data;

import javax.persistence.*;
import java.time.LocalDateTime;
import java.util.UUID;

@Data
@Entity
@Table(name = "user")
public class HUser {
    @Id
    @Column(name = "id") //, columnDefinition = "uuid", updatable = false)
//    @Type(type="pg-uuid")
    private UUID id;

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

    @Column(name = "about")
    private String about;

    @Column(name = "is_permabanned")
    private Boolean isPermabanned;

    @Column(name = "created")
    private LocalDateTime created;

    @Column(name = "last_active")
    private LocalDateTime lastActive;
}

Как видите, я экспериментировал с различными опциями в поле id, но ни одной из них.из них работали с HQL-запросом.

Версия Java - 11, PostgreSQL - также 11, и здесь есть связанные зависимости:

dependencies {
    compile 'org.springframework.data:spring-data-jpa:2.1.5.RELEASE'
    compile 'javax.persistence:javax.persistence-api:2.2'
    compile 'com.vladmihalcea:hibernate-types-52:2.4.4'

    implementation 'org.hibernate:hibernate-core:5.4.3.Final'
    implementation 'org.postgresql:postgresql:42.2.5.jre7'
}

Кроме того, я пробовал решения в этих вопросах, но они былибез помощи: 1 2 3 4

UPD1 : Вот SQL, сгенерированный Hibernateпри неудачном запросе:

    select
        huser0_.id as id1_0_,
        huser0_.about as about2_0_,
        huser0_.created as created3_0_,
        huser0_.is_permabanned as is_perma4_0_,
        huser0_.last_active as last_act5_0_,
        huser0_.name as name6_0_ 
    from
        user huser0_ 
    where
        huser0_.id=?

1 Ответ

1 голос
/ 15 июня 2019

Благодаря доброму комментарию @JBNizet я обнаружил, что проблема не в странном поведении UUID, а в том, что Hibernate по умолчанию не экранирует идентификаторы.

На самом деле есть три простых решения вопроса:

  1. Не используйте зарезервированные ключевые слова, измените имя таблицы на другое.

  2. Вручную экранируйте имя таблицы (например, @Table(name = "\"user\"") в HUser.java).

  3. Добавить строку hibernate.globally_quoted_identifiers=true в вашу конфигурацию.Интересно, почему это не true по умолчанию ... Подробнее см. это .

...