同学们,帮我表弟检查下代码?

背景

表弟刚参加工作半年,就遇到批量调用接口返回错误的问题,刚好是周五遇到让周六加班弄完,由于周六本是休息,表弟积极性很低,于是直接选择短平快的方式先应付上去,并且运行了一下,说日志有空指针报错,但核对了一下数据库数据正常,暂时没发现问题。

为了保险起见让我帮忙给review一下

表弟说用大模型分析,老是回答说存在问题,让换一种写法,但大模型的那些问题像是在专业的胡说,不太放心自己临时写的代码。说经常看很多人喜欢review代码,就跑过来让我看一下,我看完后心中已有数。但为了表弟面前表现的更专业,故将其代码去除所有业务信息,做了最简化处理让各位也来点评一下,博采众长。

顺便吆喝一句,技术大厂跳板,前后端/测试,多地捞人机会,待遇还可以~感兴趣的冲冲!

表弟的代码(极简版)

表弟的环境是jdk8的单体服务,此接口调用频率很低,但一旦调用并发量很多。

import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

import java.util.Queue;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.locks.ReentrantLock;

@Slf4j
@RequestMapping("/queue")
@RestController
public class QueueController {

    //服务一旦宕机,队列消息就会全部丢失
    private static final Queue<String> queue = new LinkedBlockingQueue<>(10000);

    private static final ReentrantLock lock = new ReentrantLock();

    /**
     * 通过内存占用换取接口的并发能力,请求进来先进队列里排队,最后一个走的线程检查一下队列是否处理完成
     * @param id 模拟任务对象
     */
    @RequestMapping("/offer")
    public void test(@RequestParam("id")String id){
        if(id != null) {
            //模拟生产任务
            boolean offered = queue.offer(id);
            if(!offered){
                log.error("消息进入队列失败:{}",id);
            }
        }
        boolean isLock = lock.tryLock();
        if(isLock) {
            try {
                while (!queue.isEmpty()) {
                    String poll = queue.poll();
                    try {
                        if (poll != null) {
                            log.info("poll:{}", poll);
                            //模拟消费任务耗时,此处可以异步再优化性能
                            Thread.sleep(1000);
                        }
                    }catch (Exception e){
                        log.error("消费任务出错,poll:{},错误信息{}",poll,e.getMessage(),e);
                    }
                }
            } catch (Exception e) {
                log.error("消费任务出现异常,id:{},错误信息:{}",id,e.getMessage(),e);
            } finally {
                if(lock.isHeldByCurrentThread()){
                    lock.unlock();
                    //进入判断前可以加个10ms的睡眠时间,进一步降低高并发下总是此线程拿到锁的可能,从而不断递归导致栈溢出
                    if(!queue.isEmpty()){
                        log.info("清理队列剩余任务,size:{}",queue.size());
                        test(null);
                    }
                }
            }
        }
        log.info("生产者执行完成,size:{}",queue.size());
    }
}

——转载自:我的咖啡要加糖

#牛客创作赏金赛#
全部评论

相关推荐

07-12 22:24
已编辑
广东药科大学 后端
实在是不想学了&nbsp;写个文章吧.....希望大家消除对云智的误解&nbsp;无所谓内包外包&nbsp;这里做的业务跟总部都是一样的明白吗?都是一样的只是钱多钱少&nbsp;竞争力和内卷不大的问题以及有没有产出&nbsp;做的是不是杂活跟组有关系&nbsp;不跟内包有关系我来这里实习是有培养计划的&nbsp;我觉得导师和leader对我还是比较看重经常跟我聊进度&nbsp;让我不会的快点问&nbsp;快点学习和成长我一个月预答辩了两次&nbsp;入职一个月预答辩两次......我导师也是对我很好&nbsp;跟我说我做的工作如果说没有什么产出就不用写了意思就是那些CRUD的杂活对于我答辩没有什么用的就不用给我写了分给我需求&nbsp;让我的导师给我做方案设计一个方案设计争取做完去上线另外一个方案即使写不完也要明白业务逻辑到时候好答辩&nbsp;这样才有产出同时我的导师也跟我说他理解我广东人想回去的心情&nbsp;即使想回去也没有关系~而且部门的同事们都非常热情&nbsp;非常~很多入职一两年的大佬们每天都会跟我们一起吃饭其他的都是有点上年纪的就会自己吃饭盒&nbsp;应该是在家里做的&nbsp;然后放到盒子保温和同事一起吃饭真的是加快感情升温的方式&nbsp;有一个校招一年的已经混到负责人了然后我就每天问他问题&nbsp;能学到很多我的左右两边每天对我都是笑嘻嘻的&nbsp;很温暖的同事们说到业务&nbsp;部门还是比较核心的&nbsp;一个部门吃完饭回来都在加班表面说早10晚6&nbsp;实际上我左右两边后面都是九点左右走的&nbsp;我的导师走的早一点leader都是十点左右走
receive177...:实习可以,奔着转正还是别去外包了
点赞 评论 收藏
分享
不愿透露姓名的神秘牛友
07-07 13:46
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务