当前位置: 代码网 > it编程>编程语言>Java > spring项目对某条单据进行加锁处理的方法

spring项目对某条单据进行加锁处理的方法

2024年11月25日 Java 我要评论
最近工作中有个对工单单据进行加锁/解锁处理,目的是为了防止多用户对同一条单据处理。以下是完整的前后端代码。前端js billlock.jslet orderlock = { orderlock:

最近工作中有个对工单单据进行加锁/解锁处理,目的是为了防止多用户对同一条单据处理。以下是完整的前后端代码。

前端js billlock.js

let orderlock = {
    orderlock:(viewmodel, id, billtype)=>{
        var url = '/orderlock/lock?domainkey='+viewmodel.getdomainkey();
        var proxy = cb.rest.dynamicproxy.create({
            ensure: {url: url, method: 'post'}
        });
        let data = {"id":id, "billtype": billtype, "ttl": 60*60*12}
        proxy.ensure(data, function (err, result) {
            if (err) {
                cb.utils.alert(err.message, 'error');
            } else {
                cb.utils.alert(result, 'info');
                if(viewmodel.originalviewmeta.cbillno && viewmodel.originalviewmeta.cbillno=="02924ed1"){
                    //维修领料页面进入
                    if(result.indexof('成功') <= 0){
                          viewmodel.biz.action().common.browse(viewmodel)
                          viewmodel.biz.action().common.setmode(viewmodel,"browse");  
                          
                    }
                }else{
                    if(result.indexof('成功') <= 0){
                        viewmodel.biz.action().common.browse(viewmodel)
                    }
                }
                
            }
        })
    },

    unorderlock:(viewmodel, id, billtype)=>{
        var url = '/orderlock/unlock?domainkey='+viewmodel.getdomainkey();
        var proxy = cb.rest.dynamicproxy.create({
            ensure: {url: url, method: 'post'}
        });
        var data = {"id":id, "billtype": billtype}
        proxy.ensure(data, function (err, result) {
            if (err) {
                cb.utils.alert(err.message, 'error');
            } else {
                cb.utils.alert(result, 'info');
            }
        })
    }
}
export default orderlock

后端java 代码

@restcontroller
@requestmapping("/orderlock")
@slf4j
public class orderlockcontroller extends basecontroller {
    @autowired
    private gmsredisutil gmsrredisutil;
    @autowired
    private userinfoservice userinfoservice;

    private string engine_no = "afterservice";

    /**
     * 加锁
     */
    @postmapping(value = "/lock")
    public void orderlock(@requestbody orderlockdto orderlockdto, httpservletresponse response) {
        try{
            string result;
            userextenddto userextenddto = userinfoservice.getuserextend();
            string nowdate = dateutil.dateformat(partcommonconstants.datetimeformatter, localdatetime.now());
            string key = engine_no + "_" + orderlockdto.getbilltype() + "_" + orderlockdto.getid();
            string message = "锁定人["+userextenddto.getstaffname()+"]锁定时间["+nowdate+"]";
            boolean flag = gmsrredisutil.trygetlock(key, message, orderlockdto.getttl(), 2);
            if(flag){
                result = "加锁成功!";
            }else{
                string lockvalue = gmsrredisutil.getobject(key);
                if(lockvalue.contains(userextenddto.getstaffname())){
                    result = "加锁成功!原锁定用户["+userextenddto.getstaffname()+"]进入单据!";
                }else{
                    result = "加锁失败!单据已被锁定,"+lockvalue;
                }
            }
            renderjson(response, resultmessage.data(result,false));
        }catch(exception e){
            renderjson(response, resultmessage.error(e.getmessage()));
            log.error("加锁失败:{}",e);
        }
    }

代码解析(以上代码大致步骤如下:)

1. 前端代码 参数是data,带有id,billtype,字符串ttl,时间变量 4个参数穿入后端。

2.后端接收参数,调用gmsrredisutil.trygetlock,这个方法是项目框架自己封装,原理是实现了redistemplate.opsforvalue().setifabsent方法

3.setifabsent方法简单介绍如下:

1.setifabsent(k var1, v var2);
如果key不存在则新增,key存在不做任何操作
redistemplate.opsforvalue().setifabsent("bbb", "好的");

2.setifabsent(k var1, v var2, long var3, timeunit var5)
如果key不存在则新增,同时设置过期时间,key存在不做任何操作。
redistemplate.opsforvalue().setifabsent("aaa", "好的", 1, timeunit.minutes);

3.setifabsent(k key, v value, duration timeout)
如果key不存在则新增,同时设置过期时间,key存在不做任何操作。
redistemplate.opsforvalue().setifabsent("bbb", "好的", duration.ofminutes(1));

4.如果单据第一次进入,key不存在,flag为true,直接返回给前端“加锁成功”,前端解析字符串中含有“成功,不设置页面为浏览态,仍为编辑态

本次加锁我调用的是第2个方法,这里的第一个参数key可见是单据id加一些特定字符。所以单据id就会被加锁,并设置加锁时间\

5 如果单据在已经加锁的情况下,仍有其他用户编辑此单据,则key重复,gmsrredisutil.trygetlock不做操作。

    gmsrredisutil.getobject(key)实际是调用redistemplate.opsforvalue().get(key) 方法,
    其中 get(object var1)  是获取指定的key对应的值。
    第一次加锁的message是用户信息,这里如果是不同用户登录的话,
    if(lockvalue.contains(userextenddto.getstaffname())) 就为false,返回给前端的信息是“加锁失败...”,
    前端获取字符串信息中没有加锁成功,会设置页面为浏览态,不能编辑。 到此,加锁完成!

总结 

到此这篇关于spring项目对某条单据进行加锁处理的文章就介绍到这了,更多相关spring某条单据加锁处理内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!

(0)

相关文章:

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论

验证码:
Copyright © 2017-2025  代码网 保留所有权利. 粤ICP备2024248653号
站长QQ:2386932994 | 联系邮箱:2386932994@qq.com