규칙 작성하기
Rego에서의 규칙
규칙은 Rego에서 작성됩니다. Rego를 작성할 때 두 가지를 수행합니다.
정책 결정을 내리는 규칙을 작성합니다. 규칙은 조건부 할당입니다.
정책에 규칙을 조직화합니다. 정책은 계층적 이름을 가진 규칙의 집합입니다.
Policy Language에 대해 더 알아보려면 OPA Policy Language Documentation Page를 방문하십시오.
새 규칙 생성 방법
시작하는 데 두 가지 옵션이 있습니다.
규칙을 작성하기 위해 필요한 파일을 생성하려면
template
명령을 사용하십시오:snyk-iac-rules template --rule <RULE-NAME> --format <hcl2|json|yaml|tf-plan>
이 명령은 제공된 구성 형식을 기반으로 규칙에 대한 틀을 생성합니다. 자세한 내용은 템플릿 명령에 대한 문서를 읽어보세요.
Rego 정책을 처음부터 작성하고 본인이 예상하는 파일 및 폴더 구조와 일치하도록 일치시킵니다:
rules
└── my_rule
├── main.rego
└── main_test.rego
규칙 구조
Rego에서 요청을 허용하거나 거부하는 문을 작성할 수 있습니다:
allow { input.name == "alice" }
또는 deny { input.name == "alice" }
다음은 snyk-iac-rules template --rule NEW-RULE --format hcl2
를 실행했을 때 생성된 별도의 규칙 스켈레톤의 모습입니다:
package rules
deny[msg] {
resource := input.resource.test[name]
resource.todo
msg := {
# Mandatory fields
"publicId": "NEW-RULE",
"title": "Default title",
"severity": "low",
"msg": sprintf("input.resource.test[%s].todo", [name]),
# Optional fields
"issue": "",
"impact": "",
"remediation": "",
"references": [],
}
}
출력이 올바르게 표시되도록 msg 속성 형식을 따라야 합니다.
속성은 다음과 같습니다:
publicId: 팀별 고유한 네이밍 규칙으로, 예를 들어 COMPANY-001입니다. 이 값은 내부 Snyk 규칙과 구분하기 위해 “SNYK-”를 포함해서는 안 됩니다.
title: 이슈를 요약하는 간단한 제목입니다.
severity: low/medium/high/critical 중 하나일 수 있습니다.
msg: Snyk는 자원 이름 및 속성을 변경하여 예를 들어
input.aws_s3_bucket[%s].tags
와 일치하도록 권장합니다.sprintf
함수는 Rego에서 제공되며 Snyk가 발견한 문제의 정확한 위치를 설명하는 동적 오류 메시지를 제공합니다.
다음 속성은 선택적이지만 Snyk CLI에서 스캔 결과를 향상시키는 데 사용할 수 있습니다:
issue: 정확한 문제에 대한 자세한 설명 문자열입니다.
impact: 이 문제를 해결하지 않았을 때의 영향에 대한 자세한 설명 문자열입니다.
remediation: 문제를 해결하는 방법에 대한 자세한 설명 문자열입니다. Snyk는 여기에 코드 스니펫을 제공하는 것을 권장합니다.
references: 문서 URL 문자열 배열을 제공할 수 있습니다.
규칙의 생성된 테스트는 허용된 및 거부된 Fixture에 대해 올바른 msg
필드가 규칙에 의해 반환되는지 확인하기 위해 두 개의 생성된 Terraform 파일을 사용합니다.
package rules
import data.lib
import data.lib.testing
test_NEW_RULE {
# 규칙이 허용되는 테스트 케이스를 포함하는 배열
allowed_test_cases := [{
"want_msgs": [],
"fixture": "allowed.tf",
}]
# 규칙이 거부되는 케이스를 포함하는 배열
denied_test_cases := [{
"want_msgs": ["input.resource.test[denied].todo"], # 거부된 규칙에 의해 반환된 올바른 msg임을 확인합니다.
"fixture": "denied.tf",
}]
test_cases := array.concat(allowed_test_cases, denied_test_cases)
testing.evaluate_test_cases("NEW-RULE", "./rules/NEW-RULE/fixtures", test_cases)
}
규칙 예시
이 예시에서 템플릿 규칙은 owner
태그가 없는 자원에 msg
를 할당하도록 수정되었습니다:
package rules
deny[msg] {
resource := input.resource.aws_redshift_cluster[name]
not resource.tags.owner
msg := {
"publicId": "MY_RULE",
"title": "Missing an owner from tag",
"severity": "medium",
"msg": sprintf("input.resource.aws_redshift_cluster[%s].tags", [name]),
"issue": "",
"impact": "",
"remediation": "",
"references": [],
}
}
제한 사항 및 참고 사항
Snyk은 Rego 정책을 Wasm 모듈로 컴파일하기 때문에 Wasm을 지원하는 내장 함수만 사용할 수 있습니다. 이러한 함수를 확인하는 표가 Policy Reference Documentation 맨 아래에 있습니다.
규칙은 동일한 이름으로 여러 번 정의될 수 있습니다. 파일이나 동일한 패키지 내의 별도 파일에서 정의할 수 있습니다. 예를 들어,
packages rules
deny[msg] {
resource.this
}
...
deny[msg] {
resource.that
}
...
이러한 규칙은 증분적(incremental)
규칙이라고 하며 각 정의가 누적적입니다. Policy Reference Documentation에서 증분적 정의에 대해 더 읽어볼 수 있습니다. 동일한 이름을 가진 규칙은 다른 값을 반환해야 하며 그렇지 않으면 OPA에서 오류를 반환합니다. Policy Reference Documentation에서 완전한 정의에 대해 더 읽어볼 수 있습니다.
더 복잡한 주제에 대해서는 OPA Conflict Resolution 해결 방법을 확인하십시오.
Last updated