TerraformでAkamai配信設定を作ってみる
お久しぶりです、インフラのいわなちゃんさん(@xcir)です。
弊社は複数のCDNを利用していますが、Akamaiを主に利用しており多数の配信設定(プロパティ)を運用しています。
これまでは新規プロパティはAkamai Control Center(ACC/旧LUNA)で作成していましたが、
今回多数のプロパティを作る必要があり既存も含めてTerraformで運用を行えるようにしたので共有します。
既存プロパティをterrafromでapplyするまで
akamai/shellを実行する
akamai/shellはakamai-cliやterraformなどが含まれており、例えばpurgeもACCを使わずにできるので何かと便利です。
1 2 3 4 5 6 7 8 9 10 11 12 |
$ docker run --rm -it --name akamai -v $HOME/.edgerc:/root/.edgerc akamai/shell ___ __ _ / | / /______ _____ ___ ____ _(_) / /| | / //_/ __ `/ __ `__ \/ __ `/ / / ___ |/ ,< / /_/ / / / / / / /_/ / / /_/ |_/_/|_|\__,_/_/ /_/ /_/\__,_/_/ =============================================================== = Welcome to the Akamai Docker Image = =============================================================== = Project page: = = https://github.com/akamai/akamai-docker = =============================================================== |
起動時の指定として先ほど配置した.edgercを/root/.edgercにマウントする必要があります。
プロパティのexportを行う
1 2 3 4 5 6 7 8 9 10 11 |
Akamai DevOps [/workdir] >> mkdir your-property-name Akamai DevOps [/workdir] >> akamai -s default terraform export-property --tfworkpath your-property-name your-property-name Fetching property your-property-name [OK] Fetching group [OK] Fetching property version [OK] Fetching property rules [OK] Fetching product name [OK] Fetching hostnames [OK] Fetching activation details [OK] Saving TF configurations [OK] Terraform configuration for property 'your-property-name' was saved successfully |
1 2 3 4 5 6 7 8 |
Akamai DevOps [/workdir] >> cd your-property-name/ Akamai DevOps [/workdir/your-property-name] >> find . ./property-snippets ./property-snippets/main.json ./variables.tf ./import.sh ./property.tf |
1 2 3 4 5 6 7 |
$ ls Compressible_objects.json Enable_H2_H3.json main.json $ grep -A1 -B1 json main.json "children": [ "#include:Compressible_objects.json", "#include:Enable_H2_H3.json" ], |
また子ルールがあると同一階層に別名のjsonがありますが、その場合でも基点はmain.jsonでそこからincludeされています。
Terraformでapplyまで行う
1 2 3 4 5 6 7 |
Akamai DevOps [/workdir/your-property-name] >> sh import.sh Initializing the backend... Initializing provider plugins... ... your Terraform state and will henceforth be managed by Terraform. |
1 2 3 4 |
Akamai DevOps [/workdir/your-property-name] >> terraform apply data.akamai_property_rules_template.rules: Reading... ... Apply complete! Resources: 0 added, 1 changed, 0 destroyed. |
設定のactivateを行う
もちろんACC上で行うことも可能です。
1 2 3 4 5 6 7 |
Akamai DevOps [/workdir/your-property-name] >> akamai -s default pm activate-version -n staging -p your-property-name Following activations are now pending: ╒════════════╤═════════╤═════════╤═══════════════╕ │"PropertyId"│"Version"│"Network"│"Activation Id"│ ╞════════════╪═════════╪═════════╪═══════════════╡ │"prp_XXXXXX"│1 │"STAGING"│XXXXXXXX │ └────────────┴─────────┴─────────┴───────────────┘ |
運用にどう乗せるか
Akamai特有のterraform運用の難しさ
設定項目と変更が多い
すべての機能をTerraformで制御できない
- プロパティを作成してActivateする(Staging/ProductionのどちらでもOK)
- DS2側にプロパティを追加してActivate
- プロパティにDS2のbehaviorを追加してActivate
ACCとterraformのどちらも使う
akamai-tf-tools
https://github.com/xcir/akamai-tf-tools
akamai-docker.sh
- 現在のパスを/workdir/mountにマウント
- 抜ける際にプロパティの格納先(/props)とワークディレクトリ(/work)を実行ユーザでchown
1 |
AKHOME=/home/foo ./akamai-docker.sh |
get_property.sh [property name] [property ver(option)]
get_all_property.py
maintenance.py
- -f tfstateがあるパスを削除する
- -x 実行が必要なコマンドをサジェストするだけでなく実行する
- maintenance.pyでアクティベートを行っていない設定を取得(プロパティV2)
- ACC上で設定編集(V2)
- 再度maintenance.pyを実行するが同一バージョン(V2)のため更新が反映されない
使ってみる
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 |
$ ./akamai-docker.sh ___ __ _ / | / /______ _____ ___ ____ _(_) / /| | / //_/ __ `/ __ `__ \/ __ `/ / / ___ |/ ,< / /_/ / / / / / / /_/ / / /_/ |_/_/|_|\__,_/_/ /_/ /_/\__,_/_/ =============================================================== = Welcome to the Akamai Docker Image = =============================================================== = Project page: = = https://github.com/akamai/akamai-docker = =============================================================== Akamai DevOps [/workdir] >> cd mount/ Akamai DevOps [/workdir/mount] >> ./maintenance.py -f -x ### NO PROPS. Need to run ./get_all_property.py >>>contract: ctr_XXXXX group: grp_XXXX property: XXXX version( stg: 5 prod: 5 latest: 5 get: 5 ) Fetching property XXXX [OK] Fetching group [OK] Fetching property version [OK] Fetching property rules [OK] Fetching product name [OK] Fetching hostnames [OK] Fetching activation details [OK] Saving TF configurations [OK] Terraform configuration for property 'XXXX' was saved successfully --------------------------------------------- ContractID | ctr_XXXX Property | XXXX --------------------------------------------- ... --------------------------------------------- ContractID | ctr_YYYY Property | YYYY --------------------------------------------- Akamai DevOps [/workdir/mount] >> ls props/*|head props/ctr_XXXXX: XXXX YYYY ... Akamai DevOps [/workdir/mount] >> exit chown -R /props /work [sudo] password for xcir: **** |
プロパティの新規作成
- テンプレートをworkディレクトリにコピーして編集
- terraform init~apply
- activate(stg)
- DS2設定
- DS2に新規作成したプロパティを追加
- プロパティにDS2設定を追加
- terraform apply
- 再activate(stg)
- そのほか必要なリソースの作成
- createRPT.py
- createLDS.py
- maintenance.py -f -x
- テスト
- git add ~ push
- activate(prod)
プロパティの更新
- maintenance.py -f -x
- 上記で変更があった場合は一度git add ~ commit
- import.sh
- terraform plan
- ここで差分が出る場合は同一バージョンで変更があったケースなので該当プロパティフォルダを削除
- maintenance.py -f -x
- import.sh
- 設定編集
- terraform plan ~ apply
- activate(stg)
- テスト
- maintenance.py -f -x
- git add ~ push
- activate(prod)
新規プロパティ用テンプレート
今回サンプルとして提供しているテンプレートは公式を改造したものです。
流石に社内のテンプレートをそのまま出せないのでだいぶ機能は削っていますが一通りのことと拡張のしやすさはあると思いますので是非改造して使ってみてください。
まずサンプルを使う前に最低限編集が必要な部分がありますのでそれを紹介した上でどのように使うかを説明します。
akamai.auto.tfvars
1 2 3 4 5 6 7 8 |
# variable edgerc_config_section to define which config_section to use inside the edgerc file. edgerc_config_section = "default" # Recommended value: default # variable contract_id reflects your Akamai Contract ID. contract_id = "コントラクトID(ctr_XXXX)" # variable group_name reflects the name of your group you want to store your config. Groups are part of an Akamai contract. group_id = "グループID(grp_XXXX)" |
コントラクトIDとグループIDの指定が必要です。
akama-cliでpm lgを実行すると現在の一覧が見れます。
1 2 3 4 5 6 7 8 9 10 |
Akamai DevOps [/workdir/mount] >> akamai pm lg -s default ╒═══════════════════════════╤════════════╤═════════════════╤═══════════════╕ │"Group Name" │"Group ID" │"Parent Group ID"│"Contract IDs" │ ╞═══════════════════════════╪════════════╪═════════════════╪═══════════════╡ │"foo" │"grp_XXXXX" │"" │"ctr_X-XXXXX" │ ├───────────────────────────┼────────────┼─────────────────┼───────────────┤ ... ├───────────────────────────┼────────────┼─────────────────┼───────────────┤ │"bar" │"grp_YYYYY" │"grp_XXXXX" │"ctr_X-XXXXX" │ └───────────────────────────┴────────────┴─────────────────┴───────────────┘ |
テンプレートを利用して新規にプロパティを作成する
1 |
$ cp -rp sample-template/ work/test |
テンプレートをworkディレクトリにコピーしてmodules.tfを編集します
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
# modules.tf # version 1.0.0 # This Terraform configuration functions as the configuration to create Akamai modules which acts as logical groupings of Akamai functionality. module "akamai-property" { source = "./akamai-property" edgerc_config_section = var.edgerc_config_section contract_id = var.contract_id group_id = var.group_id # 設定が必要なもの hostname = "ホスト名を設定する" # akamaiで受け付けたいホスト名 edge_hostname = "エッジホスト名を設定する" # 既存でも新規でも origin_hostname = "オリジンホスト名" # example.netなど cpcode_name = "CPコードの名前を設定" # 基本的にホスト名と同一 default_ttl = "デフォルトのTTL設定" # smhd(秒分時日) 30d=30日 # 何かあれば変更するもの product_id = "prd_Download_Delivery" # prd_Download_Delivery, prd_Dynamic_Site_Del ip_behavior = "IPV4" # IPV4(v4only) , IPV6_COMPLIANCE(v4/v6 dualstack) rule_format = "latest" # latest, v2023-05-30 cert_provisioning_type = "CPS_MANAGED" } |
コメントの通りなのでそこまで悩むことはないと思いますが、cdn.example.netのプロパティを作るとしたらこんな形でしょうか
なお、プロダクトはDownloadDeliveryにしていますが、環境に合わせて変更してください。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
# modules.tf # version 1.0.0 # This Terraform configuration functions as the configuration to create Akamai modules which acts as logical groupings of Akamai functionality. module "akamai-property" { source = "./akamai-property" edgerc_config_section = var.edgerc_config_section contract_id = var.contract_id group_id = var.group_id # 設定が必要なもの hostname = "cdn.example.net" # akamaiで受け付けたいホスト名 edge_hostname = "cdn-example-net.akamaized.net" # 既存でも新規でも origin_hostname = "example.net" # example.netなど cpcode_name = "cdn.example.net" # 基本的にホスト名と同一 default_ttl = "1d" # smhd(秒分時日) 30d=30日 # 何かあれば変更するもの product_id = "prd_Download_Delivery" # prd_Download_Delivery, prd_Dynamic_Site_Del ip_behavior = "IPV4" # IPV4(v4only) , IPV6_COMPLIANCE(v4/v6 dualstack) rule_format = "latest" # latest, v2023-05-30 cert_provisioning_type = "CPS_MANAGED" } |
ひとまずこれでプロパティを作成します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 |
$ ./akamai-docker.sh ___ __ _ / | / /______ _____ ___ ____ _(_) / /| | / //_/ __ `/ __ `__ \/ __ `/ / / ___ |/ ,< / /_/ / / / / / / /_/ / / /_/ |_/_/|_|\__,_/_/ /_/ /_/\__,_/_/ =============================================================== = Welcome to the Akamai Docker Image = =============================================================== = Project page: = = https://github.com/akamai/akamai-docker = =============================================================== Akamai DevOps [/workdir] >> cd mount/work/test/ Akamai DevOps [/workdir/mount/work/test] >> terraform init Initializing the backend... Initializing modules... - akamai-property in akamai-property Initializing provider plugins... - Finding latest version of akamai/akamai... - Installing akamai/akamai v5.6.0... - Installed akamai/akamai v5.6.0 (signed by a HashiCorp partner, key ID A26ECDD8F0BCBA73) Partner and community providers are signed by their developers. If you'd like to know more about provider signing, you can read about it here: https://www.terraform.io/docs/cli/plugins/signing.html Terraform has created a lock file .terraform.lock.hcl to record the provider selections it made above. Include this file in your version control repository so that Terraform can guarantee to make the same selections by default when you run "terraform init" in the future. Terraform has been successfully initialized! You may now begin working with Terraform. Try running "terraform plan" to see any changes that are required for your infrastructure. All Terraform commands should now work. If you ever set or change modules or backend configuration for Terraform, rerun this command to reinitialize your working directory. If you forget, other commands will detect it and remind you to do so if necessary. Akamai DevOps [/workdir/mount/work/test] >> Akamai DevOps [/workdir/mount/work/test] >> terraform apply Terraform used the selected providers to generate the following execution plan. Resource actions are indicated with the following symbols: + create <= read (data resources) ... Apply complete! Resources: 3 added, 0 changed, 0 destroyed. Akamai DevOps [/workdir/mount/work/test] >> |
これで作成できたのでひとまずACC上で確認してみましょう
無事設定ができていることが確認できます。
そのままactivateしてもいいのですが、ルールを追加します。
akamai-property/property-snippets/main.jsonを修正してrules/Enable_H2_H3.jsonを追加します。
1 2 3 4 5 6 7 8 9 10 11 12 |
{ "ruleFormat": "latest", "rules": { "name": "default", "behaviors": "#include:behavior-default.json", "children": [ "#include:rules/Compressible_objects.json", "#include:rules/Enable_H2_H3.json" ], "options": {} } } |
再度terraformで適用します。
なおterraformのプラグインがないというエラーが出た場合は再度initしてapplyすればいけます。
さきほどからEnable H2/H3が増えています。
この後はmaintenance.py -f -xを実行すればprops以下に今作成した設定がexportされます。
テンプレートのカスタム
先ほど機能を削ったと書きましたが、削ったのはEnable_H2_H3.jsonのような子ルールです。
他にもPOSTキャッシュやDS2つなぎこみなどの様々なルールがありますが、ここは各々で増やしていけばよいでしょう。
増やし方も簡単です。適当なプロパティでルールを作成してJSONを表示するだけです。
これをrules以下に配置した上で#include:rules/template.jsonとするだけです。
またここで作成したルールはもちろん既存の設定にも適用できます。
exportしたプロパティはprops以下にあるので
props/ctr_[contractID]/[propertyname]/property-snippets/
に利用したいルールjsonをコピーして同じように#includeすれば利用できます。
またすべての設定をテンプレートで実現する必要はなく、他で使いづらいものやテンプレート化しづらいものはACC上で編集してしまえばよいです。
その辺の割り切りが重要です。
最後に
単純にAkamaiのプロパティをexportして編集してterraformでapplyするだけなら簡単なのですが、
いざ実際の運用に乗せようと考えるとACCをどう扱うかという問題にぶち当たります。
今回紹介したフローではterraformで操作した後は消すことでACC/terraformのどちらでも操作ができるようにして解決しました。
このフローはまだ途上で改善が必要なポイントもあるのですがひとまず最初のステップとしては有用だとおもいますので試してもらえれば幸いです。
またテストについては次の記事で紹介します。