技术教程 · 阅读约 9 分钟

用 30 行 Python 让 AI 帮你审完整个 Git Repo——GPT-4o 替代方案对比实测

用 30 行 Python 让 AI 帮你审完整个 Git Repo——GPT-4o 替代方案对比实测

很多人第一次用 AI 做 Code Review,都是这样的:把一个文件粘贴进对话框,等回答,再粘下一个。审完 10 个文件花了 40 分钟,结果发现漏了三个最关键的模块。

这个工作流是错的。

正确的做法是让脚本自动遍历 repo、批量调用 API、把所有结果汇总成一份报告。整个过程你只需要喝完一杯咖啡。下面是完整实现。


思路拆解

1. 用 pathlib 递归扫描 repo,过滤出目标文件类型

2. 每个文件单独发一次 Chat Completion 请求,prompt 要求模型输出结构化问题列表

3. 汇总所有响应,生成 Markdown 报告

模型选择上,这类任务对上下文窗口有要求。测试下来 gpt-4o 和 claude-sonnet-4-5 都能用,后者在理解代码意图上略强,但价格也更高——后面会说怎么省钱。


完整代码


#!/usr/bin/env python3

"""

repo_review.py — 自动化 AI Code Review 工具

依赖: pip install openai

"""



import os

from pathlib import Path

from openai import OpenAI



# ✅ 改这一行就能切换到国内直连、比官方便宜 60% 的 API

client = OpenAI(

    api_key=os.environ.get("WULIANG_API_KEY"),

    base_url="https://api2everything.xyz/v1",

)



REVIEW_PROMPT = """你是一名资深工程师,请对以下代码进行 Code Review。



要求:

1. 指出潜在 Bug(注明行号或函数名)

2. 指出性能问题

3. 指出安全隐患(SQL注入、未校验输入等)

4. 给出 1-2 条最重要的重构建议

5. 用 Markdown 列表格式输出,没有问题的类别直接写"无"



文件路径:{filepath}



{code}


"""



def collect_files(repo_path: str, extensions: list[str]) -> list[Path]:

    root = Path(repo_path)

    files = []

    skip_dirs = {".git", "node_modules", "__pycache__", ".venv", "dist", "build"}

    for ext in extensions:

        for f in root.rglob(f"*.{ext}"):

            if not any(skip in f.parts for skip in skip_dirs):

                files.append(f)

    return sorted(files)



def review_file(filepath: Path, model: str = "gpt-4o") -> dict:

    try:

        code = filepath.read_text(encoding="utf-8", errors="ignore")

    except Exception as e:

        return {"file": str(filepath), "result": f"读取失败: {e}"}



    # 超过 8000 字符只取前后各 4000,避免超出 context

    if len(code) > 8000:

        code = code[:4000] + "\n\n... [中间部分已截断] ...\n\n" + code[-4000:]



    response = client.chat.completions.create(

        model=model,

        messages=[

            {

                "role": "user",

                "content": REVIEW_PROMPT.format(

                    filepath=filepath,

                    code=code,

                ),

            }

        ],

        temperature=0.2,

    )

    return {

        "file": str(filepath),

        "result": response.choices[0].message.content,

        "tokens": response.usage.total_tokens,

    }



def generate_report(reviews: list[dict], output_path: str = "review_report.md"):

    total_tokens = sum(r.get("tokens", 0) for r in reviews)

    lines = [

        "# AI Code Review 报告\n",

        f"共审查 **{len(reviews)}** 个文件 | 消耗 Token:**{total_tokens:,}**\n",

        "---\n",

    ]

    for r in reviews:

        lines.append(f"## `{r['file']}`\n")

        lines.append(r["result"])

        lines.append("\n---\n")



    Path(output_path).write_text("\n".join(lines), encoding="utf-8")

    print(f"✅ 报告已生成:{output_path}(共 {total_tokens:,} tokens)")



def main():

    import argparse



    parser = argparse.ArgumentParser(description="AI 自动 Code Review")

    parser.add_argument("repo", help="repo 根目录路径")

    parser.add_argument("--ext", nargs="+", default=["py", "js", "ts"], help="文件扩展名")

    parser.add_argument("--model", default="gpt-4o", help="模型名称")

    parser.add_argument("--output", default="review_report.md")

    args = parser.parse_args()



    files = collect_files(args.repo, args.ext)

    print(f"📂 找到 {len(files)} 个文件,开始审查...\n")



    reviews = []

    for i, f in enumerate(files, 1):

        print(f"[{i}/{len(files)}] 审查中:{f}")

        result = review_file(f, model=args.model)

        reviews.append(result)



    generate_report(reviews, args.output)



if __name__ == "__main__":

    main()


使用方法


# 安装依赖

pip install openai



# 设置 API Key(在无量Api注册后获取)

export WULIANG_API_KEY="sk-..."



# 审查当前目录下的 Python 和 TypeScript 文件

python repo_review.py ./my_project --ext py ts --model gpt-4o



# 换成 claude-sonnet-4-5 审查(更擅长理解业务逻辑)

python repo_review.py ./my_project --ext py ts --model claude-sonnet-4-5

生成的 review_report.md 长这样:


# AI Code Review 报告

共审查 23 个文件 | 消耗 Token:147,832



---

## `src/auth/jwt.py`



**潜在 Bug**

- `decode_token()` 未处理 `ExpiredSignatureError`,会导致 500



**安全隐患**

- 第 34 行 secret 从环境变量读取但没有默认值保护,生产环境可能泄露...


几个实用细节

模型选择建议

| 场景 | 推荐模型 |

|------|----------|

| 快速过一遍、找明显问题 | gpt-4o-mini |

| 深度审查、理解业务逻辑 | claude-sonnet-4-5 |

| 安全审计(SQL注入/权限等) | gpt-4o |

| 预算有限的大 repo | deepseek-v3(性价比极高) |

Token 消耗估算:一个中型 Python 项目(约 50 个文件)用 gpt-4o 审下来大概消耗 20-40 万 token。官方价格大约 $1-2,用国内转发服务能省 60% 左右,审个 repo 成本降到 $0.4 以内。

并发加速:如果文件多,可以用 concurrent.futures.ThreadPoolExecutor 并行发请求,速度提升 5-10x。但注意各家 API 的 RPM 限制,并发数建议控制在 5 以内。


关于 API 选择

代码里 base_url 换成 https://api2everything.xyz/v1 是因为我现在用的是无量Api——国内直连,不需要梯子,OpenAI / Claude / Gemini / DeepSeek 300+ 模型都在一个 key 里。注册送 ¥1 余额可以直接跑上面这个脚本试试效果。余额永久有效,不用担心过期。

对于这种批量调用场景,比官方便宜 60% 这个差价是实实在在的。


如果你在跑的过程中遇到某个文件的 review 质量不好(比如模型乱改 prompt 格式),欢迎评论区贴出来,我们一起调 prompt。

觉得有用的话点个赞,后续打算写「用同样方式做自动化单测生成」,感兴趣可以关注。