LoginSignup
1
0

More than 1 year has passed since last update.

AWS-ApplyAnsiblePlaybooksをAmazon Linux 2023でも使えるようにする。

Posted at

はじめに

先月あたりにAmazon Linux 2023が登場しましたが、Ansibleが実行できるSystems Manager Run CommandAWS-ApplyAnsiblePlaybooksがまだAmazon Linux 2023に対応していなかったため、Amazon Linux 2023でも動かせるようにしたいと思います。

Systems Manager Run CommandによるAnsibleの実行

過去記事で何度か紹介しているため、詳しくは以下を参照。

Systems Manager Run Commandについて

Systems Manager Run Commandは予め準備されている「ドキュメント」と呼ばれる定義ファイルに従って、指定したインスタンスに対してコマンド等を実行する機能となります。

Ansibleを実行するAWS公式のAWS-ApplyAnsiblePlaybooksドキュメントもドキュメント内の設定を見ると分かる通り、やっていることはAnsibleのインストールとplaybookの実行、あとはAWSマネジメントコンソールからの操作時に表示する設定が書かれているだけなので、このドキュメントをカスタマイズして、Amazon Linux 2023でも使えるようにします。

なぜAmazon Linux 2023のインスタンスに対して実行できないか?

実際に実行してみれば分かりますが、AWS-ApplyAnsiblePlaybooksドキュメントに書かれている条件式がAmazon Linux 2023に対応していないからとなります。

以下ドキュメントからの条件式部分抜粋ですが、インスタンスのOS判定のため、/etc/system-releaseというファイルの中身を見てOSを判定し、OS毎にAnsibleのインストール方法を変えています。

OS判定条件式抜粋
        "runCommand": [
          "#!/bin/bash",
          "if  [[ \"{{InstallDependencies}}\" == True ]] ; then",
          "   echo \"Installing and or updating required tools: Ansible, wget unzip ....\" >&2",
          "   if [ -f  \"/etc/system-release\" ] ; then",
          "     if cat /etc/system-release|grep -i 'Amazon Linux release 2' ; then ",
          "       sudo yum install -y https://dl.fedoraproject.org/pub/epel/epel-release-latest-7.noarch.rpm",
          "       sudo yum install -y ansible",
          "       sudo yum -y install unzip",
          "     elif cat /etc/system-release|grep -i 'Amazon Linux AMI' ; then ",
          "       sudo pip install ansible --upgrade",
          "       sudo yum -y install unzip",
          "     elif cat /etc/system-release|grep -i 'Red Hat Enterprise Linux' ; then ",
          "       sudo yum -y install python3-pip",
          "       sudo pip3 install ansible",
          "       sudo yum -y install unzip",
          "     else",
          "       echo \"There was a problem installing or updating the required tools for the document. You can review the log files to help you correct the problem.\" >&2",
          "       exit 1",
          "     fi",

ちなみにAmazon Linux 2023/etc/system-releaseには以下のような文言が記載されております。

Amazon Linux 2023の/etc/system-release
Amazon Linux release 2023 (Amazon Linux)

Amazon Linux 2023のインスタンスで実行した場合、Amazon Linux 2用のAmazon Linux release 2に引っかかるため、epelリポジトリインストールしてAnsibleをインストールする流れとなりますが、Amazon Linux 2023のリポジトリにはepelリポジトリが無いことからAnsibleのインストールに失敗してしまうことが原因となります。

カスタムドキュメント作成

以下よりAmazon Linux 2023対応したカスタムドキュメントを作成していこうと思います。

AWS Systems Manager」の左ペインから「ドキュメント」を選択し、「AWS-ApplyAnsiblePlaybooks」を選びます。

右上の「アクション」から「ドキュメントのクローン作成」を選択するとクローンが作成できるため、以下のように入力。

尚、名前については先頭がAWSで始まる名前は予約されており、指定できないので、今回はCustom-ApplyAnsiblePlaybooksAL2023といった名前にしました。

項目 設定 備考
名前 Custom-ApplyAnsiblePlaybooksAL2023 適当な名前を入力
ターゲットタイプ 空欄
ドキュメントタイプ コマンドドキュメント クローン作成の場合は指定不可
コンテンツ JSON コンテンツの中身については後述
ドキュメントのタグ 任意

Amazon Linux 2023対応版コンテンツの作成

先に対応版のドキュメント全容を紹介。

Custom-ApplyAnsiblePlaybooksAL2023
{
  "schemaVersion": "2.2",
  "description": "Use this document to run Ansible Playbooks on Systems Manager managed instances. For more information, see https://docs.aws.amazon.com/systems-manager/latest/userguide/systems-manager-state-manager-ansible.html.",
  "parameters": {
    "SourceType": {
      "description": "(Optional) Specify the source type.",
      "type": "String",
      "allowedValues": [
        "GitHub",
        "S3"
      ]
    },
    "SourceInfo": {
      "description": "(Optional) Specify the information required to access the resource from the specified source type. If source type is GitHub, then you can specify any of the following: 'owner', 'repository', 'path', 'getOptions', 'tokenInfo'. Example GitHub parameters: {\"owner\":\"awslabs\",\"repository\":\"amazon-ssm\",\"path\":\"Compliance/InSpec/PortCheck\",\"getOptions\":\"branch:master\"}. If source type is S3, then you can specify 'path'. Important: If you specify S3, then the IAM instance profile on your managed instances must be configured with read access to Amazon S3.",
      "type": "StringMap",
      "displayType": "textarea",
      "default": {}
    },
    "InstallDependencies": {
      "type": "String",
      "description": "(Required) If set to True, Systems Manager installs Ansible and its dependencies, including Python, from the PyPI repo. If set to False, then verify that Ansible and its dependencies are installed on the target instances. If they aren’t, the SSM document fails to run.",
      "allowedValues": [
        "True",
        "False"
      ],
      "default": "True"
    },
    "PlaybookFile": {
      "type": "String",
      "description": "(Optional) The Playbook file to run (including relative path). If the main Playbook file is located in the ./automation directory, then specify automation/playbook.yml.",
      "default": "hello-world-playbook.yml",
      "allowedPattern": "[(a-z_A-Z0-9\\-\\.)/]+(.yml|.yaml)$"
    },
    "ExtraVariables": {
      "type": "String",
      "description": "(Optional) Additional variables to pass to Ansible at runtime. Enter key/value pairs separated by a space. For example: color=red flavor=cherry",
      "default": "SSM=True",
      "displayType": "textarea",
      "allowedPattern": "^$|^\\w+\\=(([^\\s|:();&]+)|('[^|:();&]+'))(\\s+\\w+\\=(([^\\s|:();&]+)|('[^|:();&]+')))*$"
    },
    "Check": {
      "type": "String",
      "description": "(Optional) Use this parameter to run a check of the Ansible execution. The system doesn’t make any changes to your systems. Instead, any module that supports check mode reports the changes it would make rather than making them. Modules that don’t support check mode take no action and don’t report changes that would be made.",
      "allowedValues": [
        "True",
        "False"
      ],
      "default": "False"
    },
    "Verbose": {
      "type": "String",
      "description": "(Optional) Set the verbosity level for logging Playbook executions. Specify -v for low verbosity, -vv or –vvv for medium verbosity, and -vvvv for debug level.",
      "allowedValues": [
        "-v",
        "-vv",
        "-vvv",
        "-vvvv"
      ],
      "default": "-v"
    },
    "TimeoutSeconds": {
      "type": "String",
      "description": "(Optional) The time in seconds for a command to be completed before it is considered to have failed.",
      "default": "3600"
    }
  },
  "mainSteps": [
    {
      "action": "aws:downloadContent",
      "name": "downloadContent",
      "inputs": {
        "SourceType": "{{ SourceType }}",
        "SourceInfo": "{{ SourceInfo }}"
      }
    },
    {
      "action": "aws:runShellScript",
      "name": "runShellScript",
      "inputs": {
        "timeoutSeconds": "{{ TimeoutSeconds }}",
        "runCommand": [
          "#!/bin/bash",
          "if  [[ \"{{InstallDependencies}}\" == True ]] ; then",
          "   echo \"Installing and or updating required tools: Ansible, wget unzip ....\" >&2",
          "   if [ -f  \"/etc/system-release\" ] ; then",
          "     if cat /etc/system-release|grep -i 'Amazon Linux release 2023' ; then ",
          "       sudo yum -y install python3-pip",
          "       sudo pip3 install ansible",
          "       sudo yum -y install unzip",
          "     elif cat /etc/system-release|grep -i 'Amazon Linux release 2' ; then ",
          "       sudo yum install -y https://dl.fedoraproject.org/pub/epel/epel-release-latest-7.noarch.rpm",
          "       sudo yum install -y ansible",
          "       sudo yum -y install unzip",
          "     elif cat /etc/system-release|grep -i 'Amazon Linux AMI' ; then ",
          "       sudo pip install ansible --upgrade",
          "       sudo yum -y install unzip",
          "     elif cat /etc/system-release|grep -i 'Red Hat Enterprise Linux' ; then ",
          "       sudo yum -y install python3-pip",
          "       sudo pip3 install ansible",
          "       sudo yum -y install unzip",
          "     else",
          "       echo \"There was a problem installing or updating the required tools for the document. You can review the log files to help you correct the problem.\" >&2",
          "       exit 1",
          "     fi",
          "   elif cat /etc/issue|grep -i Ubuntu ; then ",
          "     UBUNTU_VERSION=$(cat /etc/issue | grep -i ubuntu | awk '{print $2}' |  awk -F'.' '{print $1}')",
          "     sudo apt-get update",
          "     if [ $(($UBUNTU_VERSION > 18)) == 1 ]; then",
          "       sudo DEBIAN_FRONTEND=noninteractive apt-get install python3-pip -y",
          "       sudo pip3 install ansible --upgrade",
          "     else",
          "       sudo DEBIAN_FRONTEND=noninteractive apt-get install python-pip -y",
          "       sudo pip install ansible --upgrade",
          "     fi",
          "     sudo DEBIAN_FRONTEND=noninteractive apt-get install unzip -y",
          "   else",
          "     echo \"There was a problem installing or updating the required tools for the document. You can review the log files to help you correct the problem.\" >&2",
          "     exit 1",
          "   fi",
          "fi",
          "echo \"Running Ansible in `pwd`\"",
          "#this section locates files and unzips them",
          "for zip in $(find -iname '*.zip'); do",
          "  unzip -o $zip",
          "done",
          "PlaybookFile=\"{{PlaybookFile}}\"",
          "if [ ! -f  \"${PlaybookFile}\" ] ; then",
          "   echo \"The specified Playbook file doesn't exist in the downloaded bundle. Please review the relative path and file name.\" >&2",
          "   exit 2",
          "fi",
          "if  [[ \"{{Check}}\" == True ]] ; then",
          "   ansible-playbook -i \"localhost,\" --check -c local -e \"{{ExtraVariables}}\" \"{{Verbose}}\" \"${PlaybookFile}\"",
          "else",
          "   ansible-playbook -i \"localhost,\" -c local -e \"{{ExtraVariables}}\" \"{{Verbose}}\" \"${PlaybookFile}\"",
          "fi"
        ]
      }
    }
  ]
}

追加修正した箇所はOS判定の部分で、先にAmazon Linux 2の判定に引っかからないよう、if文の先頭にAmazon Linux release 2023を追加し、else ifでAmazon Linux 2の判定とするようにしています。

また、Amazon Linux 2023Ansibleをインストールする方法としては、Red Hat Enterprise Linuxの手順がそのまま利用できたので、 そのままコピペしています。

以下追加修正箇所抜粋。

追加修正した条件判定部分抜粋
          "   if [ -f  \"/etc/system-release\" ] ; then",
          "     if cat /etc/system-release|grep -i 'Amazon Linux release 2023' ; then ",
          "       sudo yum -y install python3-pip",
          "       sudo pip3 install ansible",
          "       sudo yum -y install unzip",
          "     elif cat /etc/system-release|grep -i 'Amazon Linux release 2' ; then ",
          "       sudo yum install -y https://dl.fedoraproject.org/pub/epel/epel-release-latest-7.noarch.rpm",
          "       sudo yum install -y ansible",
          "       sudo yum -y install unzip",

上記を見て分かる通りAmazon Linux 2とは異なりpipによるインストールとなることから、yum・dnfによる管理では無くなるためご注意ください。

また、今回はRed Hat Enterprise Linuxの判定部分をそのままコピペしてきたので修正していませんが、気になる方はyumの部分をdnfに変更しても問題ありません。(yumdnfにリンクされているので内部的には変わりませんが)

カスタムドキュメントの実行

やることは通常のRun Commandを実行する場合と変わらず、ドキュメント指定する際に先程作成したカスタムドキュメントを指定するだけです。

条件式以外はAWS公式のドキュメントと変えていないので、AWS-ApplyAnsiblePlaybooksと同じように指定すれば実行できます。

おわりに

まだ登場して間もないため、対応していないサービスも多いですが、各サービスともに順次Amazon Linux 2023に対応していくと思うので、今回のような対応を行わなくてもすぐにAWS公式で対応してくれるかと思います。

Amazon Linux 2023でもいち早くAnsibleのドキュメントを使いたいという方はAWS公式で対応するまでの暫定対処として参考にしてもらえればと思います。

1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0