Infrastructure as Code―クラウドにおけるサーバ管理の原則とプラクティス(第一版)を読み進める雑メモ

このメモはスマホで入力しているので、Markdownの表示が崩れていると思います

9章
昨日読んだ時点で、スタックにNWやアプリなどを全部いることはアンチパターンであることがわかった。
↓本のスクショ

10章
品質・DevOps的なお話。
でもSIだといつでもデプロイできるわけではないから、そこは考えて読まないといけない
ソフトウェア工学とあるが、厳密に言うとコンピューターサイエンスではなく、技術的DevOpsのお話だね。
IaCを導入しても品質は必ず上がらないのは同意する。
だってVPCと2つのサブネット、Lambda関数2個だけで、自動生成したCloudFormationが450行になるもん。
しかも普通にコードは汚くて、意味変わんない命名までされている。
高速フィードバックって、技術じゃなくてソフトスキルのお話。
ちょっとした軽作業でも作業開始前に進め方を確認したほうがいい。
それで手戻り防止になるから
Gitのお話。
やはりGitHubFlowのような、全体の共有開発ブランチを逐次更新していく方が良い。
でも大規模開発SierはFeatureのFeatureを切って開発をしている。
それだと大きい変更がたくさん生まれてキツイ。
いっそのことリポジトリを分けてしまったほうがいい
テスト環境と本番環境に差分があると、環境差異で本番デプロイが失敗してしまう。
継続的デリバリー≠継続的デプロイである。
理由として、デリバリーはあくまで本番環境で動作ができることを担保する作業であり、デプロイ自体をすることではない。
今までCI/CD構築してきたけど、ずっとデプロイが行われていないmainブランチを本番環境で動く保証があるのかと疑問に思ってきた。
そのモヤモヤ感が解消された感じだ。
ソフトウェアクラフトマンシップはスクラム開発と相性がいいかもしれない。
定期的に課題を話し合う場があるから。
旧機能と新機能の切り替えトグルは不要になっなら、削除しなければいけない。
理由は将来必要と思っても使わなければ、技術負債になるため。
具体的な技術負債としては、コードの複雑度を上げて、システムの理解が難しくなるためだ。

11章
テストの内容
テストピラミッドの話、もう知っているためあまり学びにはならない(別の視点で見れば、理解していること言うことかもしれない)
IaCのテストは意外とアプリのテストとあまり変わらないのかもしれない。
しかしIaCのテストはアプリのテストより、テスト数が少ない。
そのため高カバレッジは目指しにくい
- 単体テスト→構成管理ファイル・IaC
- 結合テスト→サーバー本体
- ローカルVM(Vagrant)もテスト可能
- E2E→デプロイされたサーバー全体
- 実行時間や運用の観点で、テスト数を絞り込まないといけない
- テストサーバのための証明書も必要になる可能性がある
運用テストは高レベルなテストが重要。
しかし運動効率を落としてはいけないため、低レベルのテストは充実させたほうがいい
単純な定義のテストは、IaCのテストとして意味がないらしい。
外部サービスのエラーや障害を検知する仕組みがあったほうがいい
結合テスト用のスタブサーバは簡易的なものでいい。
例えばNginxサーバをテストしたい場合、接続先のAPサーバは固定jsonを返すものでいい。

12章
CD(デリバリー)パイプラインの違い
- デプロイパイプライン = ソフトウェアに対するもの
- 変更管理パイプライン = インフラに対するパイプライン
変更管理パイプラインのメリット
- IaCと本番環境がいつも対応付けられる
- デリバリーの自動化
- コンプラ・ガバナンスの運用が簡単になる
- 変更管理プロセスの軽量化
パイプライン設計のガイドライン
- 全環境において、ツールやプロセス、構成を統一させなければいけない。
- 統一させないといけないもの
- MWやツールのバージョン
- 最低限の冗長化(本番環境で50台のサーバがある場合、検証環境では2台で冗長化する)
- 自動化プロセス
- 統一しなくてもいいもの
- サーバーの台数、スペック
- 統一が難しい場合は、統一の優先順位を考える。
- 統一させないといけないもの
パイプラインは素早くフィードバック返すようにする。
もしパイプラインを使わずに手作業で変更作業が行われていたら、パイプラインの速度改善を行わなければいけない。
もし速度改善ができない場合、実行を定期実行(数時間ごと、夜間実行)に切り替える。
パイプラインで、手動テスト前に自動テストをする
先に自動テストを実行すれば、初歩的な問題は解決可能だから。
テストは出来る限り早く本番環境に近い環境でテストする
本番環境に近い環境で行うテストが遅いと、リリース直前でバグを発見することになるから
パイプラインの基本設計
パイプラインのライフサイクル
CI→ビルド成果物生成→ビルド成果物保管→検証環境にデプロイ→E2Eテスト→手動テスト→本番環境にデプロイ
ビルドの成果物には以下の性質がある
- アトミック
- ポータブル
- 完全性
- 統一性
構成マスター(IaC管理サーバ)でパイプラインのステージ内容・状態、ビルド成果物を管理できる。
マスターレス構成管理の場合は、ビルド成果物は汎用ストレージ(S3やファイルサーバ)に提供される。
デモンストレーションとQAの環境は分けた方がいい。
理由はデモンストレーション前になると環境の取り扱いが慎重なる。
そのため、QA実施が難しくなる。
手動テストや本番環境で起こる問題は、自動テストでキャッチできるように継続的な改良を行う。
パイプラインを使うためのプラクティス
全変更は本番に対応した品質でなければいけない。
本番環境で駄目な変更が見つかってはいけない。
本番環境で発生する理由は、複数人で同じコンポーネントを編集しているため。
防止策としては、GitOpsやIaCのアーキテクチャを見直すこと。
変更を行う際は変更内容をVCSに記録して、最初からパイプラインを回す。
あるステージで失敗した際、全員の作業を中断しなければいけない。
もし中断しなければ、問題が解決しないまま後続作業がコミットされる。
そうして成果物が大きくなり、問題発見が難しくなる。
本番環境を緊急フィックスする場合、パイプラインを通してからロールアウトする。
もし直接フィックスした場合、VCSと本番環境で差分が生まれるから
複雑なパイプラインは、本番環境前にテストする。
ファインパイプライン
IaCにレイヤードアーキテクチャを採用した場合のパイプライン
CIも各レイヤーで単位で実施する。 フィーダーブランチではレイヤー同士がマージされて結合テスト・ビルドが行われる。システムが複雑化すると、フィーダーブランチが多くなり、ダウンタイムが発生してしまう。
もし変更管理のために手作業が発生する場合、システム設計、パイプライン、組織が成長におついていないことになる。
根本解決したい場合は、ファインパイプラインをやめる事を検討した方がいい。
検討一覧
- パイプラインを短くして、チームごとに分割する。
- パイプラインの実行環境をスケールアップ・アウトする