見出し画像

スペースマーケットの事例で考える「サーバレスで何かを作ること」について

こんにちは!
Hulu、Amazon Prime、Netflix に続き、ディズニー+も契約してコンテンツ選び放題エンジニア藤田です。

MCU 作品は映画について多く語られがちですが、実はドラマシリーズもこんなに豊富なんですよ。
全部見ておかないと気が済まない自分はディズニー+契約に踏み切りました。

さて、そんな引きこもりエンジニアが今回「サーバレス」についての記事を書かせていただきました。

「サーバレス」という言葉も Web 業界にも浸透して、そのプラクティスそのものに "目新しさ" のようなものはなくなってきたように思える昨今ですが、それでも、「サーバレスなアーキテクチャでなにか作ってみる」という意思決定においてはまだまだ向き合うべきことがたくさんあり、奥が深いトピックではないかなと個人的には思っております。

「サーバレス」という言葉をどのように捉えるか

みなさんは「サーバレス」という言葉をどのように捉えていますでしょうか?

へ〜。サーバがないんだ。やるじゃん。
○○○レスって、無駄を削減している感じがして、ナウでヤングでトレンディーな感じするじゃん。
サーバがないってどういうことなんだ?!
じゃあ、一体どこでこのコードを実行してるんだ!!!???

私が数年前初めてこの言葉に出会ったときは、「サーバが要らない」の意味が分からなすぎて泡吹いて白目向いて倒れそうになりました。

そもそも、任意のコードを実行するにも、データを格納するにも、何かしらのサーバ(もしくはストレージ)が必要になるはずです。
この前提を頭に置きつつ、この数年での経験も踏まえると、自分は「サーバレス」=「第三者によるマネージドなサーバ」と捉えるようになりました。
もちろん、厳密には語弊がある表現かもしれませんが、「サーバレス」を他者に説明するときはおおよそ、この概念をベースに説明することが多いです。

① 「サーバレス」と言っても必ずどこかにサーバはある
② そのサーバを自分たち以外の誰かが管理してくれている
③ ②の前提のお陰で、運用の煩わしさからの開放されて、リソース最適化・コスト最適化といったメリットを享受できる

極端な話、自分がメンバーの開発したコードを実行するサーバ環境を整えて、開発メンバーに代わってサーバの運用・リソースの最適化を継続的に行った場合、それは開発メンバーにとっては「サーバレス」と言えるんじゃないかなって思ったりもします笑

現在ではこの「サーバレス」の役割を主要なクラウドベンダーが提供する FaaS や BaaS が担ってくれるケースが多いため、サーバレスの文脈では AWS Lambda, Cloud Functions, Firebase といったサービスの名前があがりやすいのですね。

スペースマーケットでのサーバレスの事例

スペースマーケットでも、ここ数年で AWS のサービスを組み合わせたサーバレス構成のシステムを構築するケースが増えてきました。

ここではサーバレスなワークロードの実例をいくつか紹介いたします。

Security Group の IP ルールの自動追加/自動削除

リモートワークが多いスペースマーケットでは
リリース前のサービスを社員が確認するために、社員の自宅 IP を登録することでネットワークレベルでのアクセス制限を行っています。

そして、そのアクセス制限の定義を比較的簡単に、かつ、安全に変更できるように簡単なシステムを構築しています。

AWS の Security Group への IP ルールの追加は
・Slack の Hubot
・AWS Lambda
・AWS の SDK(EC2 の Security Group 用モジュール)
を組み合わせて、Slack へのチャット経由で行えるようにしました。

IP追加

一方 AWS の Security Group から IP ルールの削除は
・CloudWatchEvent
・AWS Lambda
・AWS の SDK(EC2 の Security Group 用モジュール)
を組み合わせて、定期実行で不要な IP 許可ルールを削除するようにしました。

自動削除

CodePipeline の結果 Slack 通知

スペースマーケットの大部分のシステムの CI/CD の "CD" の部分は AWS の CodePipeline で構築されています。
また、システム毎に開発環境(sandbox と呼びます)・staging 環境・production 環境と複数の環境が存在します。
更に、複数の開発者が異なるプロジェクトで異なるシステムにデプロイを行うので、CodePipeline の実行が入り乱れるのです。
(もう、開発者が Pipeline を回しているのか、Pipeline に開発者が回されているのか分かりません笑)

そのため、Pipeline の実行の結果を Slack 通知で確認できるように簡単なシステムを構築しています。

具体的には
・CodePipeline
・CloudWatchEvent
・AWS Lambda
を組み合わせて、全ての CodePipeline の状態変化イベントを CloudWatchEvent に横流しして、それらのイベントをトリガーに Lambda を実行して、その内容を整形して Slack に通知するようにしています。

CodePIpeline の結果通知 (1)

CodePipeline の実行結果通知専用の Slack チャンネルには↓のような通知が届くようになっています。

スクリーンショット 2021-05-29 15.27.55

スクリーンショット 2021-05-29 15.28.12

主要システムのテストカバレッジレポート通知

主要システムの品質の担保は重要な課題です。
スペースマーケットでは様々な方法でプロダクトの品質を担保する方法に取り組んでいます。
その一つとして、単体テストによるカバレッジの向上を継続的に進めています。
各リポジトリ毎に現状のカバレッジ状況・カバレッジの経過をレポートとして定期的に Slack 通知するようにしています。
(チームの目標として管理しやすい、カバレッジ向上が可視化されるのでモチベーションに繋がる・・・といった効果を期待しています)

カバレッジ状況のデータストアは直感的に扱いやすい Google のスプレッドシートを採用しています。

スプレッドシートへのカバレッジの記録は
・API Gateway
・AWS Lambda
を組み合わせて、サーバレス構成な専用の API を構築しています。
構築した API のエンドポイントを各種の CI サービスのワークフロー内で呼び出すことで自動的に最新のカバレッジを記録するようにしています。

【ブログ用】スプレッドシートへの書き込み

一方で、Slack へのカバレッジ状況の定期レポートの通知は
・CloudWatchEvent
・AWS Lambda
を組み合わせて、定期実行でスプレッドシートに記録されている内容を整形して、所定の Slack チャンネルに投稿するようにしています。

【ブログ用】スプレッドシートからの読み込み&Slack 通知

サーバレスで何かを作るときに考えていること

これまで紹介した事例は比較的、「プロダクトそのものの改善」というよりは 「Developer Experience(開発体験)の改善」 の文脈で行われたものばかりです。
いずれも、自分自身が開発を進めていく中で感じた課題や
開発チームのメンバーの普段の業務を見ている中で「この課題はテクノロジーで解決できないか?」と考えた結果、勝手に導入したものです。
(組織的に明確にプロジェクト化された機能開発ではなく、エンジニア起案で「やってみよう」的な機能開発という意味です)

「何故そうなるのかな?」と考えたのですが

・サーバが常時稼働しないため、ランニングコストをほぼ無視でき、構築前に社内の予算的な調整をあまり必要としない
・解決したい課題/要求が比較的明確で、提供する機能が1つであることが多いため、FaaS との相性が良い
・社内利用がメインなので FasS で懸念されやすい非機能要求面(同時接続数上限、メモリ上限、コールドスタンバイ問題)がある程度許容できるものになりやすい
・(あまりプレッシャーなく)サーバレスでなにか作るの楽しい(^q^)

といった点が理由なのかなと自分は考えました。
逆に、非機能要求がセンシティブになってくる場合や、Lambda や FaaS が抱えるデメリットが大きく影響してくるような場合は、「サーバレスであること」にこだわらないようにしています。
何を選択するにしてもケースバイケースですね。

少し前まではデータストアの選択肢によってサーバレスの採用可否が決まっていました。
(「Lambda x RDS はアンチパターン」と呪文のように繰り返している時期が私にも有りました。)

参考記事

少し前までは「じゃあ、データストアは DynamoDB だなぁ。でも、リレーションをガッツリ使いたいんだよなぁ」という時代でしたね。
今では RDS, DynamoDB, ElastiCache, S3 といった AWS サービスから
Google のスプレッドシートまで、データの保存先の選択肢は広がりました。

私が構築したサーバレスのシステムに関しては、非エンジニアも内容もデータを確認できる Google のスプレッドシートをデータストアとして採用していることが多いです。
(これはデータを確認するときに RDS にクエリを実行したりする手間や現状の運用を想定した選択です)

そういった意味で
「何が Lambda を呼び出すか?」のインプットの部分
「Lambda の何が保存されるか?」のアウトプットの部分
は後から変更可能なように、Lambda の実装をすることも重要ですね。

インプットの部分は

・CloudWatchEvent の定期実行で Lambda を呼び出す
・API Gateway を挟んで API のエンドポイント経由で Lambda を呼び出す
・S3 へのファイル追加イベントをトリガーに Lambda を呼び出す
・別の Lambda から Lambda を呼び出す

アウトプットの部分も

・Lambda の実行の結果、RDS に記録される
・Lambda の実行の結果、スプレッドシートに記録される
・Lambda の実行の結果、S3 に csv が吐き出される
・Lambda の実行の結果、Slack に内容が通知される
・Lambda の実行の結果、別の API や Lambda を呼び出すことになる

といったように、選択肢は様々です。
(ここらへんはマイクロサービス的な話でもありますかね)

「あれ?このパターン作ったことあるぞ」って感覚が大事

今回ご紹介した事例は全て Serverless Application Model(SAM) で構築しています。

SAM ではサーバレスなアプリケーションの構成を CloudFormation のテンプレートを拡張した template.yml ファイルで記述していくことになります。

そして、複数の SAM アプリケーションを作り続けていると、「あれ?この組み合わせは以前作ったことあるぞ」となることが多いです。
インプットとアウトプットの組み合わせを整理すると、Lambda 内で実行するコードの中身やランタイムは全然違っていても、全体のアーキテクチャ自体はパターン化されていくからですね。

そうなると、前回使ったテンプレートを横展開して
少し修正するだけで、比較的簡単に構築することができます。
(サーバレスなシステムの事例の増加に伴って、初期構築のスピードがどんどんあがっていることが実感できました)

定期実行で Security Group のルールを削除して
実行結果を Slack 通知したいんです

こんな要求が出たときに「はいはい、あのパターンね」ってなるぐらいまでは、簡単なサーバレスなアプリケーションをたくさん作ってみるというのがすごく重要だなって思いました。

まとめ

スペースマーケットのサーバレスなシステムの事例を紹介しつつ
何かを作るときに
「どんなシチュエーションならばサーバレスで作りやすそうか?」
「どんなことを考えて設計しているか?」
をご紹介しました。

これらは、あくまでもスペースマーケットという組織内での考え方ではありますが、是非皆様の組織内のサーバレス推進の参考になれば嬉しいです。

とにかく、サーバレスでなにか作るのって楽しいですよ!

エンジニア募集中!

スペースマーケットでは現在 SRE エンジニアを募集中です!
スペースシェアの社会インフラ化を目指して、私たちと一緒にスペースシェアリングプラットフォーム「SPACEMARKET」を創っていきませんか?


この記事が気に入ったらサポートをしてみませんか?