Terraform と Azure を使用したコンプライアンス テストを実装する

Terraform を使用すると、クラウド インフラストラクチャの定義、プレビュー、およびデプロイを行うことができます。 Terraform を使用する際は、HCL 構文を使って構成ファイルを作成します。 HCL 構文では、Azure などのクラウド プロバイダーと、クラウド インフラストラクチャを構成する要素を指定できます。 構成ファイルを作成したら、"実行プラン" を作成します。これにより、インフラストラクチャの変更をデプロイ前にプレビューすることができます。 変更を確認したら、実行プランを適用してインフラストラクチャをデプロイします。

多くの場合、コンプライアンス テストは継続的インテグレーション プロセスに含まれており、ユーザー定義のポリシーに従っていることを確認するために使用されます。 たとえば、Azure リソースに地理的な名前付け規則を定義する場合があります。 もう 1 つの一般的な例は、定義済みのイメージのサブセットから仮想マシンを作成する場合です。 コンプライアンス テストは、これらやその他多くのシナリオで規則を適用するために使用されます。

この記事では、次のことについて説明します。

  • コンプライアンス テストを使用する状況を理解する
  • コンプライアンス テストの実行方法について確認する
  • コンプライアンス テストの例を確認して実行する

1. 環境を構成する

  • Azure サブスクリプション:Azure サブスクリプションをお持ちでない場合は、開始する前に無料アカウントを作成してください。
  • Docker:Docker をインストールします。

  • Python:Python をインストールします。

  • Terraform コンプライアンス ツール:pip install terraform-compliance コマンドを実行して、Terraform コンプライアンス ツールをインストールします。

  • コード例とリソース: DownGit ツールを使用して、GitHub から compliance-testing プロジェクトをダウンロードし、新しいディレクトリにコード例が格納されるように解凍します。 このディレクトリを "サンプル ディレクトリ" と呼びます。

2. コンプライアンスのテストとチェックについて理解する

コンプライアンス テストは、システムが規定の標準を満たしているかどうかを判定するための非機能テスト手法です。 コンプライアンス テストは "準拠合致テスト" とも呼ばれています。

ほとんどのソフトウェア チームは、標準が適切に適用および実装されていることを確認するための分析を行います。 多くの場合、並行して標準の改善に取り組むことで、結果的に品質が向上します。

コンプライアンス テストでは、コンプライアンス テストとコンプライアンス チェックという 2 つの重要な概念を考慮する必要があります。

  • "コンプライアンス テスト" により、各開発ライフサイクル フェーズの出力が、合意された要件に準拠していることが確認されます。
  • "コンプライアンス チェック" は、プロジェクトの開始時に開発サイクルに組み込む必要があります。 要件自体が適切に文書化されていない場合、後の段階でコンプライアンス チェックを追加しようとすると、その作業がますます難しくなります。

コンプライアンス チェックは簡単に実行できます。 開発ライフサイクルのフェーズごとに、一連の標準と手順が作成され、文書化されています。 各フェーズの出力が、文書化された要件と比較されます。 テストの結果として、事前に定義された標準に準拠していないという点での "ギャップ" が示されます。 コンプライアンス テストは検査プロセスを通じて実施され、レビュー プロセスの結果は文書化する必要があります。

具体的な例を見てみましょう。

一般的な問題として、複数の開発者が相容れない変更を適用した場合に環境が中断するという問題があります。 ある人が変更に取り組んで、リソースを適用している (たとえば、テスト環境で VM を作成している) とします。 その後に、別の人が、その VM の別のバージョンをプロビジョニングする別のバージョンのコードを適用します。 ここで必要なことは、規定された規則への準拠を確認するための監視です。

この問題に対処する 1 つの方法は、rolecreator タグなどで、リソースにタグ付けするポリシーを定義することです。 ポリシーを定義したら、Terraform-compliance のようなツールを使用して、ポリシーが守られていることを確認します。

Terraform-compliance は "ネガティブ テスト" に重点を置いています。 ネガティブ テストは、予期しない入力や望ましくない動作をシステムが適切に処理できるようにするプロセスです。 "ファジー テスト" は、ネガティブ テストの 1 つの例です。 ファジー テストを使用すると、入力を受け取るシステムがテストされ、それが予期しない入力を安全に処理できることが確認されます。

幸い、Terraform は、クラウド インフラストラクチャ エンティティを作成、更新、または破棄する API の抽象化レイヤーです。 Terraform では、ローカル構成とリモート API レスポンスが同期していることも確認されます。Terraform は主にクラウド API に対して使用されるため、インフラストラクチャに対してデプロイされたコードが特定のポリシーに従っていることを確認する方法が必要です。 Terraform-compliance (無料のオープンソース ツール) では、Terraform の構成にこの機能が提供されます。

VM の例を使用すると、コンプライアンス ポリシーは次のようになります: 「Azure リソースを作成する場合は、タグを含める必要があります」

Terraform-compliance ツールには、この例のようなポリシーを作成するテスト フレームワークが用意されています。 次に、それらのポリシーを Terraform 実行プランに対して実行します。

Terraform-compliance を使用すると、BDD、つまり "振る舞い駆動開発" の原則を適用できます。 BDD は、すべての関係者が連携してシステムの動作を定義するコラボレーション プロセスです。 これらの関係者には、通常、開発者、テスト担当者、および開発中のシステムに既得権を持つ (またはこのシステムによる影響を受ける) ユーザーが含まれます。 BDD の目的は、システムの動作についての共通の理解を示す具体的な例をチームが構築できるようにすることです。

3. コンプライアンス テストの例を確認する

この記事では先ほど、テスト環境用の VM の作成でのコンプライアンス テストの例について説明しました。 このセクションでは、その例を BDD の機能とシナリオに変換する方法について説明します。 この規則は、最初に Cucumber (BDD をサポートするために使用するツール) を使用して表現します。

when creating Azure resources, every new resource should have a tag

先ほどの規則は次のように変換されます。

If the resource supports tags
Then it must contain a tag
And its value must not be null

Terraform HCL コードは、次のようにこの規則に従います。

resource "random_uuid" "uuid" {}

resource "azurerm_resource_group" "rg" {
  name     = "rg-hello-tf-${random_uuid.uuid.result}"
  location = var.location

  tags = {
    environment = "dev"
    application = "Azure Compliance"
  } 
}

最初のポリシーは、次のように BDD 機能のシナリオとして記述できます。

Feature: Test tagging compliance  # /target/src/features/tagging.feature
    Scenario: Ensure all resources have tags
        If the resource supports tags
        Then it must contain a tag
        And its value must not be null

次のコードは、特定のタグのテストを示しています。

Scenario Outline: Ensure that specific tags are defined
    If the resource supports tags
    Then it must contain a tag <tags>
    And its value must match the "<value>" regex

    Examples:
      | tags        | value              |
      | Creator     | .+                 |
      | Application | .+                 |
      | Role        | .+                 |
      | Environment | ^(prod\|uat\|dev)$ |

4. コンプライアンス テストの例を実行する

このセクションでは、サンプルをダウンロードしてテストします。

  1. サンプル ディレクトリ内で、src ディレクトリに移動します。

  2. terraform init を実行して、作業ディレクトリを初期化します。

    terraform init
    
  3. terraform validate を実行して、構成ファイルの構文を検証します。

    terraform validate
    

    重要なポイント:

    • Terraform の構成が有効であることを示すメッセージが表示されます。
  4. terraform plan を実行して、実行プランを作成します。

    terraform plan -out main.tfplan
    
  5. terraform show を実行して、コンプライアンス ステップの実行プランを JSON に変換します。

    terraform show -json main.tfplan > main.tfplan.json
    
  6. docker pull を実行して、terraform-compliance のイメージをダウンロードします。

    docker pull eerkunt/terraform-compliance
    
  7. docker run を実行して、Docker コンテナーでテストを実行します。

    docker run --rm -v $PWD:/target -it eerkunt/terraform-compliance -f features -p main.tfplan.json
    

    重要なポイント:

    • このテストは失敗します。タグが存在することを要求する最初の規則は成功しますが、2 番目の規則は、Role タグと Creator タグが欠落しているために失敗します。

    Example of a failed test

  8. エラーを修正するには、main.tf を次のように変更します (Role タグと Creator タグが追加されます)。

      tags = {
        Environment = "dev"
        Application = "Azure Compliance"
        Creator     = "Azure Compliance"
        Role        = "Azure Compliance"
      } 
    
    

    重要なポイント:

    • 構成がポリシーに準拠するようになりました。

5. 結果を確認する

  1. terraform validate を再度実行して構文を検証します。

    terraform validate
    
  2. terraform plan を再度実行して、新しい実行プランを作成します。

    terraform plan -out main.tfplan
    
  3. terraform show を実行して、コンプライアンス ステップの実行プランを JSON に変換します。

    terraform show -json main.tfplan > main.tfplan.json
    
  4. docker run を再度実行して、構成をテストします。 仕様が全面的に実装されている場合、テストは成功します。

    docker run --rm -v $PWD:/target -it eerkunt/terraform-compliance -f features -p main.tfplan.json
    

    Example of a successful test

  5. terraform apply を実行して、実行プランを適用します。

    terraform apply main.tfplan -target=random_uuid.uuid
    

    重要なポイント:

    • rg-hello-tf-<random_number> というパターンに従う名前のリソース グループが作成されます。

Azure での Terraform のトラブルシューティング

Azure で Terraform を使用する場合の一般的な問題のトラブルシューティング

次のステップ