7

プロジェクトは、監査に Hibernate 3.5、Spring Webflow 2、および Hibernate Envers を使用します。Envers は hibernate.cfg.xml で構成されます。エンティティ 'ArticleGroup' と 'Article' の間に 1 対多の関係マッピングがあります。テーブル 'articles' には、テーブル 'article_groups' の ID への外部キー 'article_group_id' 参照があります。フロントエンドで記事を削除すると、Hibernate Envers が削除後イベントの制約違反例外をスローします。Envers を使用しない場合、削除操作は正常に機能します。2 つのエンティティは次のように定義されます。

    @Entity
    @Table(name="article_groups")
    @Audited
    public class ArticleGroup implements Serializable {

        @OneToMany(mappedBy="articleGroup", fetch = FetchType.EAGER, cascade = CascadeType.ALL)
        @OrderBy("id")
        private List<Article> articles;

        // other fields, getters and setters
    }

    @Entity 
    @Table(name="articles")
    @Audited
    public class Article implements Serializable {

        @ManyToOne
        @JoinColumn(name = "article_group_id")
        private ArticleGroup articleGroup;

        // other fields, getters, setters
    }

記事の削除は次のようにコード化されます。

    @Service("articleManager")
    public class ArticleManagerImpl implements ArticleManager {
            // inject dao
            @SuppressWarnings("unchecked")
            @Transactional(readOnly = false, propagation = Propagation.REQUIRES_NEW)
            public void deleteArticle(Article article, Object articles) {
            articleDao.delete(article);
            ((List<Article>)  ((OneSelectionTrackingListDataModel)articles).getWrappedData()).remove(article);
        }
    }

制約違反の例外:

Hibernate: delete from live.articles where id=?
Hibernate: select nextval ('hibernate_sequence')
Hibernate: insert into audit.REVINFO (REVTSTMP, REV) values (?, ?)
Hibernate: insert into audit.articles_AUD (REVTYPE, content, language, name, order_number, title, article_group_id, id, REV) values (?, ?, ?, ?, ?, ?, ?, ?, ?)
82828 [http-bio-8080-exec-2] DEBUG   org.springframework.orm.hibernate3.HibernateTransactionManager  - Initiating transaction rollback after commit exception
org.springframework.dao.DataIntegrityViolationException: Could not execute JDBC batch update; nested exception is org.hibernate.exception.ConstraintViolationException: Could not execute JDBC batch update
...
Caused by: java.sql.BatchUpdateException: Batch entry 0 insert into audit.articles_AUD (REVTYPE, content, language, name, order_number, title, article_group_id, id, REV) values ('2', NULL, NULL, NULL, NULL, NULL, NULL, '14', '17') was aborted.  Call getNextException to see the cause.
at org.postgresql.jdbc2.AbstractJdbc2Statement$BatchResultHandler.handleError(AbstractJdbc2Statement.java:2619)

ご覧のとおり、Envers がテーブル 'audit.articles_AUD' に挿入すると、article_group_id が null になり、制約違反が発生しました。誰もそれを修正する方法を知っていますか? どうもありがとうございました。

4

2 に答える 2

8

とった。構成ファイルで次のプロパティを設定します。

<prop key="org.hibernate.envers.store_data_at_delete">true</prop>

参照: http://docs.jboss.org/hibernate/envers/3.6/reference/en-US/html/configuration.html 表 3.1. Envers 設定プロパティ org.hibernate.envers.store_data_at_delete

于 2012-08-14T15:20:02.797 に答える
7

事後削除を行っていて、この操作中に削除するエントリまたはその他のエントリarticles_AUDに制約がある場合は、存在しない参照を使用してエントリを追加しようとします。articlesarticles_AUD

経験則として、改訂履歴をより適切に保持するために、参照を監査テーブルから除外します。監査テーブルに非監査テーブルに対する制約が含まれている場合、監査対象テーブルからエントリが削除されると、改訂履歴が壊れる可能性があります。


設定時に機能するソリューションを参照してくださいorg.hibernate.envers.store_data_at_delete

エンティティが削除されたときにエンティティ データをリビジョンに保存する必要があります ( id と他のすべてのプロパティを null として保存するだけではなく)。データは最後の 2 つ前のリビジョンに存在するため、これは通常は必要ありません。ただし、最後のリビジョンでアクセスする方が簡単で効率的である場合があります (その後、削除前にエンティティに含まれていたデータが 2 回保存されます)。

これは、Envers が を挿入しようとしているため、監査テーブルに の列があるNOT NULLため、制約違反であることがわかりnullます。監査テーブルで null を許可したい場合があります。

于 2012-08-14T14:12:53.850 に答える