精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
|
|
---|---|
作者 | 正文 |
发表时间:2012-11-28
业务上的很简单,说白了,是一个人力资源系统; 使用人数大约在2000人左右。 数据关系分为部门,用户,工作组,角色,资源(权限过滤用的)等。当然还有一些其它,不细说; 现在用hibernate 的二级缓存。但发现有不少的问题,其中最主要的问题就是脏数据的问题,可能是我用得不好,不过以下这个问题要如何处理? 资源中,分类别,类别分组,组中挂资源,如果我进行以下操作,会出现脏数据: 1. 通过类别,组,加载资源 2. 删除资源(直接删除,没通过类别中的set<组>,组中的set<资源>删除) 3. 再重复第一步操作 这时候就会出现脏数据,因为数据库中是已经删掉了,但缓存中类别,组中的set的数据还在! 上面只是提出一个具体问题进行讨论,这里主要不是要向大家提问这个具体问题,而是想让大家发表对hibernate的二级缓存的看法,调查一下用hibernate二级缓存(包括查询缓存)的人多不多,还有最好是怎么去用,怎么去设计?也请各位指点一下,谢谢~ 声明:ITeye文章版权属于作者,受法律保护。没有作者书面许可不得转载。
推荐链接
|
|
返回顶楼 | |
发表时间:2012-11-28
最后修改:2012-11-28
我认为主要是删除资源没有同步cache
(1)关键:因为你的业务涉及read-write操作,所以要保证read-write在一个transactional的操作。 (2)以为hibernate的secondary cache需要第三方cache 组件support,所以你要确定你用的是哪种cache,比如EHCache OSCache等 (3)如果想要保证数据一致性,需要Cache Component支持事务性缓存策略实现。目前大都流行的框架都是支持读写事物,参考这个属性配置:hibernate.transaction.manager_lookup_class,它指定了一个事务管理的类,用来保证数据一致性。 (4)上一点只能保证单机部署,如果集群的话,需要考虑加锁的方式 |
|
返回顶楼 | |
发表时间:2012-11-28
cectsky 写道 我认为主要是删除资源没有同步cache
(1)关键:因为你的业务涉及read-write操作,所以要保证read-write在一个transactional的操作。 (2)以为hibernate的secondary cache需要第三方cache 组件support,所以你要确定你用的是哪种cache,比如EHCache OSCache等 (3)如果想要保证数据一致性,需要Cache Component支持事务性缓存策略实现。目前大都流行的框架都是支持读写事物,参考这个属性配置:hibernate.transaction.manager_lookup_class,它指定了一个事务管理的类,用来保证数据一致性。 (4)上一点只能保证单机部署,如果集群的话,需要考虑加锁的方式 cectsky 你好,谢谢回复: 1. 目前可以保证在一个事务中read-write操作,但二级缓存是跨transaction的,比如,现在直接删除一个子实体(不通过根实体删除),那么根实体中的set缓存区是不知道该子实体被删除的,所以,下个transaction被删除的时候依然会查出这个子实体 2. 目前采用ehcache 4. 如果只考虑单机部署的话~ 请问你们现在用二级缓存都是怎么用的呢?用得多吗?有遇到什么问题没? |
|
返回顶楼 | |
发表时间:2012-11-28
Hibernate 的cache 实现都对cache flush 的机制做了保证的, 这个本身不是问题。
你这个脏数据的问题是否和web app 集群下发生的? |
|
返回顶楼 | |
发表时间:2012-11-28
一江春水邀明月 写道 Hibernate 的cache 实现都对cache flush 的机制做了保证的, 这个本身不是问题。 你这个脏数据的问题是否和web app 集群下发生的? 您好,可否介绍一下hibernate cache对cache flush 的机制的保证吗? 不是web app集群环境下,目前应用还比较简单~没有集群,而且数据库也没有多个应用使用。 这样说吧,如 @Cache(region="Group") public class Group{ @cache(region="group.items") private Set<Item> items; } @Cache(region="item") public class Item{ //...... } public class ItemService{ public void remove(Item item){ dao.remove(item);// 这里的操作,不有通知group,此时再通过group拿items的时候,被删除的数据的信息还是存在的(估计也只保存ID之类,未知,这时再通过该ID到数据库拿,就出问题了~(对象找不到 )) } } 以上代码即兴写,忽略语法问题,呵呵~ |
|
返回顶楼 | |
发表时间:2012-11-28
To be honest, 很久以前用过hibernate,没用过secondary cache
1.首先对于你这种场景,放在二级cache中是不明智的(放在二级cache中是那些经常查询,很少修改,能够保证在同级别下的更新的数据) 2.可以在每次修改子实体的时候,进行对根实体通知,进行cache同步操作。此时就涉及一个read-write的同步机制,EHCache已经支持。这可能会造成一些性能损耗,当然你的web app并发2000,还算能接受吧。 3.可以对修改子实体的方法注入操作,也就是AOP,简便并且松耦合 |
|
返回顶楼 | |
发表时间:2012-11-28
cectsky 写道 To be honest, 很久以前用过hibernate,没用过secondary cache 1.首先对于你这种场景,放在二级cache中是不明智的(放在二级cache中是那些经常查询,很少修改,能够保证在同级别下的更新的数据) 2.可以在每次修改子实体的时候,进行对根实体通知,进行cache同步操作。此时就涉及一个read-write的同步机制,EHCache已经支持。这可能会造成一些性能损耗,当然你的web app并发2000,还算能接受吧。 3.可以对修改子实体的方法注入操作,也就是AOP,简便并且松耦合 to cectsky HI,您好, 其实现在的问题是,我最想实现的是hibernate二级缓存的可拔插 1. 是的,二级缓存的数据很少修改,目前我放到二级缓存的数据也是很少修改的,但这限于上线后运行一段时间,客户数据完善后。 2、3. 因为如果要手动更新,即使是用aop,但也要有这些同步的代码,而且如果有多对parent-child的话,那么就要有多个这样的代码,想问下大家做项目的时候也需要做这样的事情吗? cectsky,你现在主要是做哪方面的项目,不知道是否方便介绍下你们的设计呢?谢谢~ |
|
返回顶楼 | |
发表时间:2012-11-29
cnblsp2 写道 cectsky 写道 To be honest, 很久以前用过hibernate,没用过secondary cache
1.首先对于你这种场景,放在二级cache中是不明智的(放在二级cache中是那些经常查询,很少修改,能够保证在同级别下的更新的数据) 2.可以在每次修改子实体的时候,进行对根实体通知,进行cache同步操作。此时就涉及一个read-write的同步机制,EHCache已经支持。这可能会造成一些性能损耗,当然你的web app并发2000,还算能接受吧。 3.可以对修改子实体的方法注入操作,也就是AOP,简便并且松耦合 to cectsky HI,您好, 其实现在的问题是,我最想实现的是hibernate二级缓存的可拔插 1. 是的,二级缓存的数据很少修改,目前我放到二级缓存的数据也是很少修改的,但这限于上线后运行一段时间,客户数据完善后。 2、3. 因为如果要手动更新,即使是用aop,但也要有这些同步的代码,而且如果有多对parent-child的话,那么就要有多个这样的代码,想问下大家做项目的时候也需要做这样的事情吗? cectsky,你现在主要是做哪方面的项目,不知道是否方便介绍下你们的设计呢?谢谢~ 目前做网管系统,用不到hibernate, 有好多知识都忘记了。 如果这个hibernate或EHCache没有内置的API解决,加code是不可避免了 |
|
返回顶楼 | |
发表时间:2012-11-29
很明显,你们代码操作的思想还是对表而不是对对象。
items是Group的属性。你删除item,应该操作group而不是单独去操作item。 |
|
返回顶楼 | |
发表时间:2012-11-29
魔力猫咪 写道 很明显,你们代码操作的思想还是对表而不是对对象。 items是Group的属性。你删除item,应该操作group而不是单独去操作item。 您好,非常感谢您的回复: 的确我之前开发的时候,都是根据表的,应该说,以前的Hibernate的使用也是简单使用,真正面向对象地去使用很少,不过按照您的说法的话,是不是操作item的时候都要通过group去操作呢? 如果有三层或者多层,如: GroupParent(Set<Group>), Group(Set<Items>) Item 那么删除item的时候,难道要先拿到parent.groups.get(x).items.remove(item) 吗? 呵呵,按照我对面向对象的理解,操作item的话,那应该是出现在item相应的模块中吧? 不对之处,还望指正,谢谢~ |
|
返回顶楼 | |