Ansibleのcopyおよびfetchモジュールを使用した安全なファイル転送
Ansibleはその構成管理機能で有名ですが、制御マシンと管理対象ノード間でファイルを効率的に移動させることは、あらゆるデプロイ戦略の基本的な要件です。カスタム設定ファイルを展開する場合でも、デプロイ成果物をプッシュする場合でも、あるいはシステムログを取得する場合でも、そのプロセスは高速で信頼性が高く、安全でなければなりません。
この記事では、ファイル転送のための2つの主要なモジュール、copyとfetchに焦点を当てます。ここでは、Ansibleの強力なアドホックコマンド構造を利用してこれらのモジュールを活用する方法を実演します。これにより、完全なプレイブックを作成することなく、迅速な一時的なファイル操作が可能になります。このガイドを読み終える頃には、ローカルファイルをリモートシステムに安全にプッシュし、必要なファイルをAnsible制御ノードに引き戻すことに習熟しているでしょう。
前提条件
以下の例を実行する前に、次のものが揃っていることを確認してください。
- Ansible制御ノード: Ansibleがインストールされているマシン。
- インベントリファイル: 管理対象ノードを定義する、動作中のインベントリファイル(例:
/etc/ansible/hosts)。 - 接続性: リモートホストへのSSHキー認証が設定されていること。
すべての例では、インベントリ内のターゲットグループ名はwebserversであると仮定します。
ファイル転送のためのアドホックコマンドの理解
アドホックコマンドは、ターミナルから直接実行される一行のコマンドであり、永続的なプレイブックを必要としない簡単なタスクに最適です。基本的な構造は次のとおりです。
ansible <ホストグループ> -m <モジュール名> -a "key=value key2=value2 ..."
ファイル転送の場合、-m copyまたは-m fetchモジュール名を使用し、必要な引数を-aフラグを介して渡します。
copyモジュール: ファイルをリモートノードにプッシュする
The copyモジュールは、Ansible制御マシン上にあるファイルを1つ以上の管理対象ノードに転送するために使用されます。これは、設定ファイル、スクリプト、または小さなアセットを展開するための標準的な方法です。
copyの主要な引数
The copyモジュールは2つの必須引数を必要とし、構成管理のためにいくつかのオプションの引数を受け入れます。
| 引数 | 説明 | 必須? | 例の値 |
|---|---|---|---|
src |
Ansible制御マシン上のファイルの絶対パス。 | はい | /tmp/config.conf |
dest |
リモート管理対象ノード上のファイルが配置される絶対パス。 | はい | /etc/app/config.conf |
owner |
リモートノード上でファイルが所有すべきユーザー名。 | いいえ | nginx |
group |
リモートノード上でファイルが所有すべきグループ名。 | いいえ | www-data |
mode |
宛先ファイルに設定するパーミッション(八進数)。 | いいえ | 0644 |
backup |
yesの場合、元のファイルを上書きする前にバックアップファイルを作成します。 |
いいえ | yes |
例1: 単純なファイル展開
ローカルにカスタムの今日のメッセージ(motd)ファイルがあり、それをすべてのウェブサーバーにプッシュしたいと仮定します。
# ローカルファイルパス: /home/user/ansible/motd_banner
# リモートの宛先: /etc/motd
ansible webservers -m copy -a "src=/home/user/ansible/motd_banner dest=/etc/motd"
例2: パーミッションと所有権の設定
セキュアな設定ファイルをデプロイする場合、所有者、グループ、および制限されたパーミッション(例:所有者のみが読み書き可能)を指定する必要があります。
# アプリケーション設定ファイルをデプロイし、所有者を 'app_user'、グループを 'devops' とし、
# 所有者のみが読み書き可能(0600)なパーミッションを設定します。
ansible webservers -m copy -b -a "src=/tmp/app_settings.yaml dest=/etc/app/settings.yaml owner=app_user group=devops mode=0600"
-bに関する注意:
-b(または--become)フラグは、リモートの宛先が昇格した権限(/etcへの書き込みなど)を必要とする場合に必要です。
fetchモジュール: リモートノードからファイルを取得する
The fetchモジュールはcopyの逆の操作を実行します。つまり、管理対象ノードからAnsible制御マシンへファイルを検索して取得します。これは、設定ファイルのバックアップ、ログの取得、または診断情報の収集に役立ちます。
fetchの主要な引数
The fetchモジュールは、リモートノード上のソースファイルと、制御マシン上の宛先ディレクトリを必要とします。
| 引数 | 説明 | 必須? | 例の値 |
|---|---|---|---|
src |
リモート管理対象ノード上のファイルの絶対パス。 | はい | /var/log/nginx/error.log |
dest |
ファイルが保存される制御マシン上のディレクトリの絶対パス。 | はい | /tmp/backups/logs |
flat |
yesの場合、結果のファイル名にホスト名の構造が含まれなくなります(複数のホストから取得する場合は非推奨)。 |
いいえ | no(デフォルト) |
重要な違い: 宛先構造
copyモジュールとは異なり、fetchモジュールは、複数のサーバーからファイルを取得する際のファイル名の競合を防ぐために、リモートホスト名に基づいて構造化されたサブディレクトリパスを自動的に作成します。
制御マシン上の結果のパスは次のようになります。
<dest>/<ホスト名>/<src>
たとえば、host1から/etc/nginx/nginx.confを/tmp/backupsに取得すると、次のようになります。
/tmp/backups/host1/etc/nginx/nginx.conf
例3: リモート設定バックアップの取得
実行中の設定ファイルをすべてのウェブサーバーからローカルのバックアップディレクトリに取得するには:
# すべてのウェブサーバーから /etc/nginx/nginx.conf をローカルディレクトリ /tmp/config_backups に取得
ansible webservers -m fetch -a "src=/etc/nginx/nginx.conf dest=/tmp/config_backups"
このコマンドを実行した後、webserver1とwebserver2をターゲットにした場合、ローカルのディレクトリ構造は次のようになります。
/tmp/config_backups/
├── webserver1
│ └── etc
│ └── nginx
│ └── nginx.conf
└── webserver2
└── etc
└── nginx
└── nginx.conf
例4: ホスト構造なしで単一のファイルを取得する(flat=yes)
単一のホストからのみファイルを取得する場合、またはファイルの内容のみが必要で元の構造が不要な場合は、flat=yesを使用できます。これにより、ファイルは宛先フォルダに直接、元のリモートファイル名で保存されます。
# 単一ホストからローカルのヘルスステータスレポートを取得し、直接保存します。
ansible webserver1 -m fetch -a "src=/tmp/health_status.txt dest=/tmp/reports flat=yes"
# 結果のパス: /tmp/reports/health_status.txt
警告:
flat=yesは、単一のホストをターゲットにしている場合、または後続の実行でファイルを上書きする意図がある場合にのみ使用してください。Ansibleは競合を防ぎません。
ベストプラクティスとセキュリティに関する考慮事項
Ansibleを使用してファイルを管理する場合、セキュリティとべき等性が最も重要です。
1. copyで常にパーミッションを設定する
modeとownerを明示的に定義せずに設定ファイルをプッシュしないでください。リモートシステムのデフォルトのumaskに依存すると、SSHキーやデータベースの認証情報などの機密ファイルが過度に緩いアクセス権を持つことになる可能性があります。
# 悪い習慣(umaskから導出されたモード)
- name: 不安全なキーをデプロイする
ansible.builtin.copy:
src: private.key
dest: /etc/app/private.key
# 良い習慣(アクセスを明示的に制限する)
- name: セキュアなキーをデプロイする
ansible.builtin.copy:
src: private.key
dest: /etc/app/private.key
mode: '0600'
owner: root
2. 重要な変更にはbackup=yesを使用する
既存の重要なファイル(例:/etc/sudoers)を上書きするためにcopyを使用する場合は、backup=yesを含めてください。Ansibleは、ファイルを上書きする前にリモートノード上にタイムスタンプ付きのバックアップコピーを作成し、容易なロールバックオプションを提供します。
3. 大容量転送にはsynchronizeモジュールを検討する
copyとfetchは、簡単なアドホック操作や小さな設定ファイルには優れていますが、大規模なディレクトリ構造を転送する必要がある場合や、効率的な差分転送(変更分のみ転送)が必要な場合は、優れたパフォーマンスと管理のためにrsyncを活用するsynchronizeモジュールが推奨されるツールです。
まとめ
The copyモジュールとfetchモジュールは、Ansible管理者のツールキットにとって不可欠なツールであり、インフラストラクチャ全体でファイルを操作するための堅牢で安全な方法を提供します。アドホックコマンドの構文を習得し、主要な引数を理解することで、単純なタスクのために完全なプレイブックを作成するオーバーヘッドなしに、デプロイ成果物を効率的に管理し、必要なデータ取得操作を実行できます。
| モジュール | 方向 | アドホックコマンドの例 |
|---|---|---|
copy |
制御ノード -> 管理対象ノード | ansible all -m copy -a "src=/local/file dest=/remote/path mode=0644" |
fetch |
管理対象ノード -> 制御ノード | ansible all -m fetch -a "src=/remote/file dest=/local/dir" |