自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(20)
  • 收藏
  • 关注

原创 一根线程把12核盒子的一格吃满,栈顶却连着三把没动过

晚高峰刚冒头,企微就开始响。 一台机器 CPU 压到 95% 下不来,接口跟着一起变慢。 GC 我看过,干净;SQL 那条链路也走了一遍,不慢。 两边都排除掉,只能自己上机器。 盒子底细:corretto 1.8.0_412,12 核。 线程名这事我在〈线程池被说不该用 Executors,自己 new 这几个参数怎么填〉里吐槽过: jstack 拉出来全是 pool-3-thread-41 这种,分不清谁在跑哪块业务。 这次逮到一根,不过栽的这根跟线程池没关系。 三步顺序不能颠倒 我固定走三步,先后顺序有

2026-11-08 19:16:04 13

原创 容器起来就溜、docker ps 找不到,便签上这几个动作我按顺手程度排的

在 CentOS 7.9、Docker 20.10.7 上折腾, docker run -d 一执行完,人就跟蒸发了一样, docker ps 翻半天也没个影子。 这种时候我就摸出那张纸条,一条只管一个动作,顺序是自己平时敲出来的,不是按教程来的。 有个收尾动作我习惯搁前头说: docker ps 敲完别急着收手,等个十几秒再回头补一查。 有些服务刚起来那五秒 Up 得稳稳当当,非得等外部那次连接没接上才肯倒。 先弄明白到底是谁在退、抛回来的那个数是多少,跳过这步基本靠蒙: $ docker ps -a -

2026-11-08 13:11:32 45

原创 封顶内存后 fork 为何仍被拒:一次 RDB 写失败排查

封顶那台机器叫 cart-cache,跑的是 CentOS 7.9 加 Redis 5.0.14,配置我原以为没动过。 三天后写缓存的接口成片报错,凑近一看,错的还不是同一路。 redis 127.0.0.1:6379> SET order:cache:20001 v (error) MISCONF Redis is configured to save RDB snapshots, but it is currently not able to persist on disk. 消息后头还缀着围绕

2026-11-06 13:59:46 142

原创 内核先动手的那晚,我盯着 maxmemory 的 0 发愣

节点 k8s-redis-07 是台 4 核 8G 的机器,CentOS 7.9, redis 和 billing-job 那个 Java 进程挤在同一块内存里过日子。 晚高峰刚过,应用侧成片甩回 Lettuce 连不上的报错,我登上去一看,redis-server 已经没了。 不用猜,内核日志尾巴上两行写得明明白白: [18743256.842011] Out of memory: Kill process 21874 (redis-server) score 823 or sacrifice child

2026-11-03 19:59:29 153

原创 那条 412876 微秒的慢日志,和一根独木桥

慢日志翻出来的第一眼,我把它读成了四百多秒。 序号 132,时间戳 1791023417,耗时 412876,命令是 keys user:* ——四个字段摆在那里,我盯着第三个数手心发潮。 单位是微秒,实际折出来四百毫秒出头,扫一百二十万键落这个量级并不离谱,但当时的判断已经偏了。 事情的起因不在我手上,是同事为凑当天活跃用户数,顺手敲了一行。 redis-cli KEYS "user:*" | wc -l 几万键的本地库跑它没感觉,键量上去之后私人习惯就变成公共事故。 这台机器的底账:CentOS 7.9

2026-11-03 14:20:17 89

原创 服务名填进连接串没用,默认 bridge 的 DNS 我查了一下午

库就在隔壁容器,应用却连不上,报错清一色 connection refused。 我一度以为是防火墙或者账号权限,在 Spring 那边来回翻配置。 先说下现场:单台测试机 CentOS 7.9,Docker 20.10.7,两具容器都跑在默认 bridge 上。 库容器叫 shop-db,应用容器叫 trade-svc,连接串里写的是裸 IP 172.17.0.3。 那个 IP 是 docker 随手派的 地址不是谁配的,是 docker0 网段自己分的。 $ docker inspect --forma

2026-10-30 13:04:24 4

原创 一个 \r 卡在 shebang 里,容器怎么都起不来

同事把 pay-svc:1.1 的镜像推给我时,交代了一句“直接 run 就行”,可我这边的测试机压根没跑起来。 机器是老面孔,Docker 20.10.7 搭 CentOS 7.9,上一版的服务就赖在这台机器上。 启动方式换了新花样,/app/start.sh 顶掉了原来的 java -jar app.jar,据说是想把 JVM 参数归拢到一处。 我先把旧容器清了,docker rm 把占着的 pay-svc 名字腾出来,然后 run 发下去,屏幕甩回来这段: $ docker run -d --name

2026-10-29 17:06:47 139

原创 那条 find 命令为什么没删掉我凌晨留下的日志

我手头有个定时清理的活,扫的是 /var/log 和 /data/bak 两个目录下的陈年 .log,脚本内容就一行: find /var/log /data/bak -name "*.log" -mtime +7 -delete 按我当初的理解,-mtime +7 的意思是「七天以前的东西,留不住了」,那三十天的历史日志自然该被清干净,只保留最近这一周。 事后翻目录核对,old_gc.log 还稳稳躺在原地。 这个文件我有印象,就是上次磁盘告警那会儿,上午临时挪出来备着的那份。 +7 的门槛比我以为的高一

2026-10-29 13:15:48 108

原创 那条 SQL 扫了十万行,只为了给我二十行

订单列表的翻页问题,最早是客服那边转过来的。 她说客户翻到后面几页就开始等,越往后等得越久。我让她把出问题的那条语句原样发我,收到的是这么一句: select * from t_order where status = 1 and create_time >= '2025-06-01' order by create_time desc limit 99980, 20; 第 5000 页,每页 20 条,所以 limit 后面那个大数是 4999 乘以 20。 客服那边掐了表,6.2 秒才回来。 先把

2026-10-27 15:22:17 123

原创 -v 左侧那个不存在的文件,让 Docker 悄悄建了个目录

反代这一层我拿 nginx 挡在 shop-gw 前面,配置想直接复用宿主机上的那份,于是整包盖进容器。 盖完容器起来就退。 docker logs 刷得飞快,之前存的那几个翻页参数这回派上用场。 捞出来的就一行: 2026-09-22 10:07:31 [emerg] 1#1: read() "/etc/nginx/nginx.conf" failed (21: Is a directory) nginx 去读文件,摸回来的却是一枚目录。 环境还是老配对:CentOS 7.9,Docker 20.10.7

2026-10-25 18:03:34 208

原创 一个残留容器让我多花了半小时:8080 被占的两种可能

先把答案放这儿:占着 8080 的,是我上一轮没清干净的旧容器。 上一篇写的是〈docker exec 进不去:OCI runtime exec failed〉,这次 order-api 换了个自带 shell 的基础镜像,重新拉起来跑。 环境没变:CentOS 7.9,Docker 20.10.7。 命令刚敲下去,报错就糊了我一脸: $ docker run -d --name order-api -p 8080:8080 order-api:1.0 docker: Error response from

2026-10-24 12:12:02 128

原创 第6层那行COPY挪了个位置,构建从九分十二秒掉到七分钟出头

欠账是〈docker build 跑了十分钟,死在第 7 层 RUN〉那篇结尾留下的。 CI 上我一天要出七八版镜像,每版九分十二秒打底,可我手上的改动小得可怜——admin 里改一行拼写而已。 机器环境是老搭配:CentOS 7.9 加 Docker 20.10.7。 第一次撞见这怪事时,屏幕上是这么一段: Step 5/13 : COPY admin/package.json admin/package-lock.json ./ ---> Using cache ---> 7a02c5e8f

2026-10-23 14:14:23 179

原创 队列堆到八,%util 逼近 98,sda 到顶了

上篇〈进程 CPU 98% 接口却慢成狗,vmstat 的 wa 列翻了案〉留了个尾巴: 哪块盘在忙,没落实。 睡了一觉再登上去,还是上午十点,wa 纹丝没动——38.4 和 38.7,b 列钉在 3。 zhang 那个 java 进程照旧没消停,pid 还是 1987。 他讲昨夜回家远程瞄了一眼,既然没崩,就搁着没管。 老环境,CentOS 7.9,4 核、8G 内存, 我线上从没正经伺候过它。 读写的总量 vmstat 能给,设备名它不带。 要报出盘名对账,只能把 iostat 请出来。 头一屏的数字掺

2026-10-16 14:21:59 80

原创 90 秒没动静,nginx 是被 systemd 掐的

同样的 web01,系统没换,CentOS 7.9。 头天填到 98% 的盘,早上腾完空退回 66%。 跟着 restart 一把 nginx,它当场 failed 给我看。 屏幕上能读出来的拢共三行, 末行缀着 status=1/FAILURE,余下的尽是黑话。 群里还有人候着那句"哪一步栽的"的答案, 这三行拿不出一个字的答案。 状态三行,只是块门牌 # systemctl status nginx ● nginx.service - nginx - high performance web serve

2026-10-13 15:01:31 170

原创 空数组传下去,in 后面被拼出一对空括号

那串 MySQL 报错其实帮不上忙,抄它没意义。 java.sql.SQLSyntaxErrorException: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ... near 往后那截跟着 SQL 变,每条都不重样,我没抄。 真正给方向的是 MyBatis 打出来的语句: selec

2026-10-11 15:44:25 71

原创 一行 if 惹出 NPE:equals 改由常量那头发起

包装类型能不能直接跟数字比,我以前是不带犹豫的。 线上那天零星冒了七八次 NPE,把这个习惯打掉了。 扒到栈顶,回回都是同一处: Integer status = order.getStatus(); if (status == 1) { // 走已支付 } 出事的正是那句判断。 上游那个服务递给过来的对象里,负责状态的字段从没被塞过值, 走一遍反序列化,落到手里自然成了 null。 为了看清单个动作,我把它剪成能独立跑的类,corretto 1.8.0_412: static Integer status

2026-10-11 10:53:44 136

原创 带 T 的时间戳解析报错,@JsonFormat 收场

对接那边推过来的回调报文里,createTime 这栏的值是这样: {"createTime":"2025-02-25T14:23:58-08:00"} 我接数据的对象把它落进一个本地时间字段,反序列化当场就抛了: com.fasterxml.jackson.databind.exc.InvalidFormatException: Cannot deserialize value of type java.time.LocalDateTime from String 说实话这层壳是 Jackson 披的,根

2026-10-10 16:36:52 220

原创 @Value 只认容器,new 出来的对象拿不到值

这个坑是在导数据的时候撞上的。 测试环境的订单表要灌数,一万两千条,走到八千多行,程序没声了。 日志里刨出来这么一行: java.lang.NullPointerException at 往后的帧全是业务包名,我就不抄了。 栈指到的代码长这样: String path = tmpPath + "/upload"; tmpPath 这个字段头顶是有注解的: @Value("${file.tmp.path}") private String tmpPath; 说实话,我当时头一个念头就是配置写漏了。 翻出 ap

2026-10-10 15:49:37 160

原创 Java 线程池生产实践指南:原理、代码与线上事故复盘

问题背景 在并发编程中,多线程同时访问共享变量往往会导致数据竞争和并发问题。但并非所有变量都会成为共享变量。比如下面这个计算斐波那契数列的方法,当多个线程同时调用时,方法内部的数组 r 是否存在并发风险? int[] fibonacci(int n) { // 创建结果数组 int[] r = new int[n]; // 初始化第一、第二个数 r[0] = r[1] = 1; // ① // 计算2..n for(int i = 2; i < n; i++) { r[i] = r[i-2] + r[

2026-10-02 17:53:51 173

原创 局部变量为何天生安全:从调用栈看 Java 并发编程的线程封闭

问题背景 在并发编程中,多线程同时访问共享变量往往会导致数据竞争和并发问题。但并非所有变量都会成为共享变量。比如下面这个计算斐波那契数列的方法,当多个线程同时调用时,方法内部的数组 r 是否存在并发风险? int[] fibonacci(int n) { // 创建结果数组 int[] r = new int[n]; // 初始化第一、第二个数 r[0] = r[1] = 1; // ① // 计算2..n for(int i = 2; i < n; i++) { r[i] = r[i-2] + r[

2026-10-02 17:51:43 346

空空如也

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除