<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    隨筆-42  評(píng)論-578  文章-1  trackbacks-0
    近來(lái),在做的一個(gè)NewsMS項(xiàng)目中,需要用到多對(duì)多關(guān)聯(lián)映射,以下是項(xiàng)目中用到的兩個(gè)實(shí)體類:用戶類User和角色類Role,它們之間是多對(duì)多的關(guān)系。
    //用戶表
    @Entity
    @Table(name
    ="rong_user")
    public class User{

        
    //省略其它內(nèi)容

        
    private Set<Role> roles = new LinkedHashSet<Role>();    //角色集合
        
        @ManyToMany(cascade 
    = {CascadeType.PERSIST, CascadeType.MERGE})
        @JoinTable(name 
    = "rong_user_role", joinColumns = { @JoinColumn(name ="user_id" )}, inverseJoinColumns = { @JoinColumn(name = "role_id") })
        @OrderBy(
    "id")
        
    public Set<Role> getRoles() {
            
    return roles;
        }

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

    }

    //角色表
    @Entity
    @Table(name
    ="rong_role")
    public class Role{
        
        
    //省略其它內(nèi)容

        
    private Set<User> user = new LinkedHashSet<User>();        //用戶集合

        @ManyToMany(cascade 
    = {CascadeType.PERSIST, CascadeType.MERGE}, mappedBy = "roles", fetch = FetchType.LAZY)
        
    public Set<User> getUser() {
            
    return user;
        }

        
    public void setUser(Set<User> user) {
            
    this.user = user;
        }

    }


             這兩個(gè)生成數(shù)據(jù)庫(kù)中的三個(gè)表,分別是rong_user, rong_role和一個(gè)中間表rong_user_role。
             Hibernate和JPA控制關(guān)聯(lián)關(guān)系的,只能是一方,不能雙方控制的,上面的程序中,我通過(guò)在Role類中設(shè)置mappedBy="roles"來(lái)設(shè)置由User來(lái)控制關(guān)系,
             這樣,問(wèn)題就出現(xiàn)了:當(dāng)我在要?jiǎng)h除角色Role時(shí),如果沒(méi)有用戶擁有這個(gè)角色的話,就能成功刪除;如果有用戶擁有這個(gè)角色的時(shí)候,就不能刪除,會(huì)拋以下異常:
    12:53:33,125  WARN JDBCExceptionReporter:100 - SQL Error: 1451, SQLState: 23000
    12:53:33,125 ERROR JDBCExceptionReporter:101 - Cannot delete or update a parent row: a foreign key constraint fails (`newsms/rong_user_role`, CONSTRAINT `FKF1698421A337A5FA` FOREIGN KEY (`role_id`) REFERENCES `rong_role` (`id`))
    12:53:33,171 ERROR AbstractFlushingEventListener:324 - Could not synchronize database state with session
    org.hibernate.exception.ConstraintViolationException: Could not execute JDBC batch update
    /****堆棧信息略****/
    Caused by: java.sql.BatchUpdateException: Cannot delete or update a parent row: a foreign key constraint fails (`newsms/rong_user_role`, CONSTRAINT `FKF1698421A337A5FA` FOREIGN KEY (`role_id`) REFERENCES `rong_role` (`id`))
    /******堆棧信息略*****/

          當(dāng)我設(shè)置成單向關(guān)系映射時(shí),即把Role類中,Set<User>信息去掉,這樣,也不能刪,原因也是說(shuō)有外鍵約束!怎么辦?
          苦惱了好幾天,最后,只能歸于Hibernate(JPA)的多對(duì)多關(guān)聯(lián)映射設(shè)計(jì)得有點(diǎn)不符實(shí)際!就像上面我說(shuō)的例子,有人選了某角色,就不能刪掉該角色。還有一種做法是,在Role類中:
    @ManyToMany(cascade = {CascadeType.PERSIST, CascadeType.MERGE,CascadeType.REMOVE}, mappedBy = "roles", fetch = FetchType.LAZY)
        
    public Set<User> getUser() {
            
    return user;
        }
            即加多一個(gè)“CascadeType.REMOVE”,這樣能把角色Role給刪掉了,但連擁有該角色的所有用戶User也被級(jí)聯(lián)刪掉了。這樣來(lái)看,某個(gè)用戶擁有許多角色,就因?yàn)槠渲杏羞@一個(gè)角色,就被級(jí)聯(lián)刪了整個(gè)自己,那不是很冤枉。這也不符合實(shí)際!
            個(gè)人認(rèn)為,Hibernate(JPA)在設(shè)置多對(duì)多關(guān)聯(lián)映射時(shí),應(yīng)該有做法能使得雙方都能控制關(guān)聯(lián)關(guān)系才好,才符合實(shí)際吧!但事實(shí)上,好像還沒(méi)有發(fā)現(xiàn)有Hibernate(JPA)這種能力!


    本文原創(chuàng),轉(zhuǎn)載請(qǐng)注明出處,謝謝!http://www.tkk7.com/rongxh7(心夢(mèng)帆影JavaEE技術(shù)博客)
        

    posted on 2009-06-08 13:33 心夢(mèng)帆影 閱讀(26943) 評(píng)論(15)  編輯  收藏 所屬分類: HibernateJPA

    評(píng)論:
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2009-06-08 18:18 | 虎嘯龍吟
    這樣就是符合實(shí)際啊:當(dāng)某個(gè)用戶擁有某個(gè)角色的時(shí)候,不應(yīng)該刪除該角色吧!  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2009-06-08 18:26 | 心夢(mèng)帆影
    @虎嘯龍吟
    用戶與角色是多對(duì)多的關(guān)系,如果系統(tǒng)不需要或個(gè)角色了,而因?yàn)橛杏脩舾@個(gè)角色有關(guān)聯(lián),而刪不了!那怎么對(duì)角色進(jìn)行管理?只能添加,修改,不能刪除?  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2009-06-08 19:20 | YangL
    LZ也在用SpringSide吧,呵呵  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2009-06-08 21:01 | 心夢(mèng)帆影
    @YangL
    被你看穿了,呵呵
    但我沒(méi)有直接把Springside當(dāng)組件用,而是學(xué)習(xí)它!
    有興趣交流一下不?我QQ:121040245,呵呵  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2009-06-08 21:18 | 小人物
    學(xué)習(xí)了!  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2009-06-09 20:44 | huliqing
    這不應(yīng)該是hibernate的不完美之處,數(shù)據(jù)庫(kù)的這個(gè)作法是正確的,這涉及到數(shù)據(jù)完整與安全性的問(wèn)題。我認(rèn)為你應(yīng)該先明確的處理掉相關(guān)的持有該角色的相關(guān)用戶的對(duì)于該角色的關(guān)系。也就是說(shuō)先刪除相關(guān)用戶對(duì)該角色的持有關(guān)系,再刪除該角色就沒(méi)有問(wèn)題。
    或者選擇不作外鍵約束,但是這樣就會(huì)對(duì)比較嚴(yán)格的系統(tǒng)造成數(shù)據(jù)冗余,不完整,還包括安全問(wèn)題。  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2009-06-11 00:33 | 虎嘯龍吟
    @YangL
    可以先去掉該用戶的角色,再刪除該角色啊  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2012-12-23 11:32 | lin
    雙方都用OneToMany就行了  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處[未登錄](méi) 2013-06-15 13:01 | James
    關(guān)聯(lián)關(guān)系不要雙方配置 只在主表配置  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處[未登錄](méi) 2013-06-15 13:03 | James
    @ManyToMany(cascade={CascadeType.PERSIST,CascadeType.MERGE})
    @JoinTable(name = "adgroup_ad", joinColumns = { @JoinColumn(name = "adgroup_id") }, inverseJoinColumns = { @JoinColumn(name = "ad_version_id") })
    這是我的項(xiàng)目的主表部分的注解配置 測(cè)試增加修改都可以 刪除也只刪除關(guān)聯(lián)關(guān)系  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處[未登錄](méi) 2013-06-15 13:10 | James
    汗 SORRY 發(fā)現(xiàn)我的問(wèn)題和你的不一樣的 我這里還是會(huì)出現(xiàn)你說(shuō)的這種情況 SORRY 看來(lái)它還真是設(shè)計(jì)有點(diǎn)不合理的  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2013-09-02 10:49 | phevose
    這在業(yè)務(wù)邏輯上是完全合理的,正在被使用的角色是不應(yīng)該被刪除的,如果刪除那么應(yīng)該做級(jí)聯(lián)刪除,對(duì)應(yīng)的用戶也應(yīng)該一并刪除,或者應(yīng)該先解除關(guān)聯(lián)關(guān)系后再刪除該角色。  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2014-11-14 16:16 | 雪妮星跡
    樓主想要的級(jí)聯(lián)功能,可以使用數(shù)據(jù)庫(kù)的外鍵約束控制。  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2015-01-27 15:20 | lp
    @心夢(mèng)帆影
    可以不建立外鍵關(guān)聯(lián),通過(guò)應(yīng)用控制數(shù)據(jù)的完整性。  回復(fù)  更多評(píng)論
      
    # re: Hibernate(JPA)多對(duì)多(ManyToMany)關(guān)聯(lián)映射不完美之處 2016-04-07 15:10 | coolcjava
    只有兩個(gè)實(shí)體類都配置了joinColumns和inverseJoinColumns屬性,并且位置互相調(diào)換,就可以使用雙向維護(hù)  回復(fù)  更多評(píng)論
      
    主站蜘蛛池模板: a毛片在线看片免费| 黄色免费在线观看网址| 亚洲精品免费在线| 激情内射亚洲一区二区三区| 亚洲AV无码精品色午夜在线观看| 久久亚洲国产中v天仙www| 国产AV无码专区亚洲AVJULIA| 亚洲精品国精品久久99热一| 国产亚洲一区二区手机在线观看 | 久久国产免费一区二区三区| 免费国产成人18在线观看| 国产精品视频白浆免费视频| 99热免费在线观看| 国产精品视频免费| 蜜桃视频在线观看免费网址入口| 毛色毛片免费观看| 国产一级一片免费播放| 亚洲日本中文字幕一区二区三区| 亚洲一区二区三区香蕉| 亚洲AV无码日韩AV无码导航 | 亚洲国产av一区二区三区| 4338×亚洲全国最大色成网站| 伊人久久大香线蕉亚洲| 精品无码一区二区三区亚洲桃色| 亚洲一级毛片免费观看| 亚洲av无码专区在线观看下载| 美女黄网站人色视频免费| 99精品免费视品| 5555在线播放免费播放| 在线免费观看污网站| 亚洲区不卡顿区在线观看| 亚洲av永久无码精品古装片| 亚洲春黄在线观看| 无码一区二区三区亚洲人妻| 中国一级特黄的片子免费 | 最近中文字幕大全中文字幕免费| 国产人在线成免费视频| 免费大香伊蕉在人线国产| 国产亚洲综合网曝门系列| 亚洲一卡2卡4卡5卡6卡残暴在线| 立即播放免费毛片一级|