TPA, Ansible, and sudo
======================

TPAはsudoでAnsibleを使用して、ターゲットインスタンスで昇格した特権でタスクを実行します。このページでは、Ansibleがsudoを使用する方法決してTPA固有ではありません、およびTPAで管理されているシステムへの影響について説明します。

TPAにはroot権限が必要です。

- パッケージをインストールするためオペレーティングシステムのネイティブパッケージマネージャーを使用した必須パッケージ、およびpipを使用したオプションパッケージ

- サービスを停止、リロード、および再起動するためPostgres、repmgr、efm、etcd、haproxy、pgbouncerなど

- 他のさまざまなタスクを実行するためたとえば、クラスターファクトの収集、スイッチオーバーの実行、クラスターノードのセットアップ

TPAはsudoを使用できることも必要です。 ``ansible_user: root``
を設定することにより、rootとして直接sshインすることができますが、引き続きsudoを使用して他のユーザーpostgresなどとしてタスクを実行します。

Ansible sudo呼び出し
--------------------

Ansibleがsudoを使用してタスクを実行すると、ターゲットインスタンスに次のようなプロセスが表示されます。

.. code:: shell

   /bin/bash -c sudo -H -S -n  -u root /bin/bash -c \
     ""echo BECOME-SUCCESS-kfoodiiprztsyerriqbjuqhhbemejgpc ; \
     /usr/bin/python2"" && sleep 0

``sudo yum install -y xyzpkg``
のようなものを期待していた人は、これに驚くことがよくあります。一般に、Ansibleのほとんどのタスクは、認識可能なシェルコマンドを実行するのではなく、Pythonインタープリターを呼び出してPythonコードを実行します。
Playbookは\ ``raw``
シェルコマンドを実行できますが、TPAはそのようなタスクをPythonインタープリターをブートストラップするためにのみ使用します。

Ansibleモジュールには、さまざまな複雑さのPythonコードが含まれており、AnsibleプレイブックはYAML形式で書かれた単なるシェルスクリプトではありません。任意のAnsibleプレイブックを実行するのと同じことを行うシェルコマンドを「抽出」する方法はありません。

Ansibleがsudo
`privilegeescalation must be general <https://docs.ansible.com/ansible/latest/playbook_guide/playbooks_privilege_escalation.html#privilege-escalation-must-be-general>`_ を使用する方法の重要な結果が1つあります。つまり、一部の管理者が慣れているように、sudoers.confでsudo呼び出しを特定のコマンドに制限することはできません。ほとんどのタスクはPythonを呼び出すだけです。すべてのコマンドにランダムな文字列がなければ、Pythonへのsudoアクセスを制限できますが、Pythonがrootとして実行されると、とにかくできることに対する事実上の制限がありません。

ターゲットホストでPythonモジュールを実行するのは、Ansibleの動作です。これはどれもTPAに固有ではなく、これらの考慮事項は他のAnsibleプレイブックに等しく適用されます。

おすすめ
--------

- SSH公開キーベースの認証を使用して、ターゲットインスタンスにアクセスします。

- SSHユーザーがパスワードなしでsudoコマンドを実行できるようにします。

- コマンドではなく時間でアクセスを制限します。

TPAは、クラスターを最初にセットアップするとき、またはメンテナンスウィンドウなどに構成を変更するために\ ``tpaexec deploy``
を再度実行するときのみにアクセスが必要です。それまでは、そのアクセスを完全に無効にすることができますsshとsudoの両方を1行の変更で。

デプロイメント中に、Ansibleが行うことはすべて、プレイブックの動作と指定したパラメーターに基づいて予測可能であり、各アクションは、ターゲットインスタンスのシステムログ、およびtpaexec自分自身が実行されるマシンのAnsibleログに表示されます。

Ansibleの焦点は、実行できるアクションにきめの細かい制限を課すことよりも、実行時に何をするのかの可視性を提供することであるため、昇格した特権はスコープではなく時間でより適切に割り当ておよび管理されます。

SSHおよびsudoパスワード
-----------------------

パスワードなしのSSHキー認証とパスワードなしのsudoアクセスを設定することを
*強く* お勧めしますが、パスワードを使用することも可能です。

tpaexecを実行する前に環境で\ ``ANSIBLE_ASK_PASS=yes``
および\ ``ANSIBLE_BECOME_ASK_PASS=yes``
を設定すると、Ansibleはリモートサーバーのログインパスワードとsudoパスワードを入力するように求めます。次に、リモートサーバーでlogin/sudoパスワードプロンプトをネゴシエートし、指定したパスワードを送信しますこれにより、Playbookの実行時間が著しく長くなります。

パスワードの組み合わせを使用してアクセスを制限するよりも、必要がないときに特定のアカウントを介したアクセスを完全に無効にする方が効果的なセキュリティ制御であると考えられるため、この操作モードはお勧めしません。
sshの公開キー認証を使用すると、サーバーにアクセスできる人を効果的に制御できます。許可されたユーザーごとに1つのプライベートキーを保護することは、1つまたは複数の共有パスワードを保護するよりも簡単です。また、ssh
/
sudoレベルでのアクセスを必要な場合に制限すると、メンテナンス期間にパスワードは追加のセキュリティを追加しません。

sudoオプション
--------------

sudoでAnsibleを使用するには、sudoers.confで\ ``requiretty``
を設定しないでください。

必要に応じて、ansible.cfgの\ ``[privilege_escalation]``
セクションで\ ``become_flags`` 、または環境の\ ``ANSIBLE_BECOME_FLAGS``
、またはインベントリの\ ``ansible_become_flags``
を設定することにより、Ansibleが使用するsudoオプション\ ``-H -S -n``
を変更できます。
3つの方法はすべて同等ですが、特定の必要がある場合にのみsudoオプションを変更してください。デフォルトが選択されたのには十分な理由があります。たとえば、パスワードなしのsudoが誤って構成されている場合、\ ``-S -n``
を削除するとタスクがタイムアウトします。

特権エスカレーション構成の管理
------------------------------

デフォルトのsudo構成
^^^^^^^^^^^^^^^^^^^^

デフォルトでは、TPAはターゲットインスタンスでのsudo関連の構成を自動的に管理します。これには、sudoパッケージが存在しない場合のインストール、さまざまなコンポーネントのsudoersファイルの構成が含まれます。

``privilege_escalation_command`` のデフォルト値は\ ``"sudo"``
で、これにより、TPAはsudoのインストールと構成を管理できます。

代替の特権エスカレーションコマンドを使用する
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

環境が別の特権エスカレーションコマンドを使用している場合、
``cluster_vars`` で\ ``privilege_escalation_command``
を設定することにより、代替を使用するようにTPAを構成できます。

.. code:: yaml

   cluster_vars:
     privilege_escalation_command: other_tool  # replaces sudo; may include arguments

この値は、TPAが管理対象アプリケーションに対して生成する各特権エスカレーションコマンドで\ ``sudo``
の直接インプレース置換として使用されます。必要に応じて追加の引数たとえば
``other_tool --flag`` などを含めることができます。

Ansibleのbecomeメカニズムでサポートされている任意の特権エスカレーションコマンドに設定できます。
`Ansible privilege escalation documentation <https://docs.ansible.com/ansible/latest/playbook_guide/playbooks_privilege_escalation.html>`_ を参照してください

サポートされているメソッドの完全なリストについては、

**重要:** ``sudo``
は、EDBで公式にサポートされている唯一の特権エスカレーションコマンドです。代替コマンドを使用する場合、互換性と適切な構成を保証するのは自分の責任です。
EDBサポートは、代替の特権エスカレーションメカニズムに関連する問題を支援する能力が制限されている場合があります。

Ansibleのbecomeメソッドと\ ``privilege_escalation_command``
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

注意する必要がある2つの別個の特権エスカレーション設定があります。

- **``ansible_become_method``**
  は、ターゲットインスタンスでデプロイメントタスクを実行するときにAnsible自分自身が特権をエスカレートする方法を制御します。これは、インベントリまたは\ ``ansible.cfg``
  に設定されたAnsible変数です。

- **``privilege_escalation_command``**
  は、管理対象アプリケーションEFM、repmgr、
  HARPが実行時に呼び出すコマンドを制御して、Ansibleとは無関係に、サービス管理操作の特権をエスカレートします。

これらは目的が異なるため、両方を一貫して構成する必要があります。環境がsudoの代わりに代替ツールを使用している場合、\ ``cluster_vars``
で\ ``privilege_escalation_command`` を設定し、 *および*
Ansibleインベントリまたは\ ``ansible.cfg`` で\ ``ansible_become_method``
と一致するように\ ``ansible.cfg`` を構成する必要があります。

推奨されるアプローチ フックを使用する
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

別の特権エスカレーションコマンドを使用する必要がある場合は、
:ref:`TPA hooks <TPA hooks>` を使用して特権エスカレーションメカニズムを構成することをお勧めします。フックを使用すると、展開中の特定のポイントでカスタムタスクを実行でき、カスタマイズをTPAのコア展開ロジックから分離したまま、特権エスカレーションの構成を完全に制御できます。

たとえば、リポジトリを構成した後、 ``post-repo``
フックを使用して特権エスカレーションコマンドをインストールおよび構成したり、
``pre-deploy``
フックを使用して、メイン展開が開始される前に必要な権限を設定したりできます。このアプローチにより、保守性が向上し、環境固有の要件の管理が簡単になります。

手動構成要件
^^^^^^^^^^^^

代替の特権エスカレーションコマンド\ ``"sudo"``
以外の場合、TPAはsudoパッケージのインストールとsudoers構成をスキップします。
``tpaexec deploy``
を実行する前に、選択した特権エスカレーションコマンドをすべてのターゲットシステムに手動またはフックを使用してインストールして構成する必要があります。

**1. postgresユーザー** のサービス管理権限

特権エスカレーションメカニズムでは、 postgres
systemユーザーがPostgreSQLおよび関連サービスを起動、停止、再起動、およびリロードするためのsystemctlコマンドを実行できるようにする必要があります。これは、フェールオーバーマネージャー
repmgr、
HARP、EFMが自動フェイルオーバー操作中に正常に機能するために必要です。

たとえば、sudoを使用すると、TPAは次の権限を構成します。

::

   postgres ALL=(ALL) NOPASSWD: /bin/systemctl start postgresql
   postgres ALL=(ALL) NOPASSWD: /bin/systemctl stop postgresql
   postgres ALL=(ALL) NOPASSWD: /bin/systemctl restart postgresql
   postgres ALL=(ALL) NOPASSWD: /bin/systemctl reload postgresql

選択した特権エスカレーションシステムで同等の権限を構成する必要があります。

**2. EFMデータベース機能の権限EFMクラスターのみ**

クラスターがフェールオーバーマネージャーとしてEFMを使用している場合、特権エスカレーションメカニズムは、EFMシステムユーザーがpostgresユーザーとして\ ``efm_db_functions``
スクリプトを実行できるようにする必要があります。これは、EFMがヘルスチェックとフェイルオーバー操作を実行するために必要です。

たとえば、sudoを使用すると、TPAは次のように構成します。

::

   efm ALL=(postgres) NOPASSWD: /usr/edb/efm-X.Y/bin/efm_db_functions

特権エスカレーションシステムで同等の権限を構成して、efmユーザーがpostgresユーザーとしてこのスクリプトを実行できるようにします。

ロギング
--------

プレイブックの実行の場合、sudoログは主にPythonの呼び出しを表示します誰かが\ ``sudo -i``
を使用するときにbashの呼び出しのみを表示するのと同様に。

詳細については、syslogには、ターゲットインスタンスでの各モジュール呼び出しの正確な引数が表示されます。そのモジュールが呼び出された理由の高レベルのビューについては、コントローラのansible.logに、そのタスクがしようとしたことと結果が表示されます。

さらに詳細な監査データの独立したソースが必要な場合は、サーバーでauditdを実行し、SELinuxログファイルを使用できます。
bpftrace/bccからさらに詳細なシステムコールレベルの情報を取得できます。たとえば、opensnoopはシステムで開かれているすべてのファイルを表示し、execsnoopはシステムで実行されたすべてのプロセスを表示します。ニーズに応じて、これらのことのいずれかまたはすべてを実行できますが、ロギングの増加に伴うオーバーヘッドの増加という明らかな注意事項。

ローカル権限
------------

:ref:`TPA installation <TPA installation>` 

sudoは、「run これらのコマンドをroot
attemptsで実行する」の短縮形としてのみ言及しています。
TPAがインストールされ、\ ``tpaexec setup``
を実行すると、TPA自分自身はローカルマシンでの昇格した特権を必要としません。ただし、Dockerを使用する場合、Dockerデーモンへの接続が許可されたグループに属するユーザーとしてtpaexecを実行する必要があります。
