web-dev-qa-db-ja.com

org.postgresql.util.PSQLException:エラー:列user0_.idは存在しません-Hibernate

Hibernateを使用してpostgresデータベースにマップされるモデルクラスがあります。私のモデルクラスは次のとおりです。

_@Entity
@Table(name="USER")
public class User {

    @Id 
    @GeneratedValue
    @Column(name="id")
    private long id;

    @Column(name="username", unique=true)
    private String username;

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

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

    public User(long id, String username, String email) {
        this.id = id;
        this.username = username;
        this.email = email;
    }
}
_

次のクエリを使用して、ユーザー名「adam」のユーザーを取得しようとしました。

_tx = session.beginTransaction();
TypedQuery<User> query = session.createQuery("FROM User u WHERE u.username = :username", User.class).setParameter("username", "adam");
user = query.getSingleResult();
_

次のような例外が表示されます。

_org.postgresql.util.PSQLException: ERROR: column user0_.id does not exist
_

Bashシェルのデータベースは次のようになります。

database

Hibernateはクラス属性をテーブル列にどのようにマップしますか? @Column(name="username")のみに基づいて一致しますか、またはデータ型や一意/自動インクリメントなどの制約に基づいて一致しようとしますか?

21
swdon

解決

PostgreSQLでは、スキーマの名前を次のように指定する必要があります。

@Table(name="table_name", schema = "myapp")
                          ^^^^^^^^^^^^^^^^

長い話

このエラーが発生しました:

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

PostgreSQLでデータベースを作成すると、publicという名前のデフォルトスキーマが作成されるため、Entityに名前を指定しないと、Hibernateはpublicスキーマで自動的に確認します。


良い習慣

  1. PostgreSQLでは、databaseschematables、またはcolumnsの名前に大文字を使用しないでください。それ以外の場合は、引用符でこの名前をエスケープする必要があり、これにより構文エラーが発生する可能性があるため、代わりに次を使用できます。
@Table(name="table_name", schema = "schame_name")
             ^^^^^^^^^^             ^^^^^^^^^^^
  1. キーワード[〜#〜] user [〜#〜]PostgreSQLで予約済みキーワードです 見てください
+----------+-----------+----------+-----------+---------+
| Key Word |PostgreSQL |SQL:2003  | SQL:1999  | SQL-92  |
+----------+-----------+----------+-----------+---------+
|  ....        ....       ....       ....       ....    |
+----------+-----------+----------+-----------+---------+
| USER     |  reserved |reserved  | reserved  | reserved|
+----------+-----------+----------+-----------+---------+
  1. DtoEntityの違いについては、たとえばUserEntityのように、エンティティの名前の最後にエンティティを使用することをお勧めします
32
YCF_L

この例外が発生する場合は、postgresで、エンティティクラスを作成するたびに、次のように、エンティティクラスを正しいスキーマ(テーブルが存在する場所)に関連付けてください。

@Entity
@Table(name = "user", schema = "users_details")
public class User implements Serializable{

    @Column(name = "id")
    Long id;    //long is not recommended

   // Other data
}

@YCF_Lが言ったように、テーブル名または列名で大文字を使用しないでくださいを指定しないと、この例外が発生します。

この規則は、エンティティクラスのテーブルを自動生成する必要があるシナリオ、またはその逆の場合に重要になります。

0
Vikash Kumar