Java 面试实录:Spring Boot + Kafka + Redis + Kubernetes,燕双非在互联网大厂的“翻车”现场
Java 面试实录Spring Boot Kafka Redis Kubernetes燕双非在互联网大厂的“翻车”现场场景互联网大厂 Java 求职面试。人物严肃的面试官和一位自带喜剧效果的水货程序员燕双非。业务背景一家电商平台在大促期间既要承接订单洪峰又要处理支付、库存、风控、通知等链路问题还要保证系统可观测、可扩展、可回滚。第一轮基础能力与订单链路面试官我们先从最基本的开始。你做过电商订单系统吗如果下单接口用了 Spring Boot你会怎么设计接口层、服务层和持久层的分工燕双非做过当然做过。接口层负责接收参数服务层负责“业务”持久层负责“存起来”。Spring Boot 就是帮我们把这些层自动装配好写起来比较快。面试官嗯方向是对的。那如果下单后要写订单表、扣库存、发消息通知你会怎么保证主流程稳定燕双非我会先把订单落库然后库存扣减最后发 Kafka 消息。这样异步解耦系统会更快。至于失败嘛……重试一下就行了。面试官重试是手段不是方案。那如果消息重复消费了怎么办燕双非那就……加个唯一索引或者消费端判断一下订单状态已处理就直接跳过。面试官这就比“重试一下”靠谱多了。继续。订单详情页你会怎么做缓存Redis 适合放什么什么又不适合放燕双非Redis 适合放热点订单详情、商品库存、用户会话这种读多写少的数据。不太适合放特别大的对象或者强一致要求特别高的内容。面试官不错至少知道边界。那缓存和数据库不一致时怎么办燕双非一般可以先更新数据库再删除缓存或者用延迟双删。反正核心就是尽量避免读到旧数据。面试官可以至少知道“先写库再删缓存”的基本思路。第二轮风控、消息与安全面试官现在进入支付风控场景。支付成功后风控系统要实时判定这笔订单是否可疑。你会怎么做链路设计燕双非支付成功后先发 Kafka 事件风控服务消费消息然后根据用户、设备、地址、下单频率做规则判断。如果有风险就打标或者拦截后续动作。面试官很好开始像个做过系统的人了。那 Kafka 的分区你怎么设计燕双非如果想保证同一个订单的消息有序可以按 orderId 做分区键。这样同一订单的消息会落到同一个分区里消费者处理顺序更容易保证。面试官对。那如果风控规则很多如何避免规则散落在代码里燕双非可以把规则抽象成配置化规则引擎或者至少做成策略模式。这样后面规则变更不用频繁改代码。面试官不错。那说说 Spring Security 在这个场景里的作用。燕双非Spring Security 可以做登录认证、接口鉴权、权限控制比如只有支付服务能调用风控内部接口普通用户不能直接访问管理端接口。还能配合 JWT 做无状态认证。面试官JWT 的优点和风险各是什么燕双非优点是无状态、适合分布式系统风险是令牌一旦签发撤销比较麻烦所以需要配合过期时间、黑名单或者刷新机制。面试官回答得还行。最后一个问题接口暴露给外部合作方时你怎么保证幂等和安全燕双非幂等可以用业务唯一流水号、请求幂等表、状态机校验。安全方面可以做签名校验、时间戳、防重放、IP 白名单、限流再加上 OAuth2 或者 JWT 鉴权。面试官这轮比上一轮成熟多了说明不是完全没做过事。第三轮高并发、可观测性与云原生面试官大促来了订单量暴涨。你说说如何做限流、熔断和降级燕双非可以用 Resilience4j 做限流和熔断。比如库存服务响应慢就熔断一段时间直接返回兜底结果支付回调太多时可以限流保护核心链路。面试官嗯这个方向对。那你怎么判断系统哪里慢燕双非要做监控和链路追踪。比如用 Micrometer 暴露指标Prometheus 抓取Grafana 看图再配合 Jaeger 或 Zipkin 做链路追踪定位慢接口、慢 SQL、慢消息消费。面试官很好。那如果数据库扛不住除了加缓存还有什么办法燕双非可以读写分离、分库分表、异步化、批处理还可以把非核心查询迁到 Elasticsearch 做搜索或者用 R2DBC 处理一些高并发的响应式场景。面试官说到高并发Spring WebFlux 和传统 Spring MVC 的区别你怎么理解燕双非Spring MVC 是阻塞式的适合传统同步调用WebFlux 是响应式的适合高并发 I/O 场景。不过如果团队和业务不适合盲目上 WebFlux 也不一定赚。面试官这个判断很重要。最后容器化部署你会关注什么燕双非会关注 JVM 参数、健康检查、资源限制、滚动发布、配置中心、日志采集还有 Pod 的启动探针和存活探针。上线后如果出问题至少能快速回滚。面试官行今天先到这儿。你回家等通知吧。面试题详细解析1. Spring Boot 下订单系统的分层设计电商下单链路通常分为接口层、服务层、持久层。接口层负责参数校验、鉴权和请求适配服务层负责编排业务流程例如创建订单、校验库存、计算优惠、调用支付持久层负责数据库读写。这样做的好处是职责清晰便于测试和扩展。2. 订单落库、扣库存、发消息的事务一致性在分布式场景中单体事务很难覆盖所有步骤。常见做法是本地事务保证订单和业务状态先落库再通过消息队列做异步通知配合消息幂等、补偿机制和状态机设计降低最终一致性风险。可以使用 Kafka 作为事件总线确保订单事件流转可追踪。3. Kafka 分区键与有序性Kafka 的分区决定了消息在 broker 上的分布。若希望同一业务对象有序处理比如同一订单的状态变更消息应以 orderId 作为分区键。这样同一订单消息会进入同一分区消费者按分区顺序消费从而保证局部有序。4. 消息重复消费与幂等设计消息队列通常至少一次投递因此重复消费必须考虑。常见方案包括业务唯一键去重、消费日志表、状态机校验、数据库唯一索引等。以订单支付通知为例可以在订单状态已完成时直接忽略重复事件避免重复发货或重复记账。5. Redis 缓存的适用场景Redis 适合热点数据、读多写少、允许短暂不一致的数据比如商品详情、库存预估、验证码、用户会话。对于特别大、结构复杂或强一致要求高的数据不建议直接缓存为大对象。缓存更新时一般采用先写数据库再删缓存减少脏读。6. 缓存与数据库一致性常见模式是 Cache Aside读时先查缓存再查数据库并回填写时先更新数据库再删除缓存。延迟双删可以进一步降低并发下旧缓存被回填的概率但仍需结合业务容忍度设计。对于强一致场景缓存并不能单独解决问题应该依赖事务、锁或状态校验。7. 风控链路中的规则抽象风控规则建议不要散落在 if-else 中而应配置化或策略化。可以将黑名单、设备指纹、地理位置异常、短时间高频下单等规则拆分为独立策略统一编排执行。这样便于迭代、灰度和回溯。8. Spring Security、JWT 与外部接口安全Spring Security 适合实现认证、授权、方法级控制和过滤器链。JWT 适合无状态认证但要注意过期、续签和撤销问题。对外接口还应增加签名、时间戳、防重放、限流和 IP 白名单不能只靠“登录态”一个手段。9. 幂等设计为什么重要支付回调、消息消费、任务重试都可能导致同一个请求多次到达。幂等设计的核心是在重复请求下系统最终状态不变。常用做法有业务唯一单号、状态机校验、幂等表、去重 token 等。10. Resilience4j 在高并发系统中的价值在高峰期系统要优先保护核心链路。Resilience4j 可以做限流、熔断、隔离和重试控制。库存服务异常时快速熔断可避免请求堆积拖垮整个系统对非核心功能可返回降级结果提升整体可用性。11. Micrometer、Prometheus、Grafana 的组合Micrometer 负责统一指标采集Prometheus 定时拉取并存储时序数据Grafana 用于可视化展示。通过 QPS、响应时间、错误率、JVM GC、线程池队列长度等指标可以快速判断性能瓶颈。12. Jaeger/Zipkin 的链路追踪在微服务体系中请求会跨多个服务调用。链路追踪可以把一次请求的完整路径串联起来定位慢在数据库、RPC、消息消费还是外部接口。尤其在大促排障时链路追踪比单点日志更有效。13. Spring WebFlux 与 Spring MVC 的选择Spring MVC 适合大多数传统企业业务开发简单、生态成熟。WebFlux 适合 I/O 密集、并发较高、链路响应式改造较完整的场景。不是所有项目都适合 WebFlux团队经验和上下游依赖才是关键。14. Kubernetes 部署时关注什么容器化部署不仅是“能跑起来”还要关注资源限制、健康检查、滚动发布、配置注入、日志收集、弹性扩缩容与回滚策略。JVM 也要根据容器资源重新评估堆大小、GC 策略和启动参数避免容器内存不足导致 OOM。感谢阅读希望这篇文章能帮助你在 Java 面试中更有思路也能把技术点真正落到业务场景里祝大家都能顺利拿到理想 offer。