ECC Kiro django-reviewer 实战指南:面向 Django 生产级质量的 AI 代码评审 Agent(ORM、DRF、迁移与安全检查)
ECC(Everything Claude Code)仓库在 .kiro/agents/ 目录下提供了一套可直接安装到 Kiro 的 AI Agent 配置,其中 django-reviewer 是专门针对 Django 项目的代码评审专家。本文以该 Agent 的定义文件为核心,完整拆解它的触发流程、按严重级别分层的评审清单(安全、ORM 正确性、迁移安全、DRF 模式、性能、代码质量与测试缺口)、诊断命令与批准标准,并结合仓库中配套的 django-patterns 与 django-security 技能说明每一项检查背后的正确写法。读完本文,你可以将这套 Django 评审流程安装到自己的 Kiro 项目,并理解每一条检查项对应的手动排查方法。
django-reviewer 在 ECC Kiro 体系中的定位
ECC 的 .kiro/ 目录是一套可分发的 Kiro 工作流包:.kiro/README.md 中给出了组件清单——33 个 Agent(JSON 与 MD 双格式)、43 个 Skill、22 个 Steering 文件、13 个 Hook 与 2 个脚本,可通过安装脚本一次性注入任意 Kiro 项目:
# 进入 .kiro 目录
cd .kiro
# 安装到指定项目
./install.sh /path/to/your/project
# 或安装到当前目录
./install.sh
# 或全局安装(作用于所有 Kiro 项目)
./install.sh ~
从 install.sh 源码看,安装器对 agents、skills、steering、hooks、scripts、settings 六个子目录做“非破坏性拷贝”:仅当目标文件不存在时才复制,因此你安装后对 Agent 提示词的任何定制都不会被重装覆盖。
在 Agent 清单中,.kiro/README.md 将 django-reviewer 描述为 “Django code reviewer. ORM patterns, DRF, migrations, and Django security.”。它的使用方式有两种(来自该 README):
- IDE 中:在 Kiro 会话里输入
/django-reviewer显式调用; - CLI 中:
/agent swap切换到该 Agent,或直接kiro-cli --agent django-reviewer启动。
同一仓库还在根目录维护了一个更长的 agents/django-reviewer.md(面向 Claude Code 等其他 harness),两者评审清单同源,Kiro 版(.kiro/agents/django-reviewer.md)是本文主体。
Agent 配置文件:frontmatter 与工具权限
.kiro/agents/django-reviewer.md 的 YAML frontmatter 定义了 Agent 的基本契约:
---
name: django-reviewer
description: Expert Django code reviewer specializing in ORM correctness, DRF patterns, migration safety, security misconfigurations, and production-grade Django practices. Use for all Django code changes. MUST BE USED for Django projects.
allowedTools:
- read
- shell
---
- description:向 Agent 调度层说明“何时使用”——所有 Django 代码变更都必须(MUST BE USED)经过该 Agent 评审;
- allowedTools:仅开放
read(读文件)与shell(执行git diff、manage.py check等诊断命令)。这意味着该 Agent 是“只评审、不代改”的角色,评审输出是问题清单而非自动补丁。
同目录下的 django-reviewer.json 是同一 Agent 的 CLI 格式声明,其中 "tools": ["@builtin"]、"allowedTools": ["fs_read", "shell"],并且把整份 Markdown 提示词内嵌在 prompt 字段中——Kiro CLI 通过 /agent swap 加载 JSON,IDE 则读取 Markdown,双格式保证了两端行为一致。
Agent 开头有一段重要约束:
Note: This agent focuses on Django-specific concerns. Ensure
python-reviewerhas been invoked for general Python quality checks before or after this review.
即 django-reviewer 只负责 Django 框架层面的问题(ORM、DRF、迁移、Django 安全配置),通用的 Python 质量检查(PEP 8、类型标注、异常处理、并发等)由 python-reviewer 负责。两个 Agent 的“当被调用时”流程几乎一致(都是先跑 git diff -- '*.py' 再看改动文件),形成“通用 Python 检查 + 框架专项检查”的双层评审。
评审触发流程:被调用时的 7 个标准步骤
文档的 “When invoked” 一节规定了 Agent 每次被调起后的固定动作序列:
- 执行
git diff -- '*.py',查看最近改动的 Python 文件; - 若存在 Django 项目,执行
python manage.py check(Django 系统检查); - 执行
python manage.py makemigrations --check,检测是否有模型改动尚未生成迁移; - 检查迁移文件中的三类高危点:
RunPython操作缺少reverse_code(迁移无法回滚);- 对大表的数据迁移未做分批处理(batching);
- 非外键的过滤列缺少
db_index(ForeignKey 字段自带索引,无需重复标注);
- 若环境可用,执行
ruff check .与mypy .; - 聚焦在改动的
.py文件及与之相关的迁移文件; - 立即开始评审。
这套流程的设计意图很清晰:先用确定性工具(Django 系统检查、迁移检查、linter、类型检查器)建立客观基线,再由 LLM 做语义级审查,避免评审 Agent 在“漏迁移”“缺索引”这类可机器判定的问题上浪费判断力。其中 makemigrations --check 尤其关键——它只检查“模型与迁移是否一致”而不生成文件,是 CI 里防止“改了模型忘记生成迁移”这一经典事故的常用手段。
评审优先级清单(Review Priorities)
Agent 的评审标准按 CRITICAL / HIGH / MEDIUM 三级组织。以下完整继承原文档的每一条目,并按级别展开讲解。
CRITICAL — 安全
这一级别的任何一条命中都足以阻断合并:
| 检查项 | 说明与正确做法 |
|---|---|
| SQL 注入 | 用 f-string 或 % 格式化拼接原始 SQL。必须使用 %s 参数占位或直接用 ORM |
对用户输入使用 mark_safe |
未先显式 escape() 就标记为安全字符串,等价于关闭 Django 的 XSS 自动转义 |
| 无正当理由的 CSRF 豁免 | 非 webhook 视图上使用 @csrf_exempt |
生产环境 DEBUG = True |
会向访问者泄露完整堆栈与配置 |
硬编码 SECRET_KEY |
必须从环境变量读取 |
DRF 视图缺少 permission_classes |
会回落到全局默认权限——必须确认这是有意为之 |
| 文件上传未校验扩展名/大小 | 存在路径穿越风险 |
这些检查项在 django-security 技能中有对应的正反代码示例。例如 SQL 注入一栏:
# 危险:直接插值用户输入
User.objects.raw(f'SELECT * FROM users WHERE username = {username}')
# 正确:参数化
User.objects.raw('SELECT * FROM users WHERE username = %s', [username])
# 正确:优先使用 ORM,参数自动转义
User.objects.filter(email__iexact=email)
XSS 防护一栏则要求“先转义、再标记安全”,或使用 format_html:
from django.utils.safestring import mark_safe
from django.utils.html import escape, format_html
# 危险
mark_safe(user_input)
# 正确
mark_safe(escape(user_input))
format_html('<span class="user">{}</span>', escape(username))
而 @csrf_exempt 的豁免只应保留给外部服务回调的 webhook 视图,且应配合签名校验。
CRITICAL — ORM 正确性
数据丢失与静默异常是这一级别的主题:
- 循环中的 N+1 查询:在遍历中访问关联对象而未使用
select_related(外键/一对一)或prefetch_related(多对多/反向关系)。配套技能 django-patterns 给出的对照示例:
# 坏:每个 product 都触发一次 category 查询
for product in Product.objects.all():
print(product.category.name)
# 好:JOIN 一次取回
for product in Product.objects.select_related('category').all():
print(product.category.name)
该技能还推荐用自定义 QuerySet(ProductQuerySet 提供 with_category() / with_tags() 方法,配合 objects = ProductQuerySet.as_manager())把这类优化固化到模型层,而不是散落在各处 view 中。
- 多步写操作缺少
atomic():涉及多张表的写入序列必须包在transaction.atomic()里,否则中途失败会留下半提交状态; bulk_create未处理冲突:主键/唯一键重复时的静默数据丢失风险,应配合update_conflicts之类的冲突策略;get()未处理DoesNotExist:查无对象时抛出未捕获异常。
CRITICAL — 迁移安全
- 改了模型却没有迁移:用
python manage.py makemigrations --check验证(非零退出码即代表有缺失); - 破坏向后兼容的删列操作:必须分两次部署——第一次先把列改为可空(nullable),第二次再真正删除,避免滚动发布期间旧代码写新 schema 时报错;
RunPython缺少reverse_code:数据迁移无法回滚,生产事故时无法安全 downgrade。
HIGH — DRF 模式
- Serializer 未显式声明
fields:fields = '__all__'会把模型所有列(可能含敏感列)暴露给 API; - 列表端点没有分页:无界查询可能一次返回百万行;
- 缺少
read_only_fields:id、created_at等自动生成字段可被 API 写入; - 认证端点没有限流:登录/注册接口直接暴露于暴力破解。
配套的 django-patterns 技能里有一个符合上述全部要求的 ViewSet 范式:queryset 上使用 select_related('category').prefetch_related('tags') 防 N+1、显式 permission_classes = [IsAuthenticated, IsOwnerOrReadOnly]、通过 get_serializer_class() 区分创建/读取序列化器、用户上下文注入放在 perform_create 而非 validate 中。限流配置则见 django-security:
REST_FRAMEWORK = {
'DEFAULT_THROTTLE_CLASSES': [
'rest_framework.throttling.AnonRateThrottle',
'rest_framework.throttling.UserRateThrottle',
],
'DEFAULT_THROTTLE_RATES': {
'anon': '100/day',
'user': '1000/day',
'upload': '10/hour',
}
}
HIGH — 性能
- 外键/过滤字段缺
db_index:过滤查询退化为全表扫描(注意触发流程第 4 步中已说明:ForeignKey 默认带索引,这里主要指非 FK 的过滤列); - 视图内同步调用外部 API:阻塞请求线程,应下沉到 Celery 异步任务;
len(queryset)代替.count():前者会把整个结果集取到内存再数长度;- 存在性判断不用
exists():if queryset:会无谓地拉取对象,应写if queryset.exists():。
django-patterns 技能中的索引示例展示了如何在 Meta.indexes 中为高频过滤/排序列建复合索引(如 ['category', 'is_active']、['-created_at']),这正是本条检查的修复手段。
HIGH — 代码质量
- 业务逻辑写在 view 或 serializer 里:应下沉到
services.py服务层(django-patterns 中的OrderService.create_order示例即演示了“事务内的多表写入集中在服务层”的写法); - 模型字段的可变默认值:
default=[]/default={}是经典陷阱,应写default=list/default=dict; - 热路径更新不带
update_fields的save():大模型或高吞吐代码中更新个别字段时,应传update_fields以避免写回全部列。文档同时注明:对象创建与表单驱动的整体保存,标准save()是正确的,不必强加。
MEDIUM — 最佳实践
- 用
print()代替日志:应使用logging.getLogger(__name__); - 缺
related_name:反向访问器只能写成user_set,可读性差; - 硬编码 URL:应使用
reverse()或reverse_lazy(); - 模型缺
__str__:Django admin 与日志可读性受损。
MEDIUM — 测试缺口
- 没有权限边界测试:必须验证未授权访问返回 403/401;
- 缺
@pytest.mark.django_db:访问数据库的测试不加该标记会抛出RuntimeError: Database access not allowed——测试会显式失败,但错误信息在陌生场景下容易误读; - 未使用 Factory:测试里裸写
Model.objects.create()脆弱且难以维护。
诊断命令(Diagnostic Commands)
文档为评审提供了可直接复制的六条基线命令,覆盖系统检查、迁移一致性、lint、类型、安全扫描与测试覆盖率:
python manage.py check
python manage.py makemigrations --check
ruff check .
mypy . --ignore-missing-imports
bandit -r . -ll
pytest --cov=apps --cov-report=term-missing -q
各命令的作用:manage.py check 运行 Django 系统检查框架(可捕获 settings、模型、URL 配置错误);makemigrations --check 校验迁移与模型同步状态;ruff 做快速 lint;mypy --ignore-missing-imports 在缺少第三方类型桩时仍可完成类型检查;bandit -r . -ll 递归扫描仅报告中等及以上严重度(-ll 表示只显示 high 级以上)的安全问题;最后一条跑测试并输出逐行缺失的覆盖率报告,配合“测试缺口”一节的检查项使用。
批准标准(Approval Criteria)
Agent 的最终结论被压缩为三档:
- Approve(通过):没有 CRITICAL 或 HIGH 级别问题;
- Warning(警告):仅存在 MEDIUM 问题——可以合并,但需谨慎;
- Block(阻断):发现任何 CRITICAL 或 HIGH 问题。
这套阈值与 .kiro/steering/review-mode.md 中定义的通用严重级别体系(Critical = 安全漏洞/数据丢失风险,High = 破坏功能/重大性能问题,Medium = 可维护性问题)保持一致,使得 django-reviewer 的输出可以直接并入 ECC 的整体评审模式。
配套技能引用与评审闭环
文档末尾的 Reference 一节指向两个技能作为深度参考:
skill: django-patterns→ 仓库内对应 .kiro/skills/django-patterns/SKILL.md(根目录也有同源副本 skills/django-patterns/SKILL.md):项目结构(split settings)、Model/QuerySet/Manager 设计、DRF Serializer 与 ViewSet 范式、服务层、缓存策略、Signals、中间件;skill: django-security→ 对应 .kiro/skills/django-security/SKILL.md(根目录副本 skills/django-security/SKILL.md):生产 settings 安全头、认证授权、SQL 注入/XSS/CSRF 防护、文件上传校验、API 限流与安全事件日志,并附一张可逐项打勾的 “Quick Security Checklist”。
在 Kiro 的自动化层面还有一层呼应:.kiro/hooks/python-lint-on-edit.kiro.hook 会在编辑 *.py 文件时触发 askAgent 检查(据 .kiro/README.md 的描述,用于尽早发现类型错误、PEP 8 违规与常见反模式),而 django-reviewer 则承担提交前的完整框架级评审。也就是说,ECC 的设计是“编辑时轻量提醒 + 提交前 Agent 深审 + 诊断命令兜底”的三段式质量闭环。
总结:把它作为你的 Django 质量门禁
.kiro/agents/django-reviewer.md 的本质是一份“可执行的评审制度”:它把生产级 Django 项目最容易出事故的七类问题(注入/密钥/CSRF 等安全配置、N+1 与事务等 ORM 正确性、迁移不可逆、DRF 暴露面、查询性能、服务分层与可变默认值、权限测试缺口)固化成带优先级的检查清单,并规定了“先跑工具、后做语义评审、最后按 CRITICAL/HIGH/MEDIUM 三档给结论”的工作流。通过 install.sh 将其装入项目后,任何一次 Django 代码变更都可以用 /django-reviewer(IDE)或 /agent swap django-reviewer(CLI)触发同一套评审,且评审边界与 python-reviewer 明确切分,与 django-patterns / django-security 两个技能形成“检查—修复参考”的完整引用链。
该 Agent 的自我定位(原文结尾)值得作为团队的评审共识直接引用:“Would this code safely serve 10,000 concurrent users without data loss, security breach, or a 3am pager alert?”(这段代码能否在万级并发下安全运行,而不发生数据丢失、安全漏洞或凌晨三点的告警?)——这正是整份清单所有检查项的验收标准。
atomcodeClaude Code 的开源替代方案。连接任意大模型,编辑代码,运行命令,自动验证 — 全自动执行。用 Rust 构建,极致性能。 | An open-source alternative to Claude Code. Connect any LLM, edit code, run commands, and verify changes — autonomously. Built in Rust for speed. Get StartedRust0624
Hy4-previewHy4 preview 是由腾讯混元团队研发的新一代混合专家(MoE)旗舰模型。模型总参数量 770B,每个 token 激活 49B,主干共包含78层,第一层采用标准 FFN,其余 77 层均为 MoE 结构,每层包含 256 个路由专家与 1 个共享专家,每个 token 激活 top-8 路由专家及共享专家。主干之外原生内置 1 层 MTP(总参数量 10B,激活 0.7B)以支持投机解码。Python00
GLM-5.3GLM-5.3 与 GLM-5.2 使用相同的基座模型——所有提升均来自后训练。与 GLM-5.2 相比,它在复杂编程和长程任务上的表现显著提升。Jinja00
GLM-5.3-FlashGLM-5.3-Flash (320B-A18B),是GLM-5系列的首个原生多模态模型。320B总参数,能力超过GLM-5.2Jinja00
Spark-X2.5-4BSpark-X2.5-4B 旨在让强大的 AI 更实用、更高效、更易获得。在广泛日常任务中表现强劲,涵盖对话、写作、翻译、推理、编码、工具调用以及智能体工作流,并在同等规模的开源模型中取得领先成绩。Spark-X2.5 将面向效率的架构与最高 1M tokens 的原生上下文窗口相结合,并支持 200 多种语言。Python00
Spark-X2.5-1.7BSpark-X2.5-1.7B 旨在让强大的 AI 更加实用、高效且易于获取。这些模型在广泛的日常任务中表现出色,涵盖对话、写作、翻译、推理、编程、工具调用和智能体工作流,并在同等规模的开源模型中取得领先结果。Spark-X2.5 将面向效率的架构与最高 1M tokens 的原生上下文窗口相结合,并支持 200 多种语言。Python00