BIG-IP Virtual Editionを使ってみる。（その５：Ansibleによる負荷分散設定）

# はじめに
前回は`Ansible`で`BIG-IP`の初期設定を行ったので、今回も「[F5自動化の取り組みとAnsiblex BIG-IP Playbookユースケースのご紹介](https://redhat.lookbookhq.com/automates-tokyo-2020/ansible-f5-webinar-1)」を参考に基本的な負荷分散設定を`Ansible`で作成してみようと思います。

- 【前】[BIG-IP Virtual Editionを使ってみる。（その４：Ansibleによる初期設定）](https://qiita.com/sakai00kou/items/92c73ee329d1cf63318a)
- 【次】[BIG-IP Virtual Editionを使ってみる。（その６：Ansibleによる冗長化設定準備）](https://qiita.com/sakai00kou/items/2e57351609dd801f6472)

# BIG-IPの負荷分散設定
`BIG-IP`の負荷分散設定を行うためには、負荷分散対象となる`Node`の設定、負荷分散対象となる`Node`をまとめた`Pool`の設定、負荷分散を行う`Pool`や負荷分散用IPを定義する`Virtual Server`の設定を行う必要があります。

今回は以下の様な名前の定義を設定していきます。

![構成.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/569912/19f88b74-5f1c-a7cd-bb9b-8a1f4c7493ee.png)

# Ansible Playbookの作成
`Node`、`Pool`、`Virtual Server`は個々にロールが分かれていたほうが管理し易いかと思うので、今回は個々の設定ごとにロールを分けて作成します。

|ロール名|説明|
|:--|:--|
|setup_bigip-node|ノードの設定を行うロール|
|setup_bigip-pool|プールの設定を行うロール|
|setup_bigip-virtual-server|Virtual Serverの設定を行うロール|

## ロールの作成
前回と同様、`ansible-galaxy`のコマンドで`Playbook`雛形を作成します。

```shell:ansible-galaxyコマンドでのロール雛形作成
cd roles/
ansible-galaxy init setup_bigip-node
ansible-galaxy init setup_bigip-pool
ansible-galaxy init setup_bigip-virtual-server
```

## Node用tasksの作成
「[F5自動化の取り組みとAnsiblex BIG-IP Playbookユースケースのご紹介](https://redhat.lookbookhq.com/automates-tokyo-2020/ansible-f5-webinar-1)」では`Pool`の`Pool Menber`の設定を行う際に設定していますが、未作成の`Node`を`Pool Menber`の設定で追加する場合、`Node`の設定は初期設定となってしまいます。

今後、`Node`に対して細かな設定を行うことも考え、今回は`Node`モジュールを使って、先に`Node`を作成するようにします。

```yml:roles/setup_bigip-node/tasks/main.yml
---
# tasks file for setup_bigip-node
- name: BIG-IP 負荷分散ノードの作成
  bigip_node:
    name: "{{ item.name }}"
    description: "{{ item.description }}"
    host: "{{ item.host }}"
    monitors: "{{ item.monitors }}"
    ratio: "{{ item.ratio }}"
    connection_limit: "{{ item.connection_limit }}"
    rate_limit: "{{ item.rate_limit }}"
    state: "present"
    provider: "{{ bigip_provider }}"
  delegate_to: "{{ bigip_delegate_to }}"
  notify: save_config
  loop: "{{ bigip_node }}"
```

## Pool用tasksの作成
`Pool`の設定には、箱となる`Pool`の設定と、`Pool`に所属する`Node`を指定する`Pool Member`の設定を行う必要があります。

`Pool`の設定は今までと同様、`Ansible`の`Pool`モジュールの説明を参考に、必要となる設定を記載していきます。

`Pool Member`の設定は、作成した`Pool`に`Node`を割り当てるため、割り当てる`Node`数分、`bigip_pool_member`モジュールを繰り返す必要があります。

「[F5自動化の取り組みとAnsiblex BIG-IP Playbookユースケースのご紹介](https://redhat.lookbookhq.com/automates-tokyo-2020/ansible-f5-webinar-1)」では、[マジック変数](https://docs.ansible.com/ansible/2.9_ja/reference_appendices/special_variables.html)である、`hostvars`と`groups`を使って、インベントリファイルに記載したホストグループのノードを繰り返す処理を行っていますが、今回作成した`Playbook`のように、`Pool`の値も、`Node`の値も変数で呼び出すようにした場合、`hostvars`と`groups`を使用した方法では`Pool`の変数値を思った通りに取得できなかったため、グループ変数に`Node`の設定を記載するようにしました。

```yml:roles/setup_bigip-pool/tasks/main.yml
---
# tasks file for setup_bigip-pool
- name: BIG-IP 負荷分散プールの作成
  bigip_pool:
    partition: "Common"
    name: "{{ item.name }}"
    description: "{{ item.description }}"
    monitors: "{{ item.monitors }}"
    lb_method: "{{ item.lb_method }}"
    priority_group_activation: "{{ item.priority_group_activation }}"
    state: "present"
    provider: "{{ bigip_provider }}"
  delegate_to: "{{ bigip_delegate_to }}"
  notify: save_config
  loop: "{{ bigip_pool }}"

- name: BIG-IP 負荷分散プールメンバの作成
  bigip_pool_member:
    partition: "Common"
    host: "{{ item.host }}"
    name: "{{ item.name }}"
    pool: "{{ item.pool }}"
    port: "{{ item.port }}"
    state: "present"
    provider: "{{ bigip_provider }}"
  delegate_to: "{{ bigip_delegate_to }}"
  notify: save_config
  loop: "{{ bigip_pool_member }}"
```

## Virtual Server用tasksの作成
`Virtual Server`の`tasks`は特に難しいこともないため、`Node`等と同じく、`Ansible`のモジュールの説明を参考に作成します。

```yml:roles/setup_bigip-virtual-server/tasks/main.yml
---
# tasks file for setup_bigip-virtual-server
- name: BIG-IP Virtual Serverの作成
  bigip_virtual_server:
    partition: "Common"
    name: "{{ item.name }}"
    description: "{{ item.description }}"
    destination: "{{ item.destination }}"
    port: "{{ item.port }}"
    pool: "{{ item.pool }}"
    enabled_vlans: "{{ item.enabled_vlans }}"
    snat: "{{ item.snat }}"
    profiles: "{{ item.profiles }}"
    state: "present"
    provider: "{{ bigip_provider }}"
  delegate_to: "{{ bigip_delegate_to }}"
  notify: save_config
  loop: "{{ bigip_virtual_server }}"
```

## コンフィグ保存用handlerの作成
前回と同様、設定変更が行われた場合にコンフィグを`save`する設定を行います。

作成した3つのロールすべての`handlers`に以下の設定を行って下さい。

```yml:roles/setup_bigip-xxxxx/handlers/main.yml
---
# handlers file for setup_bigip-xxxxx
- name: save_config
  bigip_config:
    save: "yes"
    provider: "{{ bigip_provider }}"
  delegate_to: "{{ bigip_delegate_to }}"
```

## グループ変数の作成
前回作成したグループ変数に今回使用する変数を追記します。

各種設定は環境に合わせて修正して下さい。

```yml:group_vars/bigip.yml
---
（前回分設定省略）
# 負荷分散ノード設定
bigip_node:
  - { name: "web01", description: "Web Server 1", host: "10.2.0.10", monitors: ["/Common/icmp"], ratio: "1", connection_limit: "0", rate_limit: "0" }
  - { name: "web02", description: "Web Server 2", host: "10.2.0.11", monitors: ["/Common/icmp"], ratio: "1", connection_limit: "0", rate_limit: "0" }

# 負荷分散プール設定
bigip_pool:
  - { name: "web_pool", description: "Web Server Pool", monitors: ["/Common/http"], lb_method: "round-robin", priority_group_activation: "0" }

# 負荷分散プールメンバ設定
bigip_pool_member:
  - { pool: "web_pool", port: "80", host: "10.2.0.10", name: "web01" }
  - { pool: "web_pool", port: "80", host: "10.2.0.11", name: "web02" }

# Virtual Server設定
bigip_virtual_server:
  - { name: "web_vs1", description: "Virtual Server 1", destination: "10.1.0.10", port: "80", pool: "web_pool", enabled_vlans: "all", snat: "Automap", profiles: ["http"] }
```

## ホスト変数の作成
今回はホスト単体に設定する内容は無いため、設定の追加は不要です。

## グループごとのロール実行ファイルの作成
前回までの分含め、今回作成した`setup_bigip-node`、`setup_bigip-pool`、`setup_bigip-virtual-server`ロールを追記します。

```yml:bigip.yml
---
- hosts: bigip
  gather_facts: no
  roles:
    - setup_bigip-license
    - setup_bigip-initconf
    - setup_bigip-node
    - setup_bigip-pool
    - setup_bigip-virtual-server
```

## 全体のロール実行ファイルの作成
前回のファイルの内容と同じになるので割愛。

# Playbookの依存関係設定
今回作成した3つのロールは、上で紹介した図のような構成となるため、`setup_bigip-node`→`setup_bigip-pool`→`setup_bigip-virtual-server`の順に作成するよう依存関係を設定します。

## metaの作成
依存関係の設定を行うため、`setup_bigip-pool`と`setup_bigip-virtual-server`のロールに以下の設定を行います。

```yml:roles/setup_bigip-pool/meta/main.yml
(略)
#dependencies: []    ←コメントアウトする。
  # List your role dependencies here, one per line. Be sure to remove the '[]' above,
  # if you add dependencies to this list.

dependencies:
  - setup_bigip-node
```

```yml:roles/setup_bigip-virtual-server/meta/main.yml
(略)
#dependencies: []    ←コメントアウトする。
  # List your role dependencies here, one per line. Be sure to remove the '[]' above,
  # if you add dependencies to this list.

dependencies:
  - setup_bigip-node
  - setup_bigip-pool
```

# Ansibleの実行
作成したロールを実行していきます。

```shell:Playbookの実行
ansible-playbook -i hosts-all site.yml
```

# おわりに
今回は一通りの負荷分散の設定を行いました。

次回は冗長化設定を行ってみようと思います。