首先我们想让用户冻结之后就不执行Action , 那么被冻结之前用户登录了,进行操作的时候,想实时检查用户状态是否是冻结状态,那么就想到用过滤器每次都读取数据库用户标志。可以这样就需要每次都读取数据库,性能太差。此观点第一个被抛弃。
既然不查数据库那么查什么呢?我们想到了查文件,每次把冻结的用户都放到一个文件里,application中记录此文件的上次更新时间,过滤器里判断此文件的lastedmodifiedtime,如果比application中的更新,就访问文件察看userid是否在此冻结文件中。如果在,就跳转至登陆页,并在文件中删除此userid。登陆页,冻结不让登陆,显示错误信息,并删除文件中的userid记录.缺点是必须要IO读写,性能不好,第二被冻结用户登录时要删除文件,是否删除过,不好判断。这个方法稍好,但是不是最好。
第三个方法,在application范围放一个HashMap , 后台冻结用户时存放此userid到hashMap , 然后过滤器察看userid是否在此HashMap中。 若在则跳到 登陆页面, 并从HashMap删除此userid 。登陆时,显示错误信息,并从并从HashMap删除此userid .这个方法把数据放到内存,缺点就是占用内存,好处就是比访问文件的性能要好。并且只要用户操作就会从内存中删除此userid数据,另外用户冻结的数据本身也不多,这样内存占用实际不会太大。
所以综合考虑,第三种方法比较好。
另外还有一个方法,就是在后台设置冻结标志之后,获得此用户的session,并将这个session设置为invalidate().或者removeAttribute("UserInfo") .首先前台需要SessionBindListener,并把登陆信息UserInfo,BmanInfo对象实现SessionBindListener接口,并实现加入session,从session中删除所使用的方法。于是在UserInfo加入session时调用的方法里,把此用户userid , 对应的session放到HashMap中对应起来,考虑到一个用户userid可以对应多个session,所以需要一个list保存所有此userid对应的session饮用,并把list放到HashMap中的value来对应起来。 如此, 后台冻结时,查找此Hash , key= 被冻结的userid , 再把对应的session饮用list 拿来, 逐个removeAttribute("UserInfo");
这样,因为session在HashMap总本来就是饮用,占用内存的只有session实例本身,所以内存消耗并不是问题。这是一个实时获得用户登陆后的session,并删除其中注册信息的好办法。