Upgrade to Pro — share decks privately, control downloads, hide ads and more …

プログラマ三大美徳を実現するデプロイフローを目指して

 プログラマ三大美徳を実現するデプロイフローを目指して

PHPerKaigi 2021 の発表で使ったスライドです。

Tomoya-Suzuki

March 28, 2021
Tweet

More Decks by Tomoya-Suzuki

Other Decks in Programming

Transcript

  1. プログラマ三大美徳を実現するデ プロイフローを目指して PHPerKaigi 2021 鈴木智也(@yamotuki)

  2. プログラマの三大美徳 とは Wikipedia によれば 1. 怠惰(Laziness) 2. 短気(Impatence) 3. 傲慢(Hubis)

    • プログラマ三大美徳を唱え始めたのは Perl 開発者のラリー・ウォール • 効率や再利用性の重視・処理速度の追求・品質にかける自尊心
  3. 怠惰 • デプロイはいつも同じことの繰り返しでめんどくさすぎる!!!!! • 同じことなら自動化させろ!!!!

  4. 傲慢 • デプロイ手順ミスってエラーとかダサすぎ!!!!! • 自動化させろ!!!!!!! 

  5. 短気 • デプロイするのに2時間もかけてられないよ!!!! • 秒で終わって!!!

  6. デプロイって面倒ですよね

  7. リリース関係のステップ • PRマージ • release ブランチの作成 • 必要に応じて修正やリリースフラグ変更 • release

    タグの作成 • dev環境デプロイ • 本番デプロイ ◦ DB migrate ◦ memcached の cache clear ◦ その他最適化(view cache, route cache) ◦ Elasticsearch の index 更新
  8. 弊社で自動化されている部分 • PRマージ(approveされたら自動) • release ブランチの作成(コマンド一発、pushまで) • 必要に応じて修正やリリースフラグ変更(手動でPR) • release

    タグの作成(コマンド一発、pushまで) • dev環境デプロイ(pushされたら勝手にデプロイ) • 本番デプロイ ◦ circle CIからワンクリック ◦ DB migrate(自動) ◦ memcached の cache clear(自動) ◦ その他最適化(view cache, route cache) (自動) ◦ Elasticsearch の index 更新 (自動)
  9. この状態までどれくらいかかったの? • サービスリリースは 2018.04 • 約2年半

  10. 時間かかりすぎじゃね?

  11. 自動化やらない言い訳 • 人数が少ないからやってる時間ない • プロダクトが当たってない(売り上げ0)なので機能追加優先 • どこ自動化したらいいかわからない • 自動化するという発想がない

  12. 自動化する理由が出てきた • 売り上げがたった • このまま会社伸びていきそう • 開発者増えた • インフラコンポーネント増えてフローも複雑に。手動辛い •

    各種オペレーションに時間取られすぎて機能追加も疎かになる
  13. 何より・・・ めんどくさいことはしたくない!!! プログラマはこれが大事です。

  14. ベンチャーの成長 とデプロイフローの歴史 どういうフェーズで自動化を進めてきたか?

  15. 15 事業売却と資金調達で次のステージへ
 業界初の買い手の顔が見えるM&Aプラットフォーム


  16. 会社や事業買いませんか? 出資しませんか? 求社広告を掲載 こういう会社を買いたい! 出資したい! プロダクト概要

  17. 2018年1月 • プロダクト作り始め • CircleCI 導入。だけどテストだけ自動化。 • エンジニア(現CTO荒井)一人 2018年4月 •

    プロダクトリリース こ こ
  18. 2018年8月 • 鈴木(私)が2人目エンジニアとして入社 • develop ブランチをそのままデプロイ ◦ eb deploy macloud-dev

    ◦ eb とは AWS ElasticBeanstalk というEC2やLB、オートスケールの管理などやってくれる • AWS ElasitcBeanstalkコンソールから本番に手動デプロイ • 検索サーバのindex更新は手動 • 環境設定は手動 • PMなし。デプロイはエンジニアがやりたい時にやる • DB migrate, cache clearは手動 ◦ 次ページで詳しく こ こ
  19. 「DB migrate, cache clearは手動」 の詳細 • (雑に)サーバ1台の場合のeb deploy の内部的ステップ 1.

    zipでS3にコードが上がる 2. コードがサーバ内に配置される 3. 即座にLB経由でアクセスがくる • 2のタイミングで急いで手動でコマンド ◦ php artisan migrate ◦ php artisan cache:clear • 実行遅れると ◦ DBの状態が古いのでコードと食い違いエラー • 詳細はこちら ◦ https://tech.macloud.jp/entry/2020/01/08/121733
  20. じゃあ自動化した方がいいね • とはならなかった!!(当時) • なぜならユーザ数が少なすぎて、ほとんどエラーにならないから

  21. 2019年05月 • 津崎(@zackey2)さん入社。エンジニア3人目 • git flow を手動で運用開始 • しばらく運用定まらず、定式化されるまでマニュアル運用 導入目的

    • developブランチ からリリース(①) • 無関係な②をコミットしてから問題が発覚!! • 修正(③)を develop に入れてリリースせざるをえない • ②もしれっと本番デプロイされてしまう • hotfix を導入したい! こ こ
  22. 2019年10月 • 4人目エンジニア久保田(@kubotak_public)さん入社 • CircleCIによるリリースフローを導入 🎉 ◦ ただし、デプロイだけで、 migrate などは未だ手動

    図 こ こ
  23. 2019年11月 • 徐々に募集記事が増えてきて、検索体験を向上させたい • 初めてのElasticsearchの index の mapping(型情報)更新 • ダウンタイム無しで

    index 更新したい 方法 • APIエンドポイントを叩くと、新しい型情報で index を作成 • 定期更新バッチでは新旧二つの index を同時更新 • 手動で alias を切り替える • 更新頻度が低いのでとりあえず手動で運用開始
  24. 2019年12月 • ユーザ同時接続も増えてきた • CircleCI に migrate と cache clear

    の自動化を導入 🎉 • しかし思わぬトラブルが・・・
  25. トラブル • migrate & cache:clear しているはず • でも、WebサーバでDB古いような不整合のエラー 何が起こった? •

    リリース時にサーバー二台に対してデプロイ • キャッシュクリアは各サーバで行われる • リリース中のユーザアクセスで、古いサーバによりキャッシュが再作成 • 新しいサーバで参照してエラー
  26. 解決策 • Laravel の CACHE_PREFIX を使用 • コミットハッシュを入れて、新旧バージョンでキャッシュを仮想的に分離 • やったね!🎉

  27. ※画像はイメージです またも問題が

  28. セッションキャッシュも消しちゃった • セッションもCACHE_PREFIX 設定の影響範囲に入ってた • リリースするたびに全員ログアウトされちゃう • DB に対するキャッシュだけを対象に変更し、解決 🎉

    • 技術詳細はこちら ◦ https://qiita.com/kubotak/items/f4342035d8104555b6e6
  29. 2020年03月 • 5人目エンジニアの濱田(@hamakou108)さん入社 • リリースタグ作成を手動から自動へ 🎉 • reletan script の導入

    やった理由 • リリース方法情報伝達が面倒 • エンジニア増えたのでミス増加の懸念 こ こ
  30. reletan script とは? • reletan とは? ◦ release tantou ◦

    リリース担当! • りりたん指名の風景 👇
  31. reletan script とは? • めんどくさいリリースブランチ作成とタグ作成を半自動化 • local repository を最新に •

    git flow コマンド自体の設定 • 前回タグからの差分PRリスト抽出 • ブランチ作成やタグ作成をリモートに自動反映
  32. 2020年08月 ユーザ数が増え、応答速度問題が頻出 • 最初はチューニング必要ないくらいユーザ数が少なかった • Laravel の route:cacle, view:cache, config:cache

    を有効化 • CircleCIのフローに組み込み こ こ
  33. 同 2020年08月 • 大きな機能のリリースが増えてきた • feature フラグを使用することで、フラグをオフにしてどんどんコードを本番に入れる • ※feature ブランチとして独自進化ブランチは

    やらない ◦ マージする時のコンフリクト解消つら過ぎ この手法の課題 • 環境変数はまだAWS ElasticBeanstalkのコンソールから管理していた (手動) • dev, prod で同じ値を設定するが、オペミスが発生しやすい 解決策 • 環境変数もコードで管理 🎉 • .env.visible と .env.secret を分離して運用負荷は重くならないように • CircleCIでデプロイ前に.envにまとめて巻き込むように
  34. 2020年11月 • PRマージの自動化 • approve されていて、ブランチ最新なら自動マージ こ こ

  35. 自動マージ仕組み • CircleCIで PRのURLは ${CIRCLE_PULL_REQUEST} • Github API の URLに変換

    • マージ可能状態 meageable_state を取得 • 判定OKなら Github API の merge エンドポイントを叩く ◦ 参考: https://docs.github.com/en/rest/reference/repos#merge-a-branch
  36. 2021年01月 • 検索対象の募集記事が増え、検索体験をさらによくしたい • Index更新が頻繁に行われることが想定。自動化 🎉 こ こ

  37. 2021年03月(今!) 募集してます! • 「もっとこういうところ楽できるよ」などコメント歓迎 • 一緒に三大美徳を実現してくれる人

  38. まとめ • 三大美徳実現は1日にして成らず • 振り返ると「もっと早くにやっておけば」は多い • プロダクト&チーム成長と自動化は密接に関係

  39. SNSなど • https://twitter.com/yamotuki • https://qiita.com/yamotuki

  40. その他おまけや没スライドなど

  41. 2019年11月 workerサーバについて • before: メール送信のジョブ実行をWeb経由で実行 ◦ CloudWatch Event -> lambda

    -> Globalに露出しているElasticBeanstalkでジョブ受付 ◦ ジョブ処理を順次行うため、一斉メール送信などで処理がつまる = 他の通知が止まる ◦ ジョブ実行トリガーが Global(トリガだけなのでリスクは低いが、セキュリティ問題) • after: workerサーバを新設し、ジョブ処理をお任せ ◦ Webサーバからジョブを積み、 Workerで並列で処理 ◦ 処理がつまる問題の低減 ◦ 負荷も分散 Worker サーバが増えたがCircleCIでデプロイ自動化されているので安心
  42. 今後の課題 • worker と web が直列でデプロイされ、時間がかかる ◦ Webのコードが先にデプロイされると、古い Workerで実行され、コードが食い違うとエラーになる (多分)

    ◦ 対策案: ▪ ちょっとだけ時間差で workerが先に始まる ▪ IDを引き渡すだけのジョブにすることで問題を緩和 • デプロイフロー以外の確認や社内共有が手動が多い ◦ dev入った後のPMやそれぞれのエンジニアの確認 ◦ リリース後の、リリースリストを slack で共有