1

私のJava spring webappには関係があります.1つのアカウントは多くのグループを持つことができ、1つのグループは1つのアカウントしか持つことができません.

グループ エンティティ:

@Entity
@Table(name = "group")
@Inheritance(strategy = InheritanceType.JOINED)
public class Group {

@Id
@GeneratedValue(generator = "group_id", strategy = GenerationType.SEQUENCE)
@SequenceGenerator(name = "group_id", sequenceName = "group_group_id_seq", allocationSize = 1)
@Column(name = "group_id")
private Long id;

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

@ManyToOne(targetEntity = Account.class, fetch = FetchType.LAZY)
@JoinColumn(name = "account_id")
private Account account;

@Basic
@NotBlank
@Column(name = "all")
private boolean all;

@ManyToMany(targetEntity = Word.class, fetch = FetchType.LAZY)
@JoinTable(name = "group_word", joinColumns = {@JoinColumn(name="group_id")}, inverseJoinColumns = {@JoinColumn(name="word_id")})
private List<Word> words;

getters/setters...

アカウント エンティティ:

@Entity
@JsonIgnoreProperties(ignoreUnknown = true)
@Table(name = "account")
@Inheritance(strategy = InheritanceType.JOINED)
public class Account  extends User implements UserDetails {

@Id
@GeneratedValue(generator = "account_id", strategy = GenerationType.SEQUENCE)
@SequenceGenerator(name = "account_id", sequenceName = "account_account_id_seq", allocationSize = 1)
@Column(name = "account_id")
private Long accountId;

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

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

@Transient
private String repeatedPassword;

@DateTimeFormat(iso = ISO.DATE_TIME)
@Column(name = "registration_date")
Date registrationDate = Calendar.getInstance().getTime();

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

@ManyToMany(targetEntity = Role.class, fetch = FetchType.LAZY)
@JoinTable(name = "account_role", joinColumns = {@JoinColumn(name="account_id")}, inverseJoinColumns = {@JoinColumn(name="role_id")})
private List<Role> roles;

public List<Role> getRoles() {
    return roles;
}

public void setRoles(List<Role> roles) {
    this.roles = roles;
}

@OneToMany(mappedBy="account", fetch = FetchType.LAZY)
private List<Group> groups;

public List<Group> getGroups() {
    return groups;
}

public void setGroups(List<Group> groups) {
    this.groups = groups;

getters/setters...

このサービスメソッドを呼び出すと:

public List<Group> listUserGroups(String username) {
    try {
        Account foundAccount = accountDao.findUserByUsername(username);
        List<Group> userGroups = foundAccount.getGroups();
        userGroups.size();
        return userGroups;
    } catch (UserNotFoundException unf) {
        logger.error("User not found: " + username, unf.getMessage());
        return Collections.emptyList();
    }
}

オンラインでエラーが発生しました:

userGroups.size();

エラー:

00:27:27,528 DEBUG [org.hibernate.engine.StatefulPersistenceContext] - initializing non-lazy collections
00:27:27,528 DEBUG [org.hibernate.loader.Loader] - loading collection: [pl.net.grodek.snd.model.Account.groups#116]
00:27:27,528 DEBUG [org.hibernate.jdbc.AbstractBatcher] - about to open PreparedStatement (open PreparedStatements: 0, globally: 0)
00:27:27,528 DEBUG [org.hibernate.SQL] - select groups0_.account_account_id as account4_20_1_, groups0_.group_id as group1_1_, groups0_.group_id as group1_19_0_, groups0_.account_account_id as account4_19_0_, groups0_.all as all19_0_, groups0_.name as name19_0_ from group groups0_ where groups0_.account_account_id=?
00:27:27,544 DEBUG [org.hibernate.jdbc.AbstractBatcher] - about to close PreparedStatement (open PreparedStatements: 1, globally: 1)
00:27:27,544 DEBUG [org.hibernate.util.JDBCExceptionReporter] - could not initialize a collection: [pl.net.grodek.snd.model.Account.groups#116] [select groups0_.account_account_id as account4_20_1_, groups0_.group_id as group1_1_, groups0_.group_id as group1_19_0_, groups0_.account_account_id as account4_19_0_, groups0_.all as all19_0_, groups0_.name as name19_0_ from group groups0_ where groups0_.account_account_id=?]
org.postgresql.util.PSQLException: ERROR: syntax error near "group"
Position: 227
at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:2103)
at org.postgresql.core.v3.QueryExecutorImpl.processResults(QueryExecutorImpl.java:1836)
at org.postgresql.core.v3.QueryExecutorImpl.execute(QueryExecutorImpl.java:257)
at org.postgresql.jdbc2.AbstractJdbc2Statement.execute(AbstractJdbc2Statement.java:512)
at org.postgresql.jdbc2.AbstractJdbc2Statement.executeWithFlags(AbstractJdbc2Statement.java:388)
at org.postgresql.jdbc2.AbstractJdbc2Statement.executeQuery(AbstractJdbc2Statement.java:273)
at com.mchange.v2.c3p0.impl.NewProxyPreparedStatement.executeQuery(NewProxyPreparedStatement.java:76)
at org.hibernate.jdbc.AbstractBatcher.getResultSet(AbstractBatcher.java:208)
at org.hibernate.loader.Loader.getResultSet(Loader.java:1953)
at org.hibernate.loader.Loader.doQuery(Loader.java:802)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:274)
at org.hibernate.loader.Loader.loadCollection(Loader.java:2166)
at org.hibernate.loader.collection.CollectionLoader.initialize(CollectionLoader.java:62)
at org.hibernate.persister.collection.AbstractCollectionPersister.initialize(AbstractCollectionPersister.java:627)
at org.hibernate.event.def.DefaultInitializeCollectionEventListener.onInitializeCollection(DefaultInitializeCollectionEventListener.java:83)
at org.hibernate.impl.SessionImpl.initializeCollection(SessionImpl.java:1863)
at org.hibernate.collection.AbstractPersistentCollection.initialize(AbstractPersistentCollection.java:369)
at org.hibernate.collection.AbstractPersistentCollection.read(AbstractPersistentCollection.java:111)
at org.hibernate.collection.AbstractPersistentCollection.readSize(AbstractPersistentCollection.java:134)
at org.hibernate.collection.PersistentBag.size(PersistentBag.java:248)
at pl.net.grodek.snd.service.GroupServiceImpl.listUserGroups(GroupServiceImpl.java:47)
at pl.net.grodek.snd.service.GroupServiceImpl.listUserGroups(GroupServiceImpl.java:1)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at 

問題はjpaによって生成されたクエリにあると思います:

select groups0_.account_account_id as account4_20_1_, groups0_.group_id as group1_1_, groups0_.group_id as group1_19_0_, groups0_.account_account_id as account4_19_0_, groups0_.all as all19_0_, groups0_.name as name19_0_ from group groups0_ where groups0_.account_account_id=?

account_id と group_id が 2 倍になっています。しかし、なぜこれが起こっているのかという私の質問。私はアイデアを使い果たしたので、この問題を明確にしてください:(

編集:

ああ、DBテーブルを忘れていました:

CREATE TABLE "group"
(
    group_id bigserial NOT NULL,
    name character varying(150)[] NOT NULL,
    "all" boolean NOT NULL DEFAULT false,
    account_id bigint NOT NULL,
    CONSTRAINT group_id_pk PRIMARY KEY (group_id ),
    CONSTRAINT account_id_fk FOREIGN KEY (account_id)
    REFERENCES account (account_id) MATCH SIMPLE
    ON UPDATE NO ACTION ON DELETE NO ACTION
)

CREATE TABLE account
(
    account_id bigserial NOT NULL,
    username character varying(32),
    password character varying(64),
    email character varying(100),
    registration_date timestamp with time zone NOT NULL,
    word_for_today bigint,
    groups_on_page integer NOT NULL,
    CONSTRAINT account_pk PRIMARY KEY (account_id ),
    CONSTRAINT word_fk FOREIGN KEY (word_for_today)
  REFERENCES word (word_id) MATCH SIMPLE
  ON UPDATE NO ACTION ON DELETE NO ACTION,
    CONSTRAINT unique_mail UNIQUE (email ),
    CONSTRAINT unique_username UNIQUE (username )
)
4

2 に答える 2

0

私の経験では、問題は永続性コンテキストの範囲に関連しています。DAOを使用してエンティティを取得しているため、分離されたエンティティのプロパティにアクセスするふりをしている可能性があります。
話をすると、おそらく、accountDao.findUserByUsername()関数のスコープ内で、エンティティマネージャーを介してエンティティを取得するときに永続コンテキストを初期化/インスタンス化しますが、オブジェクトが戻った後、この関数のスコープは終了し、永続性のインスタンスになりますコンテキスト(entityManager)。つまり、Java SEアプリ環境では、entityManagerを静的な方法で参照して、すべてのアプリ実行スコープで存続させることはありません。

これとは別に、Hibernateはプロキシと連携します。これは、例に従って、すべての基本属性がロードされたオブジェクトAccountを取得しますが、それどころか、遅延関係(グループ、ロールなど)を取得することを意味します。getGroups()を呼び出すと、プロキシはグループのリストを照会しませんが、sizeを呼び出すと、プロキシはそれらを照会する必要があります。これと一般的なHibernateの動作をよりよく理解するために、第13章「 Hibernatein Action-Java Persistence with Hibernate(isbn 1-932394-88-5) 」のプロキシを理解することをお勧めします。

よろしく

于 2012-10-27T00:17:24.567 に答える
0

グループテーブル名をグループに変更したところ、機能しました。しかし、それがなぜなのか誰か教えてください。以前の関係では、私はそのような不思議な問題を抱えていませんでした. 私は正気を失っています。:(

誰かが私のコードに問題を見つけたのではないでしょうか? アカウントとグループの関係は適切に設定されていますか?

編集:@AdrianShumが言ったように、グループはSQLキーワードであるため、別の名前に変更したときにマッピングが機能しました

于 2012-10-28T23:25:40.363 に答える