[小ネタ] EventBridge と Lambda で新規作成された ENI に自動でタグを付与してみた

[小ネタ] EventBridge と Lambda で新規作成された ENI に自動でタグを付与してみた

CloudFormation を使って EventBridge と Lambda による自動タグ付与システムを作ってみました
2025.09.07

アノテーション・テクニカルサポートチームの hato です。

CloudFormation を使って、ENI が新規作成されるとタグを自動で付与するシステムを作成する機会がありましたので、小ネタとして紹介します。

構成と仕様

  • EventBridge
    • CreateNetworkInterfaceイベントをトリガーに Lambda 関数を実行します。
  • Lambda
    • イベント情報をもとに、作成された ENI にタグを付与します。
  • CloudFormation
    • 上記を含む必要なリソースをまとめて作成します。

付与するタグについて

デフォルトで次の 2 つのタグを付与します。

CloudFormation のパラメータで指定したタグ

  • キー:hato_key
  • 値:hato_value

Lambda 関数内で指定したタグ

  • キー:ManagedBy
  • 値:Lambda-AutoTagging

※ Lambda 関数内で指定したタグは、 Lambda のソースコードにハードコーディングしているので不要であれば消してください。

テンプレート

AWSTemplateFormatVersion: '2010-09-09'
Description: 'Lambda function to automatically tag ENIs when created'

Parameters:
  TagKey:
    Type: String
    Default: 'hato_key'
    Description: 'Tag key to apply to ENIs'

  TagValue:
    Type: String
    Default: 'hato_value'
    Description: 'Tag value to apply to ENIs'

Resources:
  ENITaggingLambdaRole:
    Type: AWS::IAM::Role
    Properties:
      RoleName: !Sub '${AWS::StackName}-eni-tagging-lambda-role'
      AssumeRolePolicyDocument:
        Version: '2012-10-17'
        Statement:
          - Effect: Allow
            Principal:
              Service: lambda.amazonaws.com
            Action: sts:AssumeRole
      ManagedPolicyArns:
        - arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole
      Policies:
        - PolicyName: ENITaggingPolicy
          PolicyDocument:
            Version: '2012-10-17'
            Statement:
              - Effect: Allow
                Action:
                  - ec2:CreateTags
                  - ec2:DescribeNetworkInterfaces
                Resource: '*'

  ENITaggingLambda:
    Type: AWS::Lambda::Function
    Properties:
      FunctionName: !Sub '${AWS::StackName}-eni-auto-tagging'
      Runtime: python3.13
      Handler: index.lambda_handler
      Role: !GetAtt ENITaggingLambdaRole.Arn
      Timeout: 60
      Environment:
        Variables:
          TAG_KEY: !Ref TagKey
          TAG_VALUE: !Ref TagValue
      Code:
        ZipFile: |
          import json
          import boto3
          import os
          import logging

          logger = logging.getLogger()
          logger.setLevel(logging.INFO)
          ec2_client = boto3.client('ec2')

          def lambda_handler(event, context):
              try:
                  logger.info(f"Received event: {json.dumps(event)}")

                  # CloudTrail イベントから ENI ID を取得
                  detail = event.get('detail', {})
                  response_elements = detail.get('responseElements', {})
                  network_interface = response_elements.get('networkInterface', {})
                  eni_id = network_interface.get('networkInterfaceId')

                  if not eni_id:
                      logger.error("ENI ID not found in event")
                      return {
                          'statusCode': 400,
                          'body': json.dumps('ENI ID not found')
                      }

                  logger.info(f"Processing ENI: {eni_id}")

                  # 環境変数からタグ情報を取得
                  tag_key = os.environ.get('TAG_KEY', 'AutoTagged')
                  tag_value = os.environ.get('TAG_VALUE', 'true')

                  # 付与するタグ
                  tags = [
                      {
                          'Key': tag_key,
                          'Value': tag_value
                      },
                      {
                          'Key': 'ManagedBy',
                          'Value': 'Lambda-AutoTagging'
                      }
                  ]

                  # ENI にタグを付与
                  response = ec2_client.create_tags(
                      Resources=[eni_id],
                      Tags=tags
                  )

                  logger.info(f"Successfully tagged ENI {eni_id} with tags: {tags}")

                  return {
                      'statusCode': 200,
                      'body': json.dumps({
                          'message': f'Successfully tagged ENI {eni_id}',
                          'tags': tags
                      })
                  }

              except Exception as e:
                  logger.error(f"Error processing event: {str(e)}")
                  return {
                      'statusCode': 500,
                      'body': json.dumps(f'Error: {str(e)}')
                  }

  ENICreationEventRule:
    Type: AWS::Events::Rule
    Properties:
      Name: !Sub '${AWS::StackName}-eni-creation-rule'
      Description: 'Trigger Lambda when ENI is created'
      EventPattern:
        source:
          - 'aws.ec2'
        detail-type:
          - 'AWS API Call via CloudTrail'
        detail:
          eventSource:
            - 'ec2.amazonaws.com'
          eventName:
            - 'CreateNetworkInterface'
          errorCode:
            - exists: false
      State: ENABLED
      Targets:
        - Arn: !GetAtt ENITaggingLambda.Arn
          Id: 'ENITaggingLambdaTarget'

  LambdaInvokePermission:
    Type: AWS::Lambda::Permission
    Properties:
      FunctionName: !Ref ENITaggingLambda
      Action: lambda:InvokeFunction
      Principal: events.amazonaws.com
      SourceArn: !GetAtt ENICreationEventRule.Arn

作り方、使い方

スタックの作成

AWS マネジメントコンソールから上記テンプレートをデプロイします。

  1. 上記テンプレートを任意の名前(例:eni-auto-tagging.yaml)でテキストファイルとして保存

  2. CloudFormation コンソール
    「テンプレートファイルのアップロード」からアップロード

EventBridge Lambda ENI Auto Tagging 1

  1. 任意のスタック名と、付与するタグをパラメータで指定してスタックを作成

EventBridge Lambda ENI Auto Tagging 2

動作確認

VPC に接続された Lambda 関数を作成して、ENI を作成します。

作成された ENI を確認すると、次のタグが付与されています。

  • ManagedBy:Lambda-AutoTagging
  • hato_keyhato_value

EventBridge Lambda ENI Auto Tagging 3

最後に

この記事が誰かのお役にたてば幸いです。

アノテーション株式会社について

アノテーション株式会社はクラスメソッドグループのオペレーション専門特化企業です。サポート・運用・開発保守・情シス・バックオフィスの専門チームが、最新 IT テクノロジー、高い技術力、蓄積されたノウハウをフル活用し、お客様の課題解決を行っています。当社は様々な職種でメンバーを募集しています。「オペレーション・エクセレンス」と「らしく働く、らしく生きる」を共に実現するカルチャー・しくみ・働き方にご興味がある方は、アノテーション株式会社 採用サイト をぜひご覧ください。

この記事をシェアする

facebookのロゴhatenaのロゴtwitterのロゴ

© Classmethod, Inc. All rights reserved.