Комплаєнс як код: Як написати власну політику на Python за допомогою Checkov

текст перекладу
В швидко змінюваному світі хмарної інфраструктури дотримання організаційних політик та галузевих стандартів є надзвичайно важливим. Практика "комплаєнс як код" (Compliance as Code) полягає в тому, щоб кодифікувати та автоматизувати вимоги комплаєнсу, забезпечуючи безперервне дотримання правил без ручного втручання. Цей підхід зменшує людську помилку, прискорює процеси розгортання та покращує загальний рівень безпеки.

Checkov — це відкритий інструмент для статичного аналізу коду, розроблений Palo Alto Networks, який сканує конфігурації хмарної інфраструктури на предмет порушень політик до їх розгортання. Він підтримує різні фреймворки Infrastructure as Code (IaC), такі як Terraform та CloudFormation, але також може використовуватись для перевірки конфігурацій Kubernetes та інших. Використовуючи Checkov, організації можуть забезпечити виконання політик комплаєнсу та безпеки на етапі розробки, гарантуючи, що тільки відповідна інфраструктура буде розгорнута.

Написання власних політик для Checkov на Python

Хоча Checkov поставляється з великим набором вбудованих політик, іноді організаціям необхідні власні політики для виконання специфічних вимог комплаєнсу. В таких випадках ви можете написати власні політики для Checkov за допомогою Python. Ось покрокова інструкція, як створити та протестувати власні політики для Terraform, зокрема для забезпечення того, щоб AWS security groups мали конкретні теги.

Передумови

  1. Встановіть Checkov:
pip install checkov
  1. Знання Python.
  2. Базові знання Terraform та його конфігураційних файлів.

Крок 1: Створення власної політики для Checkov

Щоб створити Python політику для Checkov, потрібно створити python файл, щоб визначити клас, який буде представляти вашу політику:

from checkov.terraform.checks.resource.base_resource_check import BaseResourceCheck  
from checkov.common.models.enums import CheckResult, CheckCategories  
from typing import Any, Dict  

class CheckSecurityGroupTags(BaseResourceCheck):  
 def __init__(self) -> None:  
 name = "Ensure all security groups have the tag 'name' equal to 'custom-tag-for-security-group'"  
 id = "CUSTOM_AWS_1"  
 supported_resources = ("aws_security_group")  
 categories = (CheckCategories.CONVENTION)  
 super().__init__(name=name, id=id, categories=categories, supported_resources=supported_resources)  

 def scan_resource_conf(self, conf: Dict[str, Any]) -> CheckResult:  
 """  
 Looks for the tag 'name' with value 'custom-tag-for-security-group' in aws_security_group configuration.  
 :param conf: aws_security_group configuration  
 :return:   
 """  
 if 'tags' in conf.keys():  
 tags = conf.get("tags")  
 if tags and isinstance(tags, list):  
 tags = tags[0]  
 if tags.get("name") == "custom-tag-for-security-group":  
 return CheckResult.PASSED  
 return CheckResult.FAILED  

check = CheckSecurityGroupTags()

У цьому прикладі:

  • name: Людсько-зрозуміла назва для політики.
  • id: Унікальний ідентифікатор для політики.
  • supported_resources: Типи ресурсів, до яких застосовується ця політика. У цьому випадку це aws_security_group.
  • categories: Категорія, до якої відноситься ця політика. Тут це політика конвенцій.
  • scanresourceconf: Метод, який містить логіку для політики. Він перевіряє, чи тег name має значення custom-tag-for-security-group для AWS security group.

Для більш детальної інформації, ознайомтесь з документацією.

Крок 2: Тестування вашої власної політики

Після того, як ви написали свою власну політику, необхідно протестувати її, щоб переконатися, що вона працює належним чином. Дотримуйтесь цих кроків для тестування вашої політики:

1.
текст перекладу
Створіть конфігураційний файл Terraform main.tf, який включає ресурси AWS security group.

resource "aws_security_group" "example" {  
 name = "example"  
 description = "Example security group"  
 vpc_id = "vpc-123456"  

 tags = {  
 name = "custom_tag_for_security_group"  
 }  
}
  1. Запустіть Checkov проти цього файлу Terraform для тестування власної політики.
checkov -d . --external-checks-dir  --check CUSTOM_AWS_1

вивід:

pic

З іншого боку, якщо тег буде змінено:

resource "aws_security_group" "example" {  
 name = "example"  
 description = "Example security group"  
 vpc_id = "vpc-123456"  

 tags = {  
 name = "wrong-tag"  
 }  
}

Checkov виявить неконфігурацію і покаже помилку:

pic

Це стає дуже корисним для ваших CI/CD пайплайнів, адже ви можете сканувати ваш код IaC перед його розгортанням.

Примітка: Після того як інфраструктура буде розгорнута, будь-які зміни до ваших політик через консоль не можна буде перевірити на відповідність за допомогою Checkov. Для таких випадків ви можете скористатися іншими інструментами, такими як Cloud Custodian, AWS Config, Azure Policies тощо…

Написання юніт-тестів для власних політик

Кожного разу, коли ваша задача пов’язана з кодом, ви повинні тестувати його, щоб переконатися, що він працює так, як передбачено. В випадку з Checkov ви можете писати юніт-тести для ваших власних політик.

Ось простий приклад для тестування вашого коду. Ідея проста: ви можете симулювати ваш код Terraform, використовуючи рядок, відформатований як HCL, а потім використати бібліотеку hcl2 для перетворення його в словник.

import unittest  
from checkov.common.models.enums import CheckResult  
from src.policies.checkov.custom_tag_check.custom_tag_check import CheckSecurityGroupTags  
import hcl2  

class TestCheckSecurityGroupTags(unittest.TestCase):  

 def setUp(self):  
 self.check = CheckSecurityGroupTags()  

 def _get_conf_from_hcl(self, hcl_string):  
 return hcl2.loads(hcl_string)  

 def test_security_group_with_correct_tag(self):  
 hcl_string = """  
 resource "aws_security_group" "good_example" {  
 tags = {  
 name = "custom_tag_for_security_group"  
 }  
 }  
 """  
 conf = self._get_conf_from_hcl(hcl_string)  
 result = self.check.scan_resource_conf(conf['resource'][0]['aws_security_group']['good_example'])  
 self.assertEqual(result, CheckResult.PASSED)  

 def test_security_group_with_incorrect_tag_value(self):  
 hcl_string = """  
 resource "aws_security_group" "bad_example" {  
 tags = {  
 name = "wrong-security-group"  
 }  
 }  
 """  
 conf = self._get_conf_from_hcl(hcl_string)  
 result = self.check.scan_resource_conf(conf['resource'][0]['aws_security_group']['bad_example'])  
 self.assertEqual(result, CheckResult.FAILED)  

 def test_security_group_with_no_name_tag(self):  
 hcl_string = """  
 resource "aws_security_group" "no_name_tag" {  
 tags = {  
 other_tag = "some_value"  
 }  
 }  
 """  
 conf = self._get_conf_from_hcl(hcl_string)  
 result = self.check.scan_resource_conf(conf['resource'][0]['aws_security_group']['no_name_tag'])  
 self.assertEqual(result, CheckResult.FAILED)  

 def test_security_group_with_no_tags(self):  
 hcl_string = """  
 resource "aws_security_group" "no_tags" {  
 }  
 """  
 conf = self._get_conf_from_hcl(hcl_string)  
 result = self.check.scan_resource_conf(conf['resource'][0]['aws_security_group']['no_tags'])  
 self.assertEqual(result, CheckResult.FAILED)  

if __name__ == '__main__':  
 unittest.main()

Висновок

Checkov є надзвичайно корисним інструментом, коли ви активно працюєте з Infrastructure as Code (IaC), оскільки він може виявити неконфігурації ще до розгортання. Однак він має обмеження, коли багато користувачів (що є поганою практикою) мають доступ до консолі вашого хмарного провайдера.
текст перекладу
Я настійно рекомендую надавати користувачам доступ лише для перегляду до консолі, коли це можливо, та використовувати інструменти, такі як Cloud Custodian, для динамічного моніторингу відповідності. Ці інструменти можуть допомогти налаштувати автоматичне виправлення помилок або сповіщення про зміни в консолі, які порушують ваші політики.

Якщо вам цікаво дізнатися більше про Cloud Custodian, напишіть у коментарях, і я напишу статтю про його основні можливості.

Перекладено з: Compliance as Code: How to write a Python custom policy using Checkov

Leave a Reply

Your email address will not be published. Required fields are marked *