dehio3’s diary

仕事、生活、趣味のメモ

Amazon Linux2のログインメッセージをansibleで追加する

f:id:dehio3:20190711140040p:plain

はじめに

サーバにログインした際にプロンプトに表示される情報をカスタマイズする方法です

Last login: Tue Feb 19 16:46:18 2019 from *************.ap-northeast-1.compute.internal

       __|  __|_  )
       _|  (     /   Amazon Linux 2 AMI
      ___|\___|___|

https://aws.amazon.com/amazon-linux-2/
6 package(s) needed for security, out of 14 available
Run "sudo yum update" to apply all updates.

調査

motdはリンクファイル

$ ls -l /etc/motd 
lrwxrwxrwx 1 root root 25 11月 14 16:25 /etc/motd -> /var/lib/update-motd/motd

リンク先のファイルがログイン時の出力と同じ

$ cat /var/lib/update-motd/motd

       __|  __|_  )
       _|  (     /   Amazon Linux 2 AMI
      ___|\___|___|

https://aws.amazon.com/amazon-linux-2/
6 package(s) needed for security, out of 14 available
Run "sudo yum update" to apply all updates.

日次の以下のcronでファイルの内容が更新される

$ cat /etc/cron.d/update-motd 
# Delay a random time between 0 and 360 minutes (6 hours) to avoid having all
# instances update at the same time.
RANDOM_DELAY=360
@daily root /usr/bin/systemctl --quiet restart update-motd

update-motdの状態

$ systemctl status update-motd
● update-motd.service - Dynamically Generate Message Of The Day
   Loaded: loaded (/usr/lib/systemd/system/update-motd.service; enabled; vendor preset: enabled)
   Active: active (exited) since 火 2019-02-19 03:01:07 JST; 14h ago
 Main PID: 8054 (code=exited, status=0/SUCCESS)
   CGroup: /system.slice/update-motd.service

unitの詳細

$ cat /usr/lib/systemd/system/update-motd.service
[Unit]
Description=Dynamically Generate Message Of The Day
After=network-online.target

[Service]
Type=oneshot
ExecStart=/usr/sbin/update-motd
RemainAfterExit=yes

[Install]
WantedBy=multi-user.target

実行コマンド

$ cat /usr/sbin/update-motd
#!/bin/bash

################################################################################
# Copyright 2011 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You may not
# use this file except in compliance with the License. A copy of the License is
# located at
#
#     http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is distributed on
# an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
# or implied. See the License for the specific language governing permissions
# and limitations under the License.
################################################################################

if [ $(/usr/bin/id -u) -ne 0 ]; then
    echo "You are not root"
    exit 1
fi

# Parse the few supported options
case "$1" in
    --enable)
        rm -f /var/lib/update-motd/disabled
        exit 0;;
    --disable)
        mkdir -p /var/lib/update-motd/
        touch /var/lib/update-motd/disabled
        exit 0;;
    '' | --force);;
    *)
        echo "update-motd [option]"
        echo "    --disable: Disable update-motd"
        echo "    --enable: Enable update-motd"
        echo "    --force: Ignore disabled setting"
        exit 1;;
esac

# Just exit if update-motd is disabled and --force wasn't passed
if [ -e /var/lib/update-motd/disabled ] && [ "$1" != "--force" ]
then
    exit 0
fi

if [ -d /etc/update-motd.d ]; then
    TMPFILE=$(mktemp --tmpdir motd.XXXXX)
    if [ -f /etc/motd.head ]; then
        cat /etc/motd.head >> $TMPFILE
    fi
    # Simulated run-parts, wildcards in bash are expanded sorted
    # Skip files ending in ~ or ,
    for part in /etc/update-motd.d/*[^~,]; do
        # Skip .rpmnew, etc.
        [[ $part =~ \.rpm* ]] && continue
        # Run only if it's a regular file and executable
        if [ -f $part ] && [ -x $part ]; then
            TMPPART=$(mktemp --tmpdir motd.partXXXXX)
            if (timeout 10s $part > $TMPPART); then
                cat $TMPPART >> $TMPFILE
            fi
            rm -f $TMPPART
        fi
    done
    if [ -f /etc/motd.tail ]; then
        cat /etc/motd.tail >> $TMPFILE
    fi
    # Only actually do the replacement if there is something in there
    if [ -s $TMPFILE ]; then
        # mktemp creates files with only user read-write permissions
        chmod go+r $TMPFILE
        mv $TMPFILE /var/lib/update-motd/motd
    else
        # Don't leave temp files
        rm -f $TMPFILE
    fi
fi

/etc/update-motd.d配下の実行ファイル

$ ls -l /etc/update-motd.d/
合計 16
-rwxr-xr-x 1 root root 146 11月  7 08:29 30-banner
-rwxr-xr-x 1 root root  67  1月 31 07:20 50-amazon-linux-extras-news
-rwxr-xr-x 1 root root 808 11月  7 08:29 70-available-updates

実行ファイルの内容

$ cat 30-banner 
#!/bin/sh
cat << EOF

       __|  __|_  )
       _|  (     /   Amazon Linux 2 AMI
      ___|\___|___|

https://aws.amazon.com/amazon-linux-2/
EOF

対応

/etc/update-motd.d配下に、ログイン時に出力したいメッセージを出力するシェルを配置すればいい。 ファイルを配置後以下のコマンドを実行して/etc/motdを更新する。

sudo /usr/sbin/update-motd

ansible role

motd-message
├── handlers
│   └── main.yml
├── tasks
│   └── main.yml
└── templates
    └── 99-login-message.j2
handlers/main.yml
- name: update motd
  systemd:
    name: update-motd
    state: restarted
tasks/main.yml
- name: Setup motd file
  template:
    src: 99-login-message.j2
    dest: /etc/update-motd.d/99-login-message
    mode: 0755
  notify: update motd
  when: ansible_distribution == 'Amazon'
templates/99-login-message.j2
#!/bin/sh
cat << EOF

{{ motd_message }}

EOF
ansible-playbook

定義方法はなんでもいいけど、以下の変数でメッセージを定義

#############################################################
# /etc/motd setup parameter
#############################################################
motd_message: |
  !!注意!!
  各パッケージ構成管理はansibleにて実施しているため、変更する場合はansibleを使用してください!!

参考

dev.classmethod.jp