一、引言
提到程序员用 AI,很多人第一反应就是"写代码"。但在日常开发中,AI 的价值远不止于此。
今天我要分享 5 个程序员用 AI 的真实场景,每个场景都配有实际案例和可复用的 Prompt 模板,帮你真正把 AI 融入工作流。
二、场景一:Code Review 预审
2.1 痛点
- PR 中隐藏的空指针、线程安全问题,人工难以全部发现
- 团队代码规范难以统一执行
- Code Review 耗时太长,影响交付效率
2.2 实战案例
代码片段(有问题):
public class OrderService {
private final OrderRepository orderRepository;
private final PaymentService paymentService;
public OrderService(OrderRepository orderRepository,
PaymentService paymentService) {
this.orderRepository = orderRepository;
this.paymentService = paymentService;
}
public void processOrder(Long orderId) {
Order order = orderRepository.findById(orderId);
if (order.getStatus() == OrderStatus.PENDING) { // 潜在 NPE
paymentService.charge(order.getAmount()); // 潜在 NPE
order.setStatus(OrderStatus.PAID);
orderRepository.save(order);
}
}
}
AI Prompt:
你是一位资深 Java 后端工程师,正在进行代码审查。
请分析以下代码中的潜在问题,包括:
1. 空指针异常风险
2. 线程安全问题
3. SQL 注入风险
4. 代码规范问题
5. 性能问题
代码如下:
[粘贴代码]
请列出所有问题,并给出修复建议。
AI 输出:
发现以下问题:
1. **空指针异常风险**(高优先级)
- `orderRepository.findById(orderId)` 可能返回 null
- `order.getStatus()` 和 `order.getAmount()` 在 order 为 null 时会抛出 NPE
- 修复建议:添加 null 检查或使用 Optional
2. **缺少事务管理**(中优先级)
- `paymentService.charge()` 和 `orderRepository.save()` 在同一方法中执行,但没有事务注解
- 如果 charge 成功但 save 失败,会导致数据不一致
- 修复建议:添加 `@Transactional` 注解
3. **缺少异常处理**(中优先级)
- `paymentService.charge()` 可能抛出 PaymentException
- 缺少 try-catch 或全局异常处理
- 修复建议:添加异常捕获并记录日志
修复后的代码:
@Transactional
public void processOrder(Long orderId) {
Order order = orderRepository.findById(orderId);
if (order != null && order.getStatus() == OrderStatus.PENDING) {
try {
paymentService.charge(order.getAmount());
order.setStatus(OrderStatus.PAID);
orderRepository.save(order);
} catch (PaymentException e) {
log.error("支付失败,订单ID: {}", orderId, e);
throw new OrderProcessingException("支付失败", e);
}
}
}
2.3 可复用 Prompt
你是一位资深 {语言/框架} 工程师,正在进行代码审查。
请分析以下代码中的潜在问题,包括:
1. 空指针异常风险
2. 线程安全问题
3. SQL 注入风险
4. 代码规范问题
5. 性能问题
代码如下:
{代码片段}
请列出所有问题,并给出修复建议。
三、场景二:技术方案评估
3.1 痛点
- 自己设计的方案,往往难以发现思维盲区
- 团队评审时,大家都在赶进度,评审流于形式
- 新技术选型时,缺乏全面的对比分析
3.2 实战案例
技术方案(分布式锁设计):
方案:基于 Redis 实现分布式锁
核心设计:
1. 使用 Redis SETNX 命令获取锁
2. 设置锁的过期时间为 30 秒
3. 如果业务执行时间超过 30 秒,锁会自动释放
4. 锁释放时使用 DEL 命令删除锁键
使用场景:
- 库存扣减
- 订单去重
- 定时任务幂等
AI Prompt:
你是一位架构师,请评估以下技术方案的优缺点,找出潜在问题和改进建议。
方案描述:
{方案内容}
请从以下维度评估:
1. 正确性:是否存在竞态条件、死锁等问题
2. 可靠性:故障场景下的表现
3. 性能:吞吐量、延迟等指标
4. 可扩展性:是否支持集群、扩容等
5. 维护性:代码复杂度、运维成本
给出具体的改进建议。
AI 输出:
方案评估:
**优点**:
1. 实现简单,依赖 Redis 即可
2. SETNX 原子性保证了锁的互斥性
3. 过期时间避免了死锁
**潜在问题**:
1. **锁过期问题**(严重)
- 如果业务执行时间超过 30 秒,锁会自动释放
- 导致多个线程同时执行临界区代码
- 解决方案:锁续期(Redisson 的看门狗机制)
2. **锁释放问题**(严重)
- 使用 DEL 命令释放锁,无法判断锁是否属于当前线程
- 线程 A 的锁过期后,线程 B 获取锁,线程 A 执行完成后可能误删线程 B 的锁
- 解决方案:使用 Lua 脚本,释放锁时验证锁的持有者
3. **单点故障**(中等)
- 如果 Redis 主节点宕机,锁信息可能丢失
- 解决方案:使用 Redis 集群或哨兵模式
4. **锁重入问题**(中等)
- 当前方案不支持锁重入
- 如果同一线程多次获取锁,会导致死锁
- 解决方案:记录锁的持有者和重入次数
**改进方案**:
```lua
-- 获取锁
SET lock:order:123 "thread-uuid" NX EX 30
-- 释放锁(Lua 脚本)
if redis.call("get", KEYS[1]) == ARGV[1] then
return redis.call("del", KEYS[1])
else
return 0
end
建议使用 Redisson 框架,内置了完整的分布式锁实现。
### 3.3 可复用 Prompt
你是一位架构师,请评估以下技术方案的优缺点,找出潜在问题和改进建议。
方案描述:
{方案内容}
请从以下维度评估:
- 正确性:是否存在竞态条件、死锁等问题
- 可靠性:故障场景下的表现
- 性能:吞吐量、延迟等指标
- 可扩展性:是否支持集群、扩容等
- 维护性:代码复杂度、运维成本
给出具体的改进建议。
---
## 四、场景三:日志分析
### 4.1 痛点
- 异常堆栈信息冗长,难以快速定位根因
- 日志文件太大,搜索效率低
- 缺乏专业知识,无法解读某些异常
### 4.2 实战案例
**异常堆栈**:
2024-01-15 10:30:00.123 ERROR [order-service] [http-nio-8080-exec-5] c.e.o.controller.OrderController - 订单处理失败
java.util.concurrent.TimeoutException: null
at java.util.concurrent.CompletableFuture.timedGet(CompletableFuture.java:1771)
at java.util.concurrent.CompletableFuture.get(CompletableFuture.java:1915)
at com.example.order.service.OrderService.processOrder(OrderService.java:45)
at com.example.order.controller.OrderController.createOrder(OrderController.java:28)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
...
Caused by: java.sql.SQLTimeoutException: Statement cancelled due to timeout or client request
at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:129)
at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:97)
at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:89)
at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:63)
at com.mysql.cj.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:1986)
at com.mysql.cj.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:1827)
at com.mysql.cj.jdbc.PreparedStatement.executeQuery(PreparedStatement.java:1924)
at com.zaxxer.hikari.pool.ProxyPreparedStatement.executeQuery(ProxyPreparedStatement.java:52)
at com.zaxxer.hikari.pool.HikariProxyPreparedStatement.executeQuery(HikariProxyPreparedStatement.java)
at com.example.order.repository.OrderRepository.findById(OrderRepository.java:32)
... 58 common frames omitted
**AI Prompt**:
你是一位资深后端工程师,请分析以下异常堆栈,找出根因并给出修复建议。
异常堆栈:
{堆栈信息}
请回答以下问题:
- 异常的根因是什么?
- 可能的触发条件有哪些?
- 修复方案是什么?
- 如何预防此类问题再次发生?
**AI 输出**:
异常分析:
1. 根因分析
这是一个数据库查询超时问题,导致了上层的 CompletableFuture.get() 超时。
调用链分析:
OrderController.createOrder()→ 发起订单创建请求OrderService.processOrder()→ 调用CompletableFuture.get()等待异步结果OrderRepository.findById()→ 执行 SQL 查询- MySQL 返回
SQLTimeoutException→ 查询超时
2. 触发条件
- 数据库负载过高(CPU、内存、IO)
- 查询语句没有走索引,导致全表扫描
- 数据库连接池耗尽,等待连接超时
CompletableFuture.get()的超时时间设置过短
3. 修复方案
// 方案1:优化查询超时设置
@Transactional
public Order processOrder(Long orderId) {
// 设置合理的超时时间
return CompletableFuture.supplyAsync(() -> {
return orderRepository.findById(orderId);
}).get(60, TimeUnit.SECONDS); // 延长超时时间
}
// 方案2:优化 SQL 查询
// 确保 order_id 字段有索引
// CREATE INDEX idx_order_id ON orders(order_id);
// 方案3:添加重试机制
public Order processOrder(Long orderId) {
return RetryTemplate.builder()
.maxAttempts(3)
.retryOn(SQLTimeoutException.class)
.build()
.execute(ctx -> orderRepository.findById(orderId));
}
4. 预防措施
- 添加慢 SQL 监控和告警
- 设置数据库查询超时参数
- 使用连接池监控,及时发现连接泄漏
- 定期审查索引使用情况
- 添加熔断机制,保护数据库
### 4.3 可复用 Prompt
你是一位资深后端工程师,请分析以下异常堆栈,找出根因并给出修复建议。
异常堆栈:
{堆栈信息}
请回答以下问题:
- 异常的根因是什么?
- 可能的触发条件有哪些?
- 修复方案是什么?
- 如何预防此类问题再次发生?
---
## 五、场景四:API 文档生成
### 5.1 痛点
- 手写 API 文档耗时费力,容易出错
- 代码和文档不同步,文档过期
- 文档格式不统一,阅读体验差
### 5.2 实战案例
**Swagger JSON**:
```json
{
"openapi": "3.0.1",
"info": {
"title": "订单服务 API",
"version": "1.0.0"
},
"paths": {
"/api/orders": {
"post": {
"summary": "创建订单",
"description": "创建一个新的订单",
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/CreateOrderRequest"
}
}
}
},
"responses": {
"200": {
"description": "创建成功",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/OrderResponse"
}
}
}
},
"400": {
"description": "请求参数错误"
}
}
}
},
"/api/orders/{orderId}": {
"get": {
"summary": "查询订单详情",
"description": "根据订单ID查询订单详情",
"parameters": [
{
"name": "orderId",
"in": "path",
"required": true,
"schema": {
"type": "string",
"format": "uuid"
}
}
],
"responses": {
"200": {
"description": "查询成功"
},
"404": {
"description": "订单不存在"
}
}
}
}
},
"components": {
"schemas": {
"CreateOrderRequest": {
"type": "object",
"properties": {
"productId": {
"type": "string",
"format": "uuid"
},
"quantity": {
"type": "integer",
"minimum": 1
},
"userId": {
"type": "string",
"format": "uuid"
}
},
"required": ["productId", "quantity", "userId"]
},
"OrderResponse": {
"type": "object",
"properties": {
"orderId": {
"type": "string",
"format": "uuid"
},
"productId": {
"type": "string",
"format": "uuid"
},
"quantity": {
"type": "integer"
},
"status": {
"type": "string",
"enum": ["PENDING", "PAID", "SHIPPED", "COMPLETED"]
},
"createdAt": {
"type": "string",
"format": "date-time"
}
}
}
}
}
}
AI Prompt:
你是一位技术文档专家,请根据以下 Swagger JSON 生成一份产品级的 API 文档。
Swagger JSON:
{Swagger JSON}
要求:
1. 按 API 分组组织文档
2. 每个 API 包含:接口描述、请求参数、响应示例、错误码说明
3. 使用 Markdown 格式输出
4. 语言简洁明了,适合前端和测试人员阅读
AI 输出:
# 订单服务 API 文档
## 概述
订单服务提供订单的创建、查询、更新等功能。
**基础路径**:`/api/orders`
## 接口列表
### 1. 创建订单
**POST** `/api/orders`
创建一个新的订单。
**请求体**:
| 字段 | 类型 | 必填 | 说明 |
|------|------|------|------|
| productId | string (UUID) | 是 | 商品ID |
| quantity | integer | 是 | 购买数量(最小为1) |
| userId | string (UUID) | 是 | 用户ID |
**请求示例**:
```json
{
"productId": "550e8400-e29b-41d4-a716-446655440000",
"quantity": 2,
"userId": "123e4567-e89b-12d3-a456-426614174000"
}
成功响应(200):
| 字段 | 类型 | 说明 |
|---|---|---|
| orderId | string (UUID) | 订单ID |
| productId | string (UUID) | 商品ID |
| quantity | integer | 购买数量 |
| status | string | 订单状态(PENDING/PAID/SHIPPED/COMPLETED) |
| createdAt | string (datetime) | 创建时间 |
成功响应示例:
{
"orderId": "987e6543-e21b-43d2-c678-876543210987",
"productId": "550e8400-e29b-41d4-a716-446655440000",
"quantity": 2,
"status": "PENDING",
"createdAt": "2024-01-15T10:30:00Z"
}
错误响应(400):
{
"code": 400,
"message": "请求参数错误",
"details": ["quantity 必须大于0"]
}
2. 查询订单详情
GET /api/orders/{orderId}
根据订单ID查询订单详情。
路径参数:
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
| orderId | string (UUID) | 是 | 订单ID |
请求示例:
GET /api/orders/987e6543-e21b-43d2-c678-876543210987
成功响应(200):
同创建订单成功响应。
错误响应(404):
{
"code": 404,
"message": "订单不存在"
}
### 5.3 可复用 Prompt
你是一位技术文档专家,请根据以下 Swagger JSON 生成一份产品级的 API 文档。
Swagger JSON:
{Swagger JSON}
要求:
- 按 API 分组组织文档
- 每个 API 包含:接口描述、请求参数、响应示例、错误码说明
- 使用 Markdown 格式输出
- 语言简洁明了,适合前端和测试人员阅读
---
## 六、场景五:技术选型参谋
### 6.1 痛点
- 面对多个技术方案,难以做出客观决策
- 缺乏全面的对比分析,容易遗漏重要因素
- 个人经验有限,无法覆盖所有技术细节
### 6.2 实战案例
**技术选型问题**:
场景:需要实现分布式锁,备选方案:
- Redis 分布式锁(基于 SETNX + Lua)
- ZooKeeper 分布式锁(基于临时节点)
请对比这两种方案,帮我做出选型决策。
**AI Prompt**:
你是一位架构师,请对比以下两种技术方案,帮助我做出选型决策。
方案 A:Redis 分布式锁(基于 SETNX + Lua)
方案 B:ZooKeeper 分布式锁(基于临时节点)
请从以下维度对比:
- 正确性:是否存在竞态条件
- 可靠性:故障场景下的表现
- 性能:吞吐量、延迟
- 可用性:CAP 特性
- 复杂度:实现难度、运维成本
- 适用场景:哪些场景更适合
给出选型建议和理由。
**AI 输出**:
Redis 分布式锁 vs ZooKeeper 分布式锁
对比表
| 维度 | Redis 分布式锁 | ZooKeeper 分布式锁 |
|---|---|---|
| 正确性 | 基本正确,需处理锁续期和误删问题 | 天然正确,临时节点自动释放 |
| 可靠性 | 主从切换时可能丢失锁 | 一致性保证,不会丢失锁 |
| 性能 | 高吞吐量(10万+ QPS) | 中等吞吐量(万级 QPS) |
| 可用性 | AP 模型,优先保证可用性 | CP 模型,优先保证一致性 |
| 复杂度 | 实现简单,需处理边缘情况 | 实现复杂,需处理会话超时 |
| 运维成本 | 低,Redis 已是基础设施 | 高,需维护 ZooKeeper 集群 |
| 锁续期 | 需要手动实现(看门狗) | 自动续期(会话心跳) |
详细分析
1. 正确性
- Redis:存在锁过期问题,如果业务执行时间超过锁的过期时间,会导致多个线程同时执行。需要额外实现锁续期机制。
- ZooKeeper:临时节点在客户端会话断开时自动删除,不存在锁过期问题,天然保证互斥性。
2. 可靠性
- Redis:主从架构下,如果主节点宕机,从节点可能还未同步锁信息,导致锁丢失。
- ZooKeeper:基于 Zab 协议,保证数据一致性,不会出现锁丢失。
3. 性能
- Redis:纯内存操作,吞吐量高,延迟低。
- ZooKeeper:需要持久化到磁盘,吞吐量较低,延迟较高。
4. 可用性
- Redis:AP 模型,优先保证可用性,允许一定的数据不一致。
- ZooKeeper:CP 模型,优先保证一致性,集群过半节点可用才能提供服务。
选型建议
选型决策树:
┌─────────────────────────────────────────┐
│ │
│ 需要高吞吐量? │
│ │ │
│ ├── 是 → Redis(库存扣减、热点 Key) │
│ │ │
│ └── 否 → 需要强一致性? │
│ │ │
│ ├── 是 → ZooKeeper(分布式协调) │
│ │ │
│ └── 否 → Redis(普通业务场景) │
│ │
└─────────────────────────────────────────┘
推荐方案:
| 场景 | 推荐方案 | 理由 |
|---|---|---|
| 库存扣减、热点 Key | Redis | 吞吐量高,性能好 |
| 分布式协调、选主 | ZooKeeper | 一致性强,可靠性高 |
| 普通业务场景 | Redis | 实现简单,运维成本低 |
| 金融级交易 | ZooKeeper | 强一致性保证 |
最终建议:
- 如果你的场景对性能要求高,且能接受一定的不一致风险,选择 Redis。
- 如果你的场景对一致性要求高,且对性能要求不高,选择 ZooKeeper。
- 如果不确定,可以先使用 Redis,遇到问题再考虑迁移到 ZooKeeper。
### 6.3 可复用 Prompt
你是一位架构师,请对比以下两种技术方案,帮助我做出选型决策。
方案 A:{方案A描述}
方案 B:{方案B描述}
请从以下维度对比:
- 正确性:是否存在竞态条件
- 可靠性:故障场景下的表现
- 性能:吞吐量、延迟
- 可用性:CAP 特性
- 复杂度:实现难度、运维成本
- 适用场景:哪些场景更适合
给出选型建议和理由。
---
## 七、数据安全与局限性
### 7.1 数据安全
⚠️ 重要提醒:
-
不要粘贴敏感信息到 AI:
- 数据库连接信息
- API Key、密码
- 用户隐私数据
- 公司内部代码
-
敏感信息处理:
- 使用占位符替换敏感值
- 脱敏处理(如将真实 ID 替换为示例 ID)
- 使用企业级 AI 服务(如 Azure OpenAI、阿里云通义千问)
-
使用私有化部署:
- 对于核心业务代码,建议使用私有化部署的 AI 服务
- 确保数据不会离开公司网络
### 7.2 AI 的局限性
⚠️ AI 不是万能的:
-
可能产生幻觉:
- AI 可能编造不存在的代码或解决方案
- 需要人工验证 AI 的输出
-
缺乏上下文:
- AI 无法了解你的业务上下文
- 需要提供足够的背景信息
-
版本差异:
- AI 训练数据可能不是最新的
- 需要确认解决方案是否适用于当前版本
-
安全风险:
- 不要直接复制 AI 生成的代码到生产环境
- 需要进行代码审查和安全测试
### 7.3 最佳实践
✅ 使用 AI 的正确姿势:
-
提供足够的上下文:
- 告诉 AI 你的技术栈、框架版本
- 描述你的业务场景和约束条件
-
验证 AI 的输出:
- 运行代码测试
- 进行代码审查
- 确认解决方案的正确性
-
迭代优化:
- 如果 AI 的回答不符合预期,提供更多信息
- 使用更精确的 Prompt 引导 AI
-
结合人类智慧:
- AI 是辅助工具,不是替代人类
- 重要决策需要人类最终确认
---
## 八、总结
### 8.1 5 个场景回顾
| 场景 | 核心价值 | 适用时机 |
|------|---------|---------|
| **Code Review 预审** | 发现人工难以察觉的问题 | PR 提交前 |
| **技术方案评估** | 发现思维盲区,全面评估方案 | 方案设计后 |
| **日志分析** | 快速定位根因,给出修复建议 | 线上故障排查 |
| **API 文档生成** | 自动生成产品级文档 | API 开发完成后 |
| **技术选型参谋** | 客观对比方案,辅助决策 | 技术选型时 |
### 8.2 场景优先级
优先级排序:
┌─────────────────────────────────────────┐
│ │
│ 高优先级 │
│ ├── 日志分析(紧急问题快速定位) │
│ ├── Code Review 预审(质量保障) │
│ │
│ 中优先级 │
│ ├── 技术方案评估(架构质量) │
│ ├── API 文档生成(效率提升) │
│ │
│ 低优先级 │
│ ├── 技术选型参谋(决策辅助) │
│ │
└─────────────────────────────────────────┘
### 8.3 核心要点
使用 AI 的核心要点:
- 提供具体的输入(代码、日志、方案)
- 使用精确的 Prompt 模板
- 验证 AI 的输出
- 保护敏感数据
- 结合人类智慧
> 💡 **互动话题**:你在工作中最常用 AI 的哪个场景?有没有什么独门技巧?欢迎在评论区分享!
