ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

Kubescape 内置策略规则开发指南:基于 policy test 的 Rego 规则验证与发布流程

Kubescape 内置策略规则开发指南:基于 policy test 的 Rego 规则验证与发布流程 Kubescape 内置策略规则开发指南基于 policy test 的 Rego 规则验证与发布流程【免费下载链接】kubescapeKubescape is an open-source Kubernetes security platform for your IDE, CI/CD pipelines, and clusters. It includes risk analysis, security, compliance, and misconfiguration scanning, saving Kubernetes users and administrators precious time, effort, and resources.项目地址: https://gitcode.com/GitHub_Trending/ku/kubescaperules/ 目录是 Kubescape 仓库内随项目一同维护、开发与验证策略规则的专属区域它承担规则开发试验场的职责而非默认扫描的策略数据源。本文以 rules/README.md 为主线结合policy子命令源码、core/pkg/policytest测试框架以及仓库内真实规则示例系统讲解 in-tree 规则目录布局、fixture 测试运行方式、规则脚手架生成、期望输出更新以及将规则发布到默认扫描策略体系的完整流程。一、rules/ 目录的定位开发与验证区域而非策略源在深入命令之前需要先明确 rules/ 目录在整个 Kubescape 策略体系中的角色。根据 rules/README.md 的说明该目录是development and validation area for policy rules that are maintained alongside Kubescape即与 Kubescape 源码一同维护的策略规则开发和验证区域它并不是普通扫描的策略来源policy source。这意味着一个关键事实Kubescape 默认扫描kubescape scan所使用的 controls 与 frameworks 来自独立的 regolibrary 策略仓库而不是本仓库的 rules/ 目录。因此在 rules/ 中合并merge一条规则并不会自动将其发布给用户。规则要进入默认扫描体系必须走发布流程见本文第四节在 regolibrary 中完成对应的关联与发布。理解了这一定位就能解释为什么 rules/ 目录下每条规则都同时带有raw.rego、rule.metadata.json和test/测试夹具——它的核心使用场景是开发、迭代、验证规则本身确保规则在被发布到 regolibrary 之前逻辑正确、行为符合预期。二、规则目录布局raw.rego rule.metadata.json test/每条 in-tree 规则都遵循统一的磁盘布局这个布局由core/pkg/ruledir包统一定义和解析。在 core/pkg/ruledir/ruledir.go 中可以看到两个关键常量RegoFileName raw.rego MetadataFileName rule.metadata.json规则目录的基本结构如下rules/rule-name/ ├── raw.rego # Rego 策略源码package 为 armo_builtins ├── rule.metadata.json # 规则元数据名称、匹配资源、描述、修复建议、规则查询等 └── test/ └── case-name/ ├── input/ # Kubernetes manifestsYAML作为规则输入 └── expected.json # 规则对输入应产生的 RuleResponse 列表ruledir.Is函数core/pkg/ruledir/ruledir.go正是通过检测目录下是否同时存在raw.rego与rule.metadata.json两个文件来判断该目录是否为一条规则目录Load函数core/pkg/ruledir/ruledir.go则读取元数据并解析 Rego 源码将其组装为reporthandling.PolicyRule。2.1 元数据文件 rule.metadata.json以仓库内的真实规则 rules/approve-csr-v1/rule.metadata.json 为例元数据字段包括name规则名与目录名一致attributes附加属性例如该规则标注了m$K8sThreatMatrix对应 K8s 威胁矩阵中的权限提升类别与useFromKubescapeVersion引入版本ruleLanguage规则语言固定为Regomatch匹配声明即规则作用于哪些 apiGroups / apiVersions / resources例如该规则匹配rbac.authorization.k8s.io/v1下的 RoleBinding、ClusterRoleBinding、Role、ClusterRoleruleDependencies规则依赖description与remediation规则的描述与修复建议文本ruleQuery规则查询入口通常为armo_builtins。2.2 测试用例目录 test/ /每个测试用例目录包含两部分见 core/pkg/policytest/load.go 的LoadCaseInput与LoadCaseExpected实现input/一个或多个 Kubernetes 清单支持.yaml/.yml会被解析为待扫描的资源集合expected.json规则对该输入应当产生的[]reporthandling.RuleResponse期望输出。以 rules/approve-csr-v1/test/clusterrole-full-chain/ 为例input/clusterrole.yaml构造了一个同时具备 CSR 创建、检索、审批更新和 signer approve 权限的 ClusterRole构成完整攻击链expected.json 则记录了规则应当产生的告警alertScore为 9alertMessage说明该 ServiceAccount 可以创建并审批 CSR 从而铸造任意客户端证书failedPaths与reviewPaths精确指向触发告警的 RBAC 路径。仓库内approve-csr-v1的测试用例覆盖了多种变体见 rules/approve-csr-v1/test/完整攻击链clusterrole-full-chain、缺少某一环节clusterrole-missing-create、clusterrole-missing-approve、clusterrole-missing-approval-update等、通配符场景clusterrole-wildcard、clusterrole-missing-approve-signer-wildcard、clusterrole-missing-approve-signer-bare-star、仅审批权限clusterrole-approval-only、允许的通配符 signer 场景clusterrole-approve-signer-wildcard-allowed以及 RoleBinding 引用 ClusterRole 的场景rolebinding-clusterrole。这种每个关键语义分支一个用例的组织方式正是 fixture 测试的核心价值让规则的行为预期可读、可审查、可回归。三、运行 in-tree fixturesgo run . policy test ./rulesrules/README.md 给出了运行全部 in-tree 规则 fixture 的命令go run . policy test ./rules该命令由policy子命令提供。在 cmd/root.go 中policy.GetPolicyCmd()被注册到根命令GetPolicyCmdcmd/policy/policy.go下挂载了两个子命令policy init与policy test。命令本身的帮助文本明确说明这是用于authoring and testing custom Rego controls的实验性功能接口未来可能变化。3.1 policy test 的执行流程policy test path的完整执行链路如下对应 cmd/policy/test.godiscoverRules(path)调用policytest.DiscoverPath将路径解析为待测试的规则集合。DiscoverPathcore/pkg/policytest/discover.go先尝试把 path 本身当作单条规则目录加载若失败则将其视为父目录发现其直接子目录中的规则若找不到任何规则目录会报错no rule directories (raw.rego rule.metadata.json) found under ...cmd/policy/test.go。对每条规则将其test/下的每个子目录识别为一个测试用例discoverCasescore/pkg/policytest/discover.go。对每个用例RunRule/runCasecore/pkg/policytest/run.go执行三步加载expected.jsonLoadCaseExpected加载input/中的清单并实际运行规则求值EvaluateCasecore/pkg/policytest/update.go。值得说明的是求值复用了真实的 OPA 处理管线它构造一个 OPA session 并调用opaprocessor.NewOPAProcessor(...).EvaluateRule(...)因此 fixture 测试的结果与真实扫描环境高度一致用Compare比较实际输出与期望输出core/pkg/policytest/compare.go。逐用例输出PASS rule/case或FAIL rule/case失败时附带 diff最后汇总N/N cases passed存在失败用例时命令以非零状态退出cmd/policy/test.go。3.2 比较逻辑的细节Compare使用go-cmp做结构化 diff但在比较前先对两侧输出做归一化normalizecore/pkg/policytest/compare.go忽略响应切片顺序对每个响应内的failedPaths、reviewPaths、deletePaths、fixPaths排序忽略路径列表顺序求值器不保证顺序将空切片与 nil 切片视作相等求值器与 fixture 对无 k8s 对象的表示方式不一致避免误报 diff。这意味着 fixture 对字段顺序不敏感只要语义等价即可通过减少了因顺序抖动导致的虚假失败。3.3 迭代单条规则rules/README.md 建议在迭代单条规则时直接传入该规则的目录避免全量运行go run . policy test ./rules/rule-name例如对仓库内的 CSR 审批规则go run . policy test ./rules/approve-csr-v1这同样得益于DiscoverPath的双模式设计路径本身是规则目录时仅返回该单条规则。3.4 CI 与 Go 测试套件的联动rules/README.md 特别强调Go 测试套件会运行全目录命令因此当 in-tree 规则不再匹配其 fixtures 时PR 会在 CI 阶段失败。对应实现在 cmd/policy/test_test.go测试使用filepath.Abs(../../rules)定位仓库的规则目录并执行policy test从而保证 rules/ 下任何规则与 fixtures 的不一致都会被测试套件捕获。四、用 policy init 脚手架快速创建规则虽然 rules/README.md 未展开介绍但policy init是与测试流程配套的重要开发入口它能在指定路径生成一个开箱即通过测试的规则目录大幅降低新规则起步成本见 cmd/policy/init.go# 脚手架新规则生成即可通过的 fixtures kubescape policy init ./rules/no-privileged-containers # 脚手架匹配不同 kind 的规则 kubescape policy init ./rules/no-privileged-pods --kind Pod # 覆盖已存在的规则目录 kubescape policy init ./rules/no-privileged-containers --forcepolicy init支持的参数cmd/policy/init.go参数默认值说明--kindDeployment生成的规则匹配的 Kubernetes 工作负载类型支持Pod、Deployment、DaemonSet、StatefulSet、Job、CronJob见 core/pkg/policytest/scaffold.go 的SupportedKinds--description自动生成写入 rule.metadata.json 的规则描述--remediation自动生成写入 rule.metadata.json 的修复建议--forcefalse覆盖已存在的规则目录脚手架的实现Scaffoldcore/pkg/policytest/scaffold.go做了以下几件事校验规则名必须为小写字母数字与连字符正则^[a-z0-9](https://link.gitcode.com/i/0af075e5af90ba776ef55454307501fa)?$按--kind选择对应的工作负载模板不同 kind 的 Rego 容器访问路径不同例如 Pod 为wl.spec.containers[i]Deployment 为wl.spec.template.spec.containers[i]CronJob 为wl.spec.jobTemplate.spec.template.spec.containers[i]生成raw.rego默认规则检测容器securityContext.privileged true即特权容器、rule.metadata.json以及test/flagged/与test/clean/两个用例——flagged用例输入包含特权容器应告警clean用例输入无特权容器不应告警对每个用例执行真实求值将当前输出写入expected.json因此脚手架产物执行policy test时立即可通过。对应的端到端测试 cmd/policy/policy_test.go 验证了init 后 test 应输出2/2 cases passed并覆盖了--kind生效、非法 kind 报错、--update重写期望输出、幂等性等行为。五、更新期望输出policy test --update当规则逻辑发生变更或脚手架生成的预期不再符合新行为时可以借助--update用规则的当前输出重写各用例的expected.jsoncmd/policy/test.gogo run . policy test ./rules/my-custom-rule --update该流程由runPolicyUpdatecmd/policy/test.go实现对每个用例执行policytest.UpdateRulecore/pkg/policytest/update.go重新求值规则输出若输出与现有expected.json语义等价复用Compare判断则不重写输出UNCHANGED——因此该操作是幂等的若存在差异则格式化写入expected.json输出UPDATED无法求值的用例输出ERROR命令最终以非零状态退出。需要强调的是--update会以当前规则行为为基准重新对齐期望输出因此应仅在确认新行为正确时使用否则会把回归错误固化进 fixture。仓库测试 cmd/policy/policy_test.go 验证了篡改 expected.json 后policy test失败--update恢复后再次测试通过且对已一致的 fixture 运行--update输出0 case(s) updated。六、将规则发布到默认扫描体系如前文所述在 rules/ 中合并规则不会自动发布给用户。要让一条 in-tree 规则进入默认扫描的 controls 与 frameworks必须按照 rules/README.md 的发布流程操作保持本仓库内规则可验证确保该规则的 Rego、元数据与 fixtures 在本仓库持续通过go run . policy test ./rules同步到 regolibrary在 regolibrary 仓库中新增或更新对应的rules/rule-name目录关联 control 与 framework在 regolibrary 中通过 control 的rulesNames字段将规则关联到某个 control并将该 control 纳入目标 frameworks运行规则测试并走发布流程运行 regolibrary 的规则测试遵循其评审与发布流程。只有当 regolibrary 的变更被合并并发布后规则才成为 Kubescape 默认策略数据的一部分。这一仓库内开发验证 外部仓库发布的双层结构确保了规则质量在进入大规模扫描前就得到 fixture 的充分约束。七、延伸同一布局如何服务于 scan --custom-rulesrules/ 的目录布局raw.rego rule.metadata.json不仅服务于policy test还被scan --custom-rules复用用于在扫描中加载用户自研规则。从 cmd/scan/scan.go 的参数说明可见--custom-rules接受三种输入形态一个规则目录即policy test所用的布局一个包含多个规则目录的父目录一个包含裸*.rego文件的目录。加载逻辑位于 core/cautils/getter/customrules.go 的LoadCustomRules规则目录布局经ruledir.Load/ruledir.Discover解析并保留 match 声明core/cautils/getter/customrules.go裸 .rego 文件则匹配所有资源类型core/cautils/getter/customrules.go最终组装成一个名为custom-rules的合成 framework。此外自定义规则的默认严重度为 MediumbaseScore 5可通过 Rego 源码中的# baseScore 1-10注释覆盖core/cautils/getter/customrules.go规则目录与裸 .rego 同名会导致 control ID 冲突加载器会拒绝重复rejectDuplicateControlscore/cautils/getter/customrules.go不完整的规则目录缺少 raw.rego 或 rule.metadata.json会被忽略。这意味着开发者在 rules/ 中验证通过的规则可以通过--custom-rules直接在真实扫描中试用验证通过后再走第六节的发布流程进入默认策略体系形成完整的开发闭环。八、实践建议与常见问题基于仓库源码与测试用例可以总结以下实践建议每个语义分支一个用例参考 rules/approve-csr-v1/test/ 的组织方式为规则的关键判定路径命中、各缺失环节、通配符边界分别建立test/case/使规则行为可审查、可回归修改规则后务必跑 fixtures由于 Go 测试套件会全目录运行policy testcmd/policy/test_test.go本地先执行go run . policy test ./rules/rule-name可以快速定位问题避免 CI 失败谨慎使用 --update它用当前输出覆盖期望值应仅在确认新行为正确后使用WriteExpected会跳过语义等价的文件core/pkg/policytest/update.go因此可以放心其不会因字段顺序变化而做无意义重写利用 policy init 起步脚手架生成的flagged/clean双用例与自动填充的 expected.json是新规则最稳妥的起点区分验证通过与发布rules/ 内验证通过只是第一步发布必须完成 regolibrary 的 rulesNames 关联与发布流程。综上rules/ 目录连同policy子命令构成了一套完整的规则开发工作台统一的目录布局core/pkg/ruledir、可复用的 fixture 测试框架core/pkg/policytest、自动化的脚手架与期望更新以及通向默认扫描体系的发布链路为 Kubescape 策略规则的开发、验证与演进提供了坚实的工程基础。【免费下载链接】kubescapeKubescape is an open-source Kubernetes security platform for your IDE, CI/CD pipelines, and clusters. It includes risk analysis, security, compliance, and misconfiguration scanning, saving Kubernetes users and administrators precious time, effort, and resources.项目地址: https://gitcode.com/GitHub_Trending/ku/kubescape创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表