如何修改Semgrep规则校验Django ForeignKey的related_name格式是否合规
该需求完全可以实现,核心通过Semgrep的metavariable-regex语法实现变量拼接和格式校验,以下是完整可运行的规则代码:
- id: python.custom.foreign-key-must-set-related-name message: ForeignKey 必须显式设置符合格式的related_name参数,格式要求为 <模型名小写>_<字段名>_set languages: [python] severity: ERROR patterns: # 限定匹配范围:Django模型类内部 - pattern-inside: | class $M(...): ... - patterns: - pattern-either: # 匹配场景1:未设置related_name参数 - pattern: $F = django.db.models.ForeignKey(...) # 匹配场景2:已设置related_name但格式不符合要求 - pattern: $F = django.db.models.ForeignKey(..., related_name=$R, ...) # 排除空字符串的related_name(如果项目允许可删除该行) - pattern-not: $F = django.db.models.ForeignKey(..., related_name="", ...) # 校验related_name格式不匹配规则时触发报错 - metavariable-regex: metavariable: $R regex: ^(?!\L$M_$F_set$).*
规则逻辑说明
- 保留了原有规则中「未显式设置related_name」的校验能力
- 新增了格式校验逻辑:通过
\L语法将捕获到的模型类名$M自动转全小写,和字段名$F、固定后缀_set拼接后和实际传入的related_name值比对,格式不符合时触发报错 - 适配你提供的示例代码:
MyCoolModel类下的correct_field字段设置的related_name='mycoolmodel_correct_field_set'符合规则不会触发报错,incorrect_field会触发格式校验错误。
如果你的项目要求模型名驼峰转下划线(例如MyCoolModel转换为my_cool_model),只需调整正则部分的转换逻辑即可。
内容的提问来源于stack exchange,提问作者fgarci03
相关产品推荐
相关产品推荐

