<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"><channel><title>元的手记</title><description>王元的中文个人博客，主要写 Java 工程实践、Spring Boot 问题排查和线上故障处理，也整理少量与技术写作相关的页面说明。</description><link>https://blog.jianghuzaijian.top/</link><item><title>告警太多但诊断仍慢，问题常出在“没按故障链分层”</title><link>https://blog.jianghuzaijian.top/blog/java/alert-storm-layering-why-too-many-alerts-but-slow-diagnosis-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/alert-storm-layering-why-too-many-alerts-but-slow-diagnosis-guide/</guid><description>真正拖慢值班的，往往不是告警不够，而是 20 多条红点挤在同一层里。把告警按起点层、放大层、结果层重新整理，并绑定到第一轮动作上，团队才会从“看见很多异常”变成“顺着一条故障链往下收”。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>一个接口的容量预算，QPS、超时、重试、线程池该怎么一起算？</title><link>https://blog.jianghuzaijian.top/blog/java/api-capacity-budget-qps-timeout-retry-thread-pool-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/api-capacity-budget-qps-timeout-retry-thread-pool-guide/</guid><description>接口容量预算最怕把 QPS、timeout、retry 和线程池拆开各算一遍。只有把入口流量、线程持有时间、重试放大量和下游退化场景放进同一张账里，预算结果才真的能指导限流、线程池 sizing 和高峰保护。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>接口响应慢怎么排查？后端 API 变慢与超时的定位步骤</title><link>https://blog.jianghuzaijian.top/blog/java/api-response-slow-troubleshooting-steps/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/api-response-slow-troubleshooting-steps/</guid><description>接口一慢，最浪费时间的做法就是所有人同时冲向不同技术点。先看影响范围，再分清是执行慢还是等待慢，排查链才不会一开始就散。</description><pubDate>Sun, 22 Mar 2026 00:00:00 GMT</pubDate></item><item><title>接口慢、CPU/GC/数据库都不高时，我是怎么沿一条隐藏等待链把问题找出来的？</title><link>https://blog.jianghuzaijian.top/blog/java/api-slow-but-cpu-gc-db-not-high-hidden-wait-points-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/api-slow-but-cpu-gc-db-not-high-hidden-wait-points-guide/</guid><description>一次下单接口变慢事故里，CPU、GC、数据库总量图都不吓人，真正拖时间的却是连接等待和事务里的额外停留。把时间线、traceId、pool pending、transaction age 和回退后的回落顺序对齐，隐藏卡点就不难找了。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Arthas 线上排障时，我最常先敲的不是 6 个命令，而是两条确认路径</title><link>https://blog.jianghuzaijian.top/blog/java/arthas-six-most-useful-commands-online-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/arthas-six-most-useful-commands-online-troubleshooting-guide/</guid><description>Arthas 真正好用的地方，不是背会 6 个命令，而是在线上先判断自己现在要确认的是线程在忙什么，还是某个方法为什么慢。把 `dashboard`、`thread`、`trace`、`watch`、`stack`、`jad` 放回两条真实排障路径里，命令边界会清楚很多。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>async-profiler、Arthas、jstack 到底什么时候该先用哪个？</title><link>https://blog.jianghuzaijian.top/blog/java/async-profiler-vs-arthas-vs-jstack-when-to-use-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/async-profiler-vs-arthas-vs-jstack-when-to-use-guide/</guid><description>线上排障时，async-profiler、Arthas、jstack 经常一起出现，但它们拿到的不是同一种证据。`jstack` 给你线程当下停在哪，Arthas 适合在线核对方法、参数和调用来源，async-profiler 则用一段时间的采样告诉你热点是不是稳定存在。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>异步任务越堆越多，很多时候根因不在异步，而在前面那段执行链失衡了</title><link>https://blog.jianghuzaijian.top/blog/java/async-task-backlog-root-cause-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/async-task-backlog-root-cause-troubleshooting-guide/</guid><description>异步 backlog 现场最容易做错的，是把问题直接归到消息队列、消费者数量或线程池。很多时候真正先坏掉的，是任务执行链里的某一段等待，让消费速度慢下来，最后才表现成 backlog 持续堆积。</description><pubDate>Sun, 22 Mar 2026 00:00:00 GMT</pubDate></item><item><title>布隆过滤器上了以后，为什么穿透还是没止住？</title><link>https://blog.jianghuzaijian.top/blog/java/bloom-filter-enabled-but-cache-penetration-still-happens-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/bloom-filter-enabled-but-cache-penetration-still-happens-guide/</guid><description>那次把数据库打高的，不是一大片随机脏 ID，而是 8 个反复出现的无效 `skuId`。Bloom Filter 明明开着，可同步链路慢了 6 分多钟，空值缓存又没补上，最后是少量漏下去的空查把等待链拖长了。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>缓存回源流量突然放大怎么排查？从一次商品详情页被热点 key 打穿说起</title><link>https://blog.jianghuzaijian.top/blog/java/cache-backsource-traffic-surge-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-backsource-traffic-surge-troubleshooting-guide/</guid><description>一次大促里，商品详情页先慢下来的不是数据库，而是一个热点 key 过期后的并发回源。真正有用的排查，不是先分型讲课，而是先证明压力是不是集中在同一批 sku、同一条 SQL 和同一个失效窗口里。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>缓存一致性问题为什么总在删缓存、改数据库之后出事？</title><link>https://blog.jianghuzaijian.top/blog/java/cache-consistency-delete-cache-update-db-problems/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-consistency-delete-cache-update-db-problems/</guid><description>缓存一致性难处理，不是因为大家没听过删缓存，而是事务提交时机、删除失败、并发回填旧值和回源压力会在同一次写操作后一起冒出来。真正麻烦的地方，通常出在这些细节刚好撞在同一段时间窗里。</description><pubDate>Sun, 22 Mar 2026 00:00:00 GMT</pubDate></item><item><title>双写、延迟双删、订阅 binlog，什么场景下各自更稳？</title><link>https://blog.jianghuzaijian.top/blog/java/cache-consistency-double-delete-vs-binlog-vs-dual-write-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-consistency-double-delete-vs-binlog-vs-dual-write-guide/</guid><description>缓存一致性最怕一上来就争论方案名字。把业务能容忍多久旧值、数据库是不是唯一事实来源、失败后怎么补偿、热点 key 回源有多贵这些前提摆清，再看双写、延迟双删和 binlog/CDC，结论通常会直接收敛。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>缓存一抖就删 key、扩线程、加重试，通常会把事故推得更大</title><link>https://blog.jianghuzaijian.top/blog/java/cache-failure-chain-drills-and-game-day-scenarios-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-failure-chain-drills-and-game-day-scenarios-guide/</guid><description>缓存故障刚开始时，最先要判断的不是名词，而是系统有没有进入回源放大。先看命中率、回源量、线程占用和数据库压力是否连成一条线，再决定保护动作，往往比急着删 key、扩线程、加重试更重要。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>缓存命中率下降怎么排查？一次发布后 key 设计被打碎的排查过程</title><link>https://blog.jianghuzaijian.top/blog/java/cache-hit-rate-drop-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-hit-rate-drop-troubleshooting-guide/</guid><description>命中率突然下降，不一定是流量变散了，也不一定是 Redis 出了故障。一次发布里，因为 key 拼接多带了渠道和实验参数，同一份商品数据被拆成了成倍增长的变体 key，命中率就是这样掉下去的。</description><pubDate>Sun, 22 Mar 2026 00:00:00 GMT</pubDate></item><item><title>缓存命中率看着正常但回源还是很高？一次“平均值掩盖高价值 miss”的排查记录</title><link>https://blog.jianghuzaijian.top/blog/java/cache-hit-rate-normal-but-backsource-still-high-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-hit-rate-normal-but-backsource-still-high-guide/</guid><description>平均命中率还在 95% 以上，数据库回源却压不住，问题往往不在图错了，而在真正昂贵的那批请求正在持续 miss。比起讨论“命中率算不算正常”，更该先把高价值 miss 从平均值里剥出来。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>缓存层出问题后，为什么应用和数据库会一起变慢的等待型链路？一次 Redis 客户端超时引发的连锁故障</title><link>https://blog.jianghuzaijian.top/blog/java/cache-layer-failure-why-app-and-db-both-slow-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-layer-failure-why-app-and-db-both-slow-guide/</guid><description>缓存层故障最怕的不是少了一层加速，而是请求持有时间被一层层拉长。这次事故里，先变坏的是 Redis 客户端超时，随后才是数据库回源、连接池等待和线程排队，一条完整的等待链就是这样被拖出来的。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>缓存预热做了还是抖？我会先把时间线、命中路径和 TTL 放在一张图上</title><link>https://blog.jianghuzaijian.top/blog/java/cache-prewarm-done-but-still-jitter-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-prewarm-done-but-still-jitter-troubleshooting-guide/</guid><description>预热任务成功、Redis 里也有 key，但切流一来还是抖，这种现场往往不是“有没有预热”这么简单。更常见的是预热范围打偏、命中路径变了、TTL 没活到接流量那一刻，或者 Redis 热了、本地状态没热。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>缓存 TTL 设计不当怎么排查？一次整点集中过期把数据库打高的事故复盘</title><link>https://blog.jianghuzaijian.top/blog/java/cache-ttl-design-traffic-backsource-database-surge-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cache-ttl-design-traffic-backsource-database-surge-guide/</guid><description>真正把数据库打高的，往往不是 TTL 短，而是 TTL 太整齐。一次整点活动里，批量预热配上统一 30 分钟 TTL，让一批商品缓存在流量最高的时候一起失效，事故感就是从这一分钟长出来的。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>熔断已经打开了，为什么系统还是要慢很久才缓过来？</title><link>https://blog.jianghuzaijian.top/blog/java/circuit-breaker-opened-why-full-link-recovery-still-slow-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/circuit-breaker-opened-why-full-link-recovery-still-slow-guide/</guid><description>熔断打开后系统没有立刻恢复，很多时候不是熔断失效，而是旧请求、重试回流和半开放量还在同一条时间线上继续拖慢恢复。把这段恢复时序看清，才知道系统到底卡在哪一步。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Java 项目里最常见的线程安全问题有哪些</title><link>https://blog.jianghuzaijian.top/blog/java/common-thread-safety-problems-in-java-projects/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/common-thread-safety-problems-in-java-projects/</guid><description>从共享变量、集合并发、单例状态到锁粒度与可见性，系统梳理 Java 项目里最常见的线程安全问题、典型场景和排查思路。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>配置刷新明明成功了，为什么 Bean 状态还是旧的？</title><link>https://blog.jianghuzaijian.top/blog/java/config-refresh-succeeded-but-bean-state-still-old-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/config-refresh-succeeded-but-bean-state-still-old-guide/</guid><description>refresh 接口返回成功、`/actuator/env` 也能看到新值，但业务行为还是老样子，这通常不是“配置没推到”，而是值只更新到了链路中的前半段：source 变了，Environment 变了，真正干活的对象却没切过去。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>连接池等待变长那晚，我怎么确认是数据库阶段慢了，不是应用拿着连接不放？</title><link>https://blog.jianghuzaijian.top/blog/java/connection-pool-wait-db-slow-vs-app-holding-connection-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/connection-pool-wait-db-slow-vs-app-holding-connection-guide/</guid><description>一次库存预占事故里，获取连接时间、连接持有时间和事务时长一起变差。真正有用的不是争论“数据库慢还是应用不放”，而是把借连接之后的时间拆开，看线程到底卡在库里还是库外。</description><pubDate>Thu, 26 Mar 2026 00:00:00 GMT</pubDate></item><item><title>容器 OOMKilled 和 Java heap OOM，区别到底在哪？</title><link>https://blog.jianghuzaijian.top/blog/java/container-oomkilled-vs-java-heap-oom-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/container-oomkilled-vs-java-heap-oom-troubleshooting-guide/</guid><description>同样都是内存事故，Pod 被 OOMKilled 和 JVM 抛出 `Java heap space` 其实是两条完全不同的入口。先看是谁先把进程停掉，再决定去保 Heap Dump，还是去保 Pod 事件、RSS 和容器边界。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>CPU 高和 GC 抖同时出现时，先证明谁是因谁是果？</title><link>https://blog.jianghuzaijian.top/blog/java/cpu-high-and-gc-frequent-causality-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cpu-high-and-gc-frequent-causality-troubleshooting-guide/</guid><description>CPU 飙高和 GC 频繁一起出现时，最怕的是一上来就站队。把时间线、线程归属、对象分配速率和回收效果对齐后，才能看清到底是 GC 在推高 CPU，还是业务热点先把 GC 带坏。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>CPU 热线程抓到了也处理了，为什么 Load 还是下不来？</title><link>https://blog.jianghuzaijian.top/blog/java/cpu-hot-thread-fixed-but-load-still-high-what-next-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/cpu-hot-thread-fixed-but-load-still-high-what-next-guide/</guid><description>高 CPU 热线程已经找到甚至临时处理掉了，系统 Load 却还是居高不下时，问题常常不在“热点线程还在不在”，而在队列积压、等待链、上下文切换、I/O 或容量恢复滞后。先把 CPU、Load、线程状态和资源队列重新放回同一条证据链，再判断下一步该查什么。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>连接池真的打满那次，我怎么往前倒回去找到根因，而不是先改 maxPoolSize</title><link>https://blog.jianghuzaijian.top/blog/java/database-connection-pool-exhausted-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/database-connection-pool-exhausted-troubleshooting-guide/</guid><description>一次支付落单事故里，Hikari 已经开始报 `connection timeout`，但真正先坏掉的不是连接数配置，而是连接回不来的那一段。把 pool exhausted 往前倒推到事务、锁等待和回退动作，根因会比盯参数更快收住。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>锁等待、热点行竞争把写接口拖慢时，应该先查什么？</title><link>https://blog.jianghuzaijian.top/blog/java/database-lock-wait-hot-row-contention-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/database-lock-wait-hot-row-contention-troubleshooting-guide/</guid><description>当写接口变慢、读接口也开始被拖慢、连接池等待跟着升高时，不要只盯数据库 CPU。把“执行慢还是等待慢 -&gt; 谁持锁太久 -&gt; 热点行还是长事务”这几个问题依次拆开，才能更快把锁等待问题和应用层超时、排队串起来。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>优惠资格回补把查询接口拖进借连接和等锁那次，真正先失控的是回补本身</title><link>https://blog.jianghuzaijian.top/blog/java/database-not-high-load-but-api-still-slow-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/database-not-high-load-but-api-still-slow-troubleshooting-guide/</guid><description>这篇只讲一次优惠资格回补事故：回补任务先把连接批量借走又迟迟不还，在线查询先堵在 Hikari 门口；进库后又撞上同一批热点券账户锁，最后把可用优惠查询一起拖慢。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>数据库 RT 抬高但慢 SQL 不明显，该从锁、线程还是 I/O 起手？</title><link>https://blog.jianghuzaijian.top/blog/java/database-rt-high-but-no-obvious-slow-sql-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/database-rt-high-but-no-obvious-slow-sql-troubleshooting-guide/</guid><description>数据库 RT 明显抬高，慢日志却不扎眼时，现场最容易卡在“SQL 看起来都还行”。这时真正要拆的往往不是某一条语句，而是 RT 里混进了多少锁等待、事务停留、连接排队和 I/O 波动。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>一次数据库等待链事故里，面板到底该怎么帮你收敛判断</title><link>https://blog.jianghuzaijian.top/blog/java/database-wait-chain-monitoring-dashboard-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/database-wait-chain-monitoring-dashboard-guide/</guid><description>真正麻烦的数据库等待链事故，不是没有图，而是现场每个人都能从图里讲出一个像样的猜测。沿一次典型夜间事故往下走，才能看清哪些面板只是证据，哪些误判最该先排掉。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>数据库 CPU 正常但 active sessions 很高那次，我是怎么把会话堆积拆回等待链的？</title><link>https://blog.jianghuzaijian.top/blog/java/db-cpu-normal-but-active-sessions-high-wait-chain-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/db-cpu-normal-but-active-sessions-high-wait-chain-guide/</guid><description>一次库存中心事故里，数据库 CPU 只有三成多，active sessions 却一路冲高。真正有用的不是盯着 CPU 争论数据库忙不忙，而是把 active sessions 拆成锁等待、事务年龄、连接归还和回退后的回落顺序。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>分布式锁没报错但吞吐变差，应该先查续约还是锁粒度？</title><link>https://blog.jianghuzaijian.top/blog/java/distributed-lock-no-errors-but-throughput-drops-renewal-vs-granularity-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/distributed-lock-no-errors-but-throughput-drops-renewal-vs-granularity-guide/</guid><description>分布式锁没有明显报错，不代表锁链路健康。吞吐下降时，把持锁时间、续约抖动、锁粒度、热点 key、下游等待和重试放到同一段时间窗里一起看，才能判断到底是锁续约不稳，还是锁设计本身把并发压扁了。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Young GC 很频繁但没 Full GC，为什么吞吐还是掉得厉害？</title><link>https://blog.jianghuzaijian.top/blog/java/frequent-young-gc-but-no-full-gc-throughput-drop-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/frequent-young-gc-but-no-full-gc-throughput-drop-guide/</guid><description>Young GC 已经越跑越密，但还没出现明显 Full GC 时，服务照样可能先掉吞吐。排这类现场，关键不是盯着 Old 区等事故升级，而是对齐对象分配、停顿频率、CPU 归属和业务推进节奏，找出真正把系统拖慢的那一段。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Full GC 频繁怎么办：从回收效果分清泄漏和分配压力</title><link>https://blog.jianghuzaijian.top/blog/java/full-gc-frequent-causes-and-analysis/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/full-gc-frequent-causes-and-analysis/</guid><description>Full GC 一频繁，最常见的错误动作就是先调 JVM 参数。但参数只能改表现，不能替你判断根因；先看回收效果、趋势和对象变化，才知道到底是泄漏、晋升过快，还是业务模型把堆顶住了。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>网关 504、应用超时、客户端超时，到底谁先超时？</title><link>https://blog.jianghuzaijian.top/blog/java/gateway-504-vs-app-timeout-vs-client-timeout-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/gateway-504-vs-app-timeout-vs-client-timeout-troubleshooting-guide/</guid><description>真正把人带偏的，往往不是 504 本身，而是每一层都在用自己的秒表报错。把客户端、网关、应用到下游的超时预算摆成一条时间线，才能看清是谁先耗尽等待，谁只是最后把故障喊出来。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>`GC overhead limit exceeded` 怎么排查？它常常不是普通 OOM</title><link>https://blog.jianghuzaijian.top/blog/java/gc-overhead-limit-exceeded-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/gc-overhead-limit-exceeded-troubleshooting-guide/</guid><description>看到 `GC overhead limit exceeded` 时，别急着把它等同成堆不够。先看 GC 已经浪费了多少时间、对象是长期回不来，还是某个业务窗口突然制造了一场对象风暴。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Heap Dump 抓到了，第一轮分析最该先排除哪几类对象？</title><link>https://blog.jianghuzaijian.top/blog/java/heap-dump-first-analysis-which-objects-to-rule-out-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/heap-dump-first-analysis-which-objects-to-rule-out-guide/</guid><description>Heap Dump 到手后，第一轮最容易被 `byte[]`、`String` 和各种大集合带偏。真正该先做的不是立刻定罪，而是结合抓取时机、MAT 的持有链和线程现场，把一批假嫌疑尽快排掉。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>高负载下 readiness 一直抖时，实例其实不是“坏了”，而是在容量边缘来回掉线</title><link>https://blog.jianghuzaijian.top/blog/java/high-load-readiness-flap-why-instances-oscillate-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/high-load-readiness-flap-why-instances-oscillate-guide/</guid><description>高负载下 readiness 一直抖，往往不是探针接口自己坏了，而是实例的接流量能力反复跨过阈值：线程池、连接池、下游等待和探针判定一起顶到了边缘。先看谁最早失稳，再决定要不要动探针。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>热点表、热点索引、热点行，该先拆哪一层？</title><link>https://blog.jianghuzaijian.top/blog/java/hotspot-table-index-row-which-layer-to-split-first-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/hotspot-table-index-row-which-layer-to-split-first-guide/</guid><description>热点集中不等于立刻分库分表。真正难的是先判断热点到底落在表、索引还是行，再决定先拆写入路径、先打散索引热点，还是先改业务模型。先把等待压在哪一层看清楚，后面的拆分才不会越做越重。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>幂等校验明明通过了，为什么消息还是会重复消费？</title><link>https://blog.jianghuzaijian.top/blog/java/idempotency-check-passed-but-duplicate-consume-still-happens-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/idempotency-check-passed-but-duplicate-consume-still-happens-guide/</guid><description>幂等校验通过，不等于业务副作用只会执行一次。把去重键、状态落库、提交可见性、ack 时序和外部副作用摆在同一个时序里，才能解释为什么“检查没问题”，重复消费却还是不断发生。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>故障复盘如何从“现象记录”升级为“可复用方法论”？</title><link>https://blog.jianghuzaijian.top/blog/java/incident-review-from-symptom-record-to-reusable-methodology-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/incident-review-from-symptom-record-to-reusable-methodology-guide/</guid><description>很多复盘把事故经过讲清了，却没有把真正可复用的判断顺序留下来。要让复盘变成下次还能直接拿来用的方法，不是多写几条改进项，而是把故障链、证据顺序、动作边界和适用范围从一次具体事故里抽出来。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>故障时间线怎么记，才能在 30 分钟后还原判断过程？</title><link>https://blog.jianghuzaijian.top/blog/java/incident-timeline-how-to-record-decisions-during-outage-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/incident-timeline-how-to-record-decisions-during-outage-guide/</guid><description>真正容易从事故现场丢掉的，不只是截图和日志，而是“为什么那时先看这个、先做那个”。把时间线记成证据、判断、动作和结果的连续变化，30 分钟后才有机会还原现场，而不是只剩一串零散操作。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>接口 timeout 冒出来那晚，我怎么确认不是应用也不是网络，而是下游慢了</title><link>https://blog.jianghuzaijian.top/blog/java/interface-timeout-application-network-downstream-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/interface-timeout-application-network-downstream-troubleshooting-guide/</guid><description>一次订单确认 timeout 事故里，真正有用的不是把 timeout 讲成三种概念，而是先把样本分堆，再按证据决定排除顺序。最后把故障收住的，是一条完整的收敛链。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>定时任务、异步任务、业务线程池应该如何隔离？</title><link>https://blog.jianghuzaijian.top/blog/java/isolate-scheduled-async-business-thread-pools-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/isolate-scheduled-async-business-thread-pools-guide/</guid><description>定时任务、异步任务和业务线程池混用，真正危险的不是结构不优雅，而是某一类任务失控时会把别的任务一起拖下水。隔离时要同时看时效性、失败影响、资源占用方式和共享依赖，别把拆线程池做成只有名字变化的假动作。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Java 内存泄漏怎么定位？从 Heap Dump 到 MAT 实战</title><link>https://blog.jianghuzaijian.top/blog/java/java-memory-leak-heap-dump-mat-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/java-memory-leak-heap-dump-mat-guide/</guid><description>从堆转储、对象占用分析到引用链排查，系统梳理 Java 内存泄漏的定位思路、常见场景和使用 MAT 分析堆快照的方法。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Java 内存持续上涨但没有 OOM，先怎么排查？</title><link>https://blog.jianghuzaijian.top/blog/java/java-memory-rising-without-oom-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/java-memory-rising-without-oom-troubleshooting-guide/</guid><description>还没 OOM 却一路涨内存，最怕的不是它还活着，而是把堆上涨、RSS 上涨和短时高峰混成一件事。先把几条曲线对到同一个事故时间窗里，方向才不会一开始就走偏。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Java 服务 CPU 高怎么排查：线上定位顺序别一上来就猜</title><link>https://blog.jianghuzaijian.top/blog/java/java-service-cpu-high-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/java-service-cpu-high-troubleshooting-guide/</guid><description>当 Java 服务 CPU 飙高时，不要先猜 GC 或直接扩容。先分清是单实例还是整组实例，再按“进程 -&gt; 线程 -&gt; 线程栈 -&gt; GC / 重试 / 热点代码”这条顺序收敛，才能更快判断问题是在计算热点、线程空转、下游放大，还是 GC 压力。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Java 服务 OOM 了怎么排查？先分类型，再决定往哪条线查</title><link>https://blog.jianghuzaijian.top/blog/java/java-service-oom-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/java-service-oom-troubleshooting-guide/</guid><description>OOM 一发生，最容易做的事就是先扩内存，或者直接认定成堆泄漏。但 OOM 这个词底下其实是好几类完全不同的事故，先分类型，后面的止血和取证才不会跑偏。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>线程池打满以后，应该先查队列、拒绝策略还是慢任务？</title><link>https://blog.jianghuzaijian.top/blog/java/java-thread-pool-parameter-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/java-thread-pool-parameter-guide/</guid><description>线程池打满只是执行层红灯，不等于根因就在参数。把队列堆积、慢任务、下游等待、数据库链路和 CPU / GC 放在同一条排查链里看，才更容易找到真正拖慢 worker 的地方。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>线上排障时，jstack、jmap、jstat 我通常怎么决定先拿哪一个</title><link>https://blog.jianghuzaijian.top/blog/java/jstack-jmap-jstat-how-to-read-in-production/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/jstack-jmap-jstat-how-to-read-in-production/</guid><description>`jstack`、`jmap`、`jstat` 不难记，难的是线上现场先动哪一个、为什么不先动另外两个。把它们放回 CPU 高、GC 抖动、疑似内存问题这几类现场里，工具边界会比平均铺开讲分工更清楚。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>JVM Safe Point 太久，为什么服务会像“卡死”一样？</title><link>https://blog.jianghuzaijian.top/blog/java/jvm-safe-point-too-long-why-service-freezes-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/jvm-safe-point-too-long-why-service-freezes-guide/</guid><description>服务像突然冻住、线程又看不出典型死锁时，Safe Point 往往是那条容易漏掉的线索。把停顿时间、线程状态、GC、线程 Dump 和当时的热点操作对在一起，才更容易看清到底是 Stop-The-World、进入安全点太慢，还是别的等待型假死。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>结算确认那次真正拖慢系统的，不是慢 SQL，而是开着事务等票据服务回包</title><link>https://blog.jianghuzaijian.top/blog/java/long-transaction-performance-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/long-transaction-performance-troubleshooting-guide/</guid><description>这篇只讲一次结算事故：`POST /settlement/confirm` 先坏掉，库里随后冒出长事务、锁等待和连接池紧张。问题不在于先讲“长事务怎么拆”，而在于先看见有人把远程调用包进了事务。</description><pubDate>Sun, 22 Mar 2026 00:00:00 GMT</pubDate></item><item><title>长事务明明已经修了，连接池还是很紧时，我怎么确认问题还卡在哪一段？</title><link>https://blog.jianghuzaijian.top/blog/java/long-tx-fixed-but-connection-pool-still-tight-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/long-tx-fixed-but-connection-pool-still-tight-guide/</guid><description>一次对账链路优化后，事务时长已经明显下降，但连接池和 pending 还是高位。真正有用的不是立刻否定修复，而是把事务时长、持连接时间、锁等待和 backlog 的回落顺序放到一个时间窗里复核。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>锁竞争不高却吞吐掉得厉害，先查线程切换还是下游等待？</title><link>https://blog.jianghuzaijian.top/blog/java/low-lock-contention-but-throughput-dropping-thread-switch-vs-downstream-wait-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/low-lock-contention-but-throughput-dropping-thread-switch-vs-downstream-wait-guide/</guid><description>锁竞争指标不高，不等于并发链路就健康。吞吐下降时，更有价值的是把线程切换、队列波动、连接池等待、下游阻塞和伪并发边界放进同一段证据里看清楚，再判断问题是线程在空耗 CPU，还是业务线程长期卡在等待型瓶颈上。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>消息越堆越多，为什么常常不是消费者数量不够，而是下游变慢了？</title><link>https://blog.jianghuzaijian.top/blog/java/message-backlog-growing-because-downstream-slow-not-consumer-count-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/message-backlog-growing-because-downstream-slow-not-consumer-count-guide/</guid><description>消息堆积时，先别急着加消费者。只有把入队速度、单消息执行时长、下游 RT、数据库等待、重试回流和热点分区放到同一个时间窗里对齐，才能解释为什么“消费者看起来很多”，积压却还是越来越重。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Metaspace 一直涨但堆没 OOM，怎么判断是不是 ClassLoader 泄漏？</title><link>https://blog.jianghuzaijian.top/blog/java/metaspace-rising-no-heap-oom-classloader-leak-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/metaspace-rising-no-heap-oom-classloader-leak-guide/</guid><description>Heap 还算平，Metaspace 和已加载类数量却一轮轮往上叠时，别再沿 heap 那条线硬查。把发布动作、类加载数量、GC 日志和 ClassLoader 持有关系放在一起，方向会快很多。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>值班时多个告警同时响，第一轮怎么把范围收清？</title><link>https://blog.jianghuzaijian.top/blog/java/multiple-alerts-first-round-scope-cutting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/multiple-alerts-first-round-scope-cutting-guide/</guid><description>19:47，群里一下子进来 12 条告警：网关 502、下单超时、Redis 慢日志、CPU 高、Pod 重启。这个时候最值钱的动作，不是赶紧去认一个根因，而是先把告警墙压成几条清楚的故障线。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>MyBatis 分页为什么慢？深分页问题怎么优化</title><link>https://blog.jianghuzaijian.top/blog/java/mybatis-pagination-deep-page-optimization/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/mybatis-pagination-deep-page-optimization/</guid><description>从 limit offset 的执行代价入手，系统梳理 MyBatis 分页在大数据量场景下变慢的常见原因、排查思路和优化方向；它更适合作为 deep page 补充内容，而不是通用分页教程。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>MySQL EXPLAIN 详解：别背字段，先看出这条 SQL 慢在哪</title><link>https://blog.jianghuzaijian.top/blog/java/mysql-explain-guide-type-rows-extra/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/mysql-explain-guide-type-rows-extra/</guid><description>EXPLAIN 真正有用的地方，不是把 type、rows、key、Extra 一列列背下来，而是借这几个信号尽快判断：这条 SQL 到底慢在扫描过重、索引路径不对，还是排序和临时处理把成本抬高了。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>explain 看起来没问题，SQL 还是很慢，下一步该查执行、等待还是连接池？</title><link>https://blog.jianghuzaijian.top/blog/java/mysql-explain-normal-but-sql-still-slow-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/mysql-explain-normal-but-sql-still-slow-troubleshooting-guide/</guid><description>explain 看着正常，不等于 SQL 在线上就真的没问题。先把时间花在哪里拆开，往往比继续争论索引对不对更有用：卡在拿连接、库内执行、数据库等待，还是返回后又被应用放大了。</description><pubDate>Thu, 26 Mar 2026 00:00:00 GMT</pubDate></item><item><title>MySQL 索引为什么没按预期生效：SQL 明明走了索引，怎么还是慢</title><link>https://blog.jianghuzaijian.top/blog/java/mysql-index-invalid-8-common-causes/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/mysql-index-invalid-8-common-causes/</guid><description>建了索引、执行计划里也能看到 key，但 SQL 还是慢，问题往往不在“索引有没有生效”，而在过滤、排序、扫描范围或回表这几步里，哪一步没有按预期接上。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>MySQL 里 order by 为什么会慢？从过滤、候选集到分页方式一条线看清</title><link>https://blog.jianghuzaijian.top/blog/java/mysql-order-by-why-slow-analysis-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/mysql-order-by-why-slow-analysis-guide/</guid><description>`order by` 变慢，常常不是排序单点出了问题，而是过滤路径不够收敛、索引顺序接不上、候选集太大，再叠上分页和回表，把成本一层层抬了起来。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>我怎么沿着一条慢 SQL，把“像索引问题”一路查到真实瓶颈</title><link>https://blog.jianghuzaijian.top/blog/java/mysql-slow-sql-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/mysql-slow-sql-troubleshooting-guide/</guid><description>慢 SQL 排查最容易一上来就盯 explain，然后把所有问题都讲成索引问题。这篇不做总纲，只沿一条真实排查线往下走：从接口变慢开始，先确认是不是这条 SQL，为什么 explain 看起来还行却还是慢，最后怎么把瓶颈坐实到锁等待和连接占用上。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Netty EventLoop 被阻塞后，为什么 RPC 超时会扩散？</title><link>https://blog.jianghuzaijian.top/blog/java/netty-event-loop-blocked-why-rpc-timeout-spreads-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/netty-event-loop-blocked-why-rpc-timeout-spreads-guide/</guid><description>RPC timeout 成片扩散时，根因不一定在下游，也可能在调用端的 Netty EventLoop。只有先辨认清楚是下游执行慢、业务线程在等，还是 I/O 线程已经推进不动，后面的线程池、Tomcat 入口线程和隐藏等待分析才不会跑偏。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>堆外内存上涨把容器逼死时，先留哪些证据？</title><link>https://blog.jianghuzaijian.top/blog/java/off-heap-memory-rising-container-oom-evidence-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/off-heap-memory-rising-container-oom-evidence-guide/</guid><description>Pod 已经被 OOMKilled，Heap 却没满时，最容易做错的不是判断，而是先把现场丢了。真正该先保住的是容器事件、RSS、NMT、线程和同 Pod 进程占用，再谈根因。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Old 区没打满却频繁 Full GC？一次 G1 Humongous Allocation 事故复盘</title><link>https://blog.jianghuzaijian.top/blog/java/old-gen-not-full-but-full-gc-frequent-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/old-gen-not-full-but-full-gc-frequent-guide/</guid><description>这篇不泛讲 Full GC 的所有成因，只复盘一次真实线上问题：Old 区只有六成多，但预览接口一次性拼出超大 JSON，触发 G1 Humongous Allocation，最后把 Full GC 节奏打出来。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>线上 OOM 之后，第一时间先保哪些现场？</title><link>https://blog.jianghuzaijian.top/blog/java/oom-first-response-scene-preservation-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/oom-first-response-scene-preservation-guide/</guid><description>这是 OOM 现场保护页：最怕的不是暂时没结论，而是现场先没了，先分 heap、容器、堆外和线程分支，再按日志、Heap Dump、GC、线程、容器事件与业务时间线的顺序留证。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>P99 很高但平均 RT 正常，这类接口性能问题该怎么查？</title><link>https://blog.jianghuzaijian.top/blog/java/p99-jitter-high-but-average-rt-normal-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/p99-jitter-high-but-average-rt-normal-troubleshooting-guide/</guid><description>平均 RT 还没明显变差，但 P99、超时和偶发卡顿已经先起来时，通常不是系统整体都慢了，而是少量请求、少量实例或某个等待阶段先出了问题。先确认这是不是尾延迟，再把接口、实例、参数、时间窗和阶段耗时切开，后面才知道该往实例差异、隐藏等待、数据库等待链还是发布差异收。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>发布后只有一小批实例异常时，我更相信实例对照，而不是整体平均值</title><link>https://blog.jianghuzaijian.top/blog/java/partial-instances-abnormal-actuator-config-env-diff-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/partial-instances-abnormal-actuator-config-env-diff-guide/</guid><description>只有一小批实例异常时，整体大盘经常会把问题盖住。把异常实例和正常实例拉成一组对照，再看 Actuator、配置来源、环境变量和启动现实，通常比继续争“是不是代码回归”快得多。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>读多写少的接口为什么也会被写事务拖慢？</title><link>https://blog.jianghuzaijian.top/blog/java/read-heavy-apis-slow-because-of-write-transactions-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/read-heavy-apis-slow-because-of-write-transactions-guide/</guid><description>读接口慢，不一定是查询自己有问题。很多读多写少的接口，真正慢在写事务把锁、连接、副本延迟和数据库等待链一起拖长了。更有用的做法，是先判断读接口到底慢在执行还是等待，再沿写事务外溢到读链路的共享等待链逐层收敛。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>线上故障排查时，为什么“最近一次变更”总值得先查？</title><link>https://blog.jianghuzaijian.top/blog/java/recent-change-first-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/recent-change-first-troubleshooting-guide/</guid><description>那天明明没人发版，21:07 的超时却紧贴着路由权重调整、回填任务恢复和证书轮换长出来。把暂停回填后的回落、权重调回后的样本变化放回现场后，“最近变更值得先查”就不再像一句主张，而像一条被验证过的收敛路径。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>最近一次发布后接口变慢，别急着追某个 commit，先把发布窗口里的变化摊平</title><link>https://blog.jianghuzaijian.top/blog/java/recent-release-interface-slow-what-to-check-first-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/recent-release-interface-slow-what-to-check-first-guide/</guid><description>19:02 发布完成，19:09 `/trade/confirm` 的 P99 从 180ms 顶到 2.1s。后来把 19:00 到 19:15 的发布窗口摊开看，先跳出来的不是某个 commit，而是灰度开关和紧跟着启动的回填任务。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Redis 缓存击穿、穿透、雪崩，到底应该怎么区分和处理？先看一次不存在商品被爬虫打穿的事故</title><link>https://blog.jianghuzaijian.top/blog/java/redis-cache-penetration-breakdown-avalanche/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/redis-cache-penetration-breakdown-avalanche/</guid><description>真到线上时，最先有价值的不是把穿透、击穿、雪崩背成定义，而是先证明请求打的到底是不是一批本来就不存在的数据。这次事故里，数据库被压高不是因为缓存整体失效，而是爬虫持续请求无效商品 ID，空结果又没有被挡住。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Redis 热 key 问题怎么发现和处理？从一次分片负载失衡查到首页活动配置说起</title><link>https://blog.jianghuzaijian.top/blog/java/redis-hot-key-detection-and-handling-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/redis-hot-key-detection-and-handling-guide/</guid><description>热 key 最容易被误查成“Redis 集群容量不够”。这次事故里，先变坏的是一个分片的 CPU 和网络，而不是整组命中率。真正有用的排查，是先证明压力有没有被压在少数节点、少数 key 上，再决定本地缓存还是拆热点。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Redis 内存一直涨，先别急着怪大 key，先看涨的是哪一段</title><link>https://blog.jianghuzaijian.top/blog/java/redis-memory-rising-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/redis-memory-rising-troubleshooting-guide/</guid><description>Redis 内存上涨时，现场最常见的误判就是一上来就找大 key 或直接扩容。真正更值钱的第一步，是先分清涨的是数据集、RSS，还是客户端相关内存。</description><pubDate>Sun, 22 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Redis 分片后热点仍集中，问题更可能出在哪一层？</title><link>https://blog.jianghuzaijian.top/blog/java/redis-sharding-done-but-hotspots-still-concentrated-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/redis-sharding-done-but-hotspots-still-concentrated-guide/</guid><description>Redis 分片能摊开平均压力，却不会顺手打散爆款对象、集中过期和回源窗口。分片做完热点还扎堆时，更该回头检查 key 设计、访问形态、本地缓存和失效节奏，而不是一上来都算到槽位分布头上。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>重试风暴把慢接口进一步放大时，怎么区分表象和根因？</title><link>https://blog.jianghuzaijian.top/blog/java/retry-storm-amplifies-slow-api-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/retry-storm-amplifies-slow-api-troubleshooting-guide/</guid><description>最危险的重试风暴，起点往往不是流量突然翻倍，而是某一段等待先变长，随后同一批请求被多打了几遍。把原始请求量、实际调用量、超时边界和重试层级对齐，才能看清是谁先点火，谁把火越吹越大。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>RPC 超时但下游不慢，很多时候是请求根本没稳定到下游</title><link>https://blog.jianghuzaijian.top/blog/java/rpc-timeout-but-downstream-not-slow-hidden-middle-layer-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/rpc-timeout-but-downstream-not-slow-hidden-middle-layer-guide/</guid><description>RPC timeout 而下游 RT 看起来正常时，排查最容易被带偏到“下游是不是没暴露出来”。很多真实现场里，请求预算其实消耗在连接池、代理层或回调线程这些中间环节，请求根本没稳定到下游。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>同一个 API 只有部分实例变慢，应该先查什么？</title><link>https://blog.jianghuzaijian.top/blog/java/same-api-only-some-instances-slow-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/same-api-only-some-instances-slow-troubleshooting-guide/</guid><description>14:07，只有 3 台 `account-api` 的 `/profile/query` P99 从 220ms 顶到 3s，另外 9 台还稳着。碰到这种形状时，我更愿意先把慢实例和正常实例绑成对照，看请求样本、节点现实、配置来源和启动后状态到底从哪一步开始分叉。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>单接口变慢和整个服务变慢，入口完全不是一回事</title><link>https://blog.jianghuzaijian.top/blog/java/single-api-slow-vs-whole-service-slow-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/single-api-slow-vs-whole-service-slow-troubleshooting-guide/</guid><description>值班群里先报的是 `/order/confirm` 超时，但把 URI 看板拆开 30 秒后，`/order/detail`、`/order/list`、`/order/coupon` 也在一起抬头。就是这 30 秒，决定了后面先查连接池还是先查那条接口自己的 SQL。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>如何建立接口慢 / 超时专题的值班检查表？</title><link>https://blog.jianghuzaijian.top/blog/java/slow-api-timeout-oncall-checklist-how-to-build-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/slow-api-timeout-oncall-checklist-how-to-build-guide/</guid><description>接口慢和超时值班最怕的不是不会查，而是每次都得从头重排顺序。把影响面、时间线、线程池、连接池、下游超时、重试放大和止血边界沉成固定检查表，值班现场才不会总靠个人经验硬扛。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>慢接口排查时，日志、Trace、指标三者先看谁？</title><link>https://blog.jianghuzaijian.top/blog/java/slow-api-troubleshooting-logs-vs-trace-vs-metrics-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/slow-api-troubleshooting-logs-vs-trace-vs-metrics-guide/</guid><description>慢接口现场最怕不是工具不够，而是三种证据一起翻却没有顺序。很多时候先决定证据顺序，比分别把日志、Trace 和指标都看一遍更重要。真正稳的做法，往往是先用指标切范围，再用 Trace 拆耗时，最后再让日志补上触发条件和上下文。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>慢 SQL 修完了，接口还是慢，怎么做全链路复核？</title><link>https://blog.jianghuzaijian.top/blog/java/slow-query-fixed-but-interface-still-slow-full-chain-verification-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/slow-query-fixed-but-interface-still-slow-full-chain-verification-guide/</guid><description>慢 SQL 修完以后接口还慢，往往不是优化没生效，而是问题根本不只在 SQL。要重新对齐的，是数据库 RT、连接池、线程池、缓存回源、RPC 依赖和超时预算这些环节里，哪一段真的降了，哪一段只是换了地方继续卡。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 异步任务为什么看起来异步了，主线程还是很慢？</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-async-not-async-main-thread-slow-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-async-not-async-main-thread-slow-guide/</guid><description>异步没按预期异步时，问题通常不只是 @Async 有没有生效。调用方还在等、线程池开始堆积、共享资源被放大，都会让“看起来异步”最后跑成同步体验。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 自动配置为什么像没生效？我会先怀疑哪几个现场</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-auto-configuration-condition-not-effective-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-auto-configuration-condition-not-effective-troubleshooting-guide/</guid><description>自动配置看起来没生效时，最浪费时间的做法就是一上来翻源码。更实用的方式，通常是先确认它到底是没进场、条件没过，还是 Bean 明明在却根本没被用上。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 启动卡在 Bean 初始化？先别说框架慢，先看它在等什么</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-bean-initialization-stuck-startup-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-bean-initialization-stuck-startup-guide/</guid><description>启动日志卡在某个 Bean 附近时，问题往往不是 Spring 自己慢，而是这个 Bean 把远程调用、数据预热或一整串依赖都拖进了启动关键路径。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 灰度发布后，为什么只有部分实例慢或行为不一致？</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-canary-release-partial-instances-slow-or-inconsistent-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-canary-release-partial-instances-slow-or-inconsistent-guide/</guid><description>灰度发布后只有部分实例变慢，最容易让人把锅全甩给&quot;新版本&quot;。但很多时候，真正拉开差异的不是代码本身，而是流量命中、环境现实、冷启动和本地状态没有对齐。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 配置改了还是旧值？从配置生效链判断卡在哪一层</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-config-changed-still-old-value-refresh-restart-config-source-drift-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-config-changed-still-old-value-refresh-restart-config-source-drift-guide/</guid><description>15:28 配置中心已经把 `order.submit.timeout-ms` 改成了 800，`/actuator/env` 看起来也是新值，但业务日志里还在按 3000ms 超时。遇到这种现场，我不会先争 refresh 还是 restart，而是先找旧值到底停在了哪一层。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 配置为什么没生效？我明明改了 yml 还是旧值</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-config-override-order-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-config-override-order-troubleshooting-guide/</guid><description>排 Spring Boot 配置问题，最容易浪费时间的就是反复翻 yml。更省时间的做法，是先确认当前进程里这个 key 到底来自哪一层，再判断是 profile、环境变量、启动参数还是刷新链路把它带偏了。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 环境不一致怎么查？从 profile、挂载文件到 JVM 参数逐项核对</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-env-diff-profile-mount-jvm-flag-checklist-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-env-diff-profile-mount-jvm-flag-checklist-guide/</guid><description>两个 Pod 跑着同一个镜像，返回结果却像两套服务。后来真正把差异找出来的，不是仓库里的 `application.yml`，而是容器里那几行 `SPRING_PROFILES_ACTIVE`、挂载文件和 `-D` 参数。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 健康检查、就绪探针和优雅下线为什么经常让服务状态看起来不对？</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-health-readiness-graceful-shutdown-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-health-readiness-graceful-shutdown-guide/</guid><description>很多“探针不准”的现场，真正错的不是某个接口返回值，而是三块钟没对齐：应用内部状态、平台探针结果、流量真正摘除的时机。把这三段时间线摆平，问题通常比单改阈值清楚得多。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot Actuator、线程池、连接池、慢请求这些运行态观测点，应该怎么串起来看？</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-runtime-observability-actuator-thread-pool-connection-pool-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-runtime-observability-actuator-thread-pool-connection-pool-guide/</guid><description>线上一慢，最麻烦的不是没图，而是每个人盯着不同一张图说话。把慢请求、线程池、连接池和下游等待放回同一分钟里，才看得出究竟是哪一段先把整条链拖住了。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 定时任务越跑越乱？一次重复执行把数据库也拖慢的常见链路</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-scheduled-task-duplicate-backlog-db-slow-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-scheduled-task-duplicate-backlog-db-slow-guide/</guid><description>定时任务重复执行、越跑越堆，最后把数据库拖慢时，问题往往不是单点故障，而是一条事故链：执行权没兜住，单轮又越来越慢，最后把锁、事务和在线请求一起拖下水。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 服务只在高峰期漂移，该从线程池、连接池还是缓存切入？</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-service-drifts-only-at-peak-thread-pool-connection-pool-cache-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-service-drifts-only-at-peak-thread-pool-connection-pool-cache-guide/</guid><description>低峰没事，一到高峰就发飘，这种问题最怕被一句“流量大了”带过去。把同一实例在高低峰的线程池、连接池、缓存命中和 readiness 放在一起比，最早失稳的那一层通常会自己露出来。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 服务发布后状态开始漂移，怎么判断问题先从哪一层开始</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-service-state-drift-after-release-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-service-state-drift-after-release-guide/</guid><description>16:04 发布完成时一切都还是绿的，16:11 开始只有两台新 Pod 的报价结果不对，16:18 P99 才跟着抬头。发布后“状态漂移”最怕的不是难，而是把后面出现的红灯误当成第一现场。</description><pubDate>Mon, 23 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring Boot 启动慢怎么排查？把启动、外部依赖和 readiness 拆开看</title><link>https://blog.jianghuzaijian.top/blog/java/spring-boot-startup-slow-analysis-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-boot-startup-slow-analysis-guide/</guid><description>Spring Boot 一慢启动，最怕把所有现象都叫成“框架太重”。问题常常分成几段：端口没起来、端口起来了但服务还没 ready，或者本地和线上压根不是同一种慢法；把这几段拉开后，才更容易判断该查哪一层。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Spring 事务为什么总像没生效？别先背概念，先回到出事现场</title><link>https://blog.jianghuzaijian.top/blog/java/spring-transaction-why-not-work-common-cases/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/spring-transaction-why-not-work-common-cases/</guid><description>事务没按预期回滚时，很多人第一反应是注解失效了。可真实项目里，更常见的是你以为在一个事务里，实际上调用没走代理、异常被吃掉，或者早就切到另一条边界了。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>SQL 优化知识笔记：从索引、写法到排查路径</title><link>https://blog.jianghuzaijian.top/blog/java/sql-optimization-notes-from-indexes-to-explain/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/sql-optimization-notes-from-indexes-to-explain/</guid><description>把面试里常被追问的 SQL 优化经验整理成一篇可反复翻看的复核型笔记，覆盖索引设计、SQL 写法、分页、排序、聚合与慢 SQL 排查，但不替代真实慢 SQL 的现场定位。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>稳定性治理先做容量评估、慢链路梳理还是告警分层？</title><link>https://blog.jianghuzaijian.top/blog/java/stability-governance-capacity-vs-slow-chain-vs-alert-layering-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/stability-governance-capacity-vs-slow-chain-vs-alert-layering-guide/</guid><description>这三件事都重要，但真正的先后顺序往往不是在会里排出来的，而是在一次事故里被逼出来的：先找到那条真实拖垮现场的慢链，告警才知道该按哪一层重做，容量边界也才算得出来。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>没配 startupProbe，为什么慢启动会被当成启动失败？</title><link>https://blog.jianghuzaijian.top/blog/java/startup-probe-missing-why-slow-boot-looks-like-failure-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/startup-probe-missing-why-slow-boot-looks-like-failure-guide/</guid><description>慢启动最像假故障的时候，不在于报错文案多像失败，而在于日志还在往前走，探针已经开始连续判死。把启动日志、Pod 事件和 probe 介入时间对齐，才知道这是启动链真断了，还是平台在应用快起来前先动了手。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>synchronized 和 ReentrantLock 有什么区别？项目里该怎么选</title><link>https://blog.jianghuzaijian.top/blog/java/synchronized-vs-reentrantlock-how-to-choose/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/synchronized-vs-reentrantlock-how-to-choose/</guid><description>`synchronized` 和 `ReentrantLock` 的区别不难背，难的是放回项目代码里时到底该为哪些能力多付复杂度。把简单互斥、超时、中断、Condition 这些真实需求拆开，选型会比直接背特点更靠谱。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>临时止血动作为什么也要记录回滚条件和观察指标？</title><link>https://blog.jianghuzaijian.top/blog/java/temporary-stopgap-actions-rollback-conditions-and-observation-metrics-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/temporary-stopgap-actions-rollback-conditions-and-observation-metrics-guide/</guid><description>很多止血动作不是做错了，而是做完以后没人说得清多久算有效、什么情况下撤回、先恢复哪一项。把动作目的、观察指标和回滚条件一起写下来，止血才不会从短期保护变成新的长期风险。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>线程池和数据库连接池的容量，为什么要一起做预算？</title><link>https://blog.jianghuzaijian.top/blog/java/thread-pool-and-db-connection-pool-capacity-planning-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/thread-pool-and-db-connection-pool-capacity-planning-guide/</guid><description>线程池和数据库连接池如果各自按经验配，线上很容易出现“线程还很多、连接先耗尽”或“连接够了、线程先堆死”的错位。把任务耗时结构、数据库连接持有时间、下游慢调用和峰值并发放回同一套容量模型里，预算才不会彼此打架。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>线程池队列不长但任务还是慢，常见瓶颈在哪里？</title><link>https://blog.jianghuzaijian.top/blog/java/thread-pool-queue-not-long-but-tasks-still-slow-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/thread-pool-queue-not-long-but-tasks-still-slow-guide/</guid><description>队列不长不等于线程池没问题。任务可能慢在执行中等待、串行化边界、连接池或下游资源，也可能只是 queue 指标没有暴露真实拥塞。先分清这是线程池伪正常、隐藏等待，还是入口线程 / 异步 backlog / 连接池链的另一种表现。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>线程池参数怎么按 CPU 密集和 IO 密集任务分别定？</title><link>https://blog.jianghuzaijian.top/blog/java/thread-pool-sizing-cpu-bound-vs-io-bound-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/thread-pool-sizing-cpu-bound-vs-io-bound-guide/</guid><description>给线程池定参数，真正难的不是记住 CPU 型和 IO 型各自的公式，而是看清任务时间花在计算、等待还是混合阶段，再据此约束线程数、队列和外部资源边界。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>ThreadLocal 常见坑有哪些？项目里最容易踩的几个问题</title><link>https://blog.jianghuzaijian.top/blog/java/threadlocal-common-pitfalls-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/threadlocal-common-pitfalls-guide/</guid><description>ThreadLocal 真正难的不是 API 用法，而是线程复用、异步切换和生命周期边界。把最常见的串用、忘记 remove、隐式上下文和内存残留问题放到真实项目里看，才知道坑通常埋在哪。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>ThreadLocal 泄漏为什么常在连接池线程里放大？</title><link>https://blog.jianghuzaijian.top/blog/java/threadlocal-leak-amplified-in-connection-pool-threads-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/threadlocal-leak-amplified-in-connection-pool-threads-guide/</guid><description>ThreadLocal 泄漏一旦叠加线程复用、事务窗口和数据库访问链路，往往不只表现成上下文串用，还会把内存基线、连接持有时长和路由错误一起放大。重点不是背原理，而是看清哪几个条件在现场里同时出现了。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>一个接口的超时、重试、熔断参数，应该怎样整体设计？</title><link>https://blog.jianghuzaijian.top/blog/java/timeout-retry-circuit-breaker-parameter-design-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/timeout-retry-circuit-breaker-parameter-design-guide/</guid><description>超时、重试、熔断如果各自为政，线上很容易从一次慢调用演变成一场放大事故。把调用预算、幂等边界、重试退避、慢调用阈值和熔断恢复条件放回同一套模型里，参数才会真正服务稳定性，而不是互相打架。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>接口超时风暴里，先止血还是先定位？如何判断分界线？</title><link>https://blog.jianghuzaijian.top/blog/java/timeout-storm-stop-bleeding-vs-root-cause-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/timeout-storm-stop-bleeding-vs-root-cause-guide/</guid><description>超时风暴最难的不是知不知道要止血或定位，而是没看清什么时候已经从“还可以取证”变成“再不减压就会整片扩散”。把影响面、资源水位、放大器和可逆动作放到同一条时间线上，分界线通常会比想象中清楚。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>Tomcat busy threads 很高，和业务线程池 backlog 是一回事吗？</title><link>https://blog.jianghuzaijian.top/blog/java/tomcat-busy-threads-high-vs-business-pool-backlog-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/tomcat-busy-threads-high-vs-business-pool-backlog-guide/</guid><description>Tomcat busy threads 高和业务线程池 backlog 长，看起来都像“线程满了”，但指向的并不是同一层问题。更有用的做法是先看请求线程究竟卡在本地阻塞、等待内部任务，还是被连接池和下游一起拖住，再决定该盯入口线程、业务线程池还是更深的等待链。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>值班现场第一眼该开 top、pidstat、ss 还是 iostat？我一般这样选</title><link>https://blog.jianghuzaijian.top/blog/java/top-pidstat-ss-netstat-iostat-when-to-use-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/top-pidstat-ss-netstat-iostat-when-to-use-guide/</guid><description>`top`、`pidstat`、`ss`、`netstat`、`iostat` 真正难的不是会不会敲，而是值班时第一眼先开哪一个。先把问题压到整机、进程、连接还是磁盘这一层，再决定要不要继续往 JVM 或数据库下钻，会比工具对照表更贴近现场。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>流量突增还是代码回归，先沿着时间线、单位成本、实例分布往下拆</title><link>https://blog.jianghuzaijian.top/blog/java/traffic-surge-vs-code-regression-priority-troubleshooting-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/traffic-surge-vs-code-regression-priority-troubleshooting-guide/</guid><description>接口突然变慢时，最容易浪费时间的不是排查，而是太早把问题说成“流量”或“代码”二选一。先把发布时间、流量爬升点、单位请求成本和新老实例分布放到同一条线上，通常更容易拆出触发器和承压能力变化。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>流量切换先于缓存预热怎么排查？发布为什么会触发读放大</title><link>https://blog.jianghuzaijian.top/blog/java/traffic-switch-before-cache-warmup-why-release-causes-read-amplification-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/traffic-switch-before-cache-warmup-why-release-causes-read-amplification-guide/</guid><description>发布后出现读放大，很多时候不是代码突然变重，而是流量已经切到新实例，缓存预热、本地状态和热点对象覆盖却还没跟上。先把顺序和时间线看清，比一开始就翻 diff 更有效。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>分布式锁什么时候该用，什么时候不该用</title><link>https://blog.jianghuzaijian.top/blog/java/when-to-use-distributed-lock/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/when-to-use-distributed-lock/</guid><description>分布式锁不是看到并发就该上的保险丝。真正要分清的是资源互斥、幂等控制、任务抢占还是吞吐治理，再决定它是不是那个值得长期维护的解法。</description><pubDate>Fri, 20 Mar 2026 00:00:00 GMT</pubDate></item><item><title>线上故障排查时，为什么很多人第一步就查错了方向？</title><link>https://blog.jianghuzaijian.top/blog/java/why-people-investigate-wrong-first-step-in-incidents-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/why-people-investigate-wrong-first-step-in-incidents-guide/</guid><description>10:22，网关 504 一片红，群里第一反应是“先查网关”。可把线程队列、active count、重试开关和下游持有时间放回同一条时间线后，先分叉的其实是 `order-service` 内部等待链，而不是最外面的红灯。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item><item><title>写接口变慢，为什么常常不是 SQL 写法差，而是索引太多了？</title><link>https://blog.jianghuzaijian.top/blog/java/write-api-slow-because-indexes-too-many-guide/</link><guid isPermaLink="true">https://blog.jianghuzaijian.top/blog/java/write-api-slow-because-indexes-too-many-guide/</guid><description>写接口越来越慢时，问题常常不在 SQL 语法本身，而在表上不断累加的索引维护成本。把二级索引、页分裂、高频更新字段和事务持锁时间一起看，才更容易解释为什么查询提速了，写路径却被拖重。</description><pubDate>Tue, 24 Mar 2026 00:00:00 GMT</pubDate></item></channel></rss>