00:06
10月18日、火曜日ですね。
遅刻は朝9時を回りました。
今日も東京の天気がちょっと曇っててですね、微妙な天気なんですけど、
まあ、やっていきたいと思います。
はい、おはようございます。耳のkeethことくわはらです。
では、本日も朝活を始めていきたいと思います。
今日の僕のMacはですね、なんか調子が悪くてですね、再起動したら死にそうだったので、一旦やめておきました。
なので、いつものUSBマイクがですね、多分認識してなく、Macの標準のマイクなので、
また音声今日違うかもしれないですね。
では、今日はやっていきましょう。
記事のタイトルのありとおりで、Fast builds, secure builds, choose two.
両方とも取りましょうみたいなお話ですね。
まあ、いろんな記事をサーッと探してたんですけど、
エンジニアブログ系を探してて、面白そうなタイトルだったので、読んでいこうと思います。
僕が最近、引きの要件に関心が強くてですね、パフォーマンスが速度改善周りのところだったりと、
あとセキュアのところですね。
セキュア周りに関心はあるんですけど、なかなか勉強はできていないっていうので、
お前本当に関心あるのかよってツッコミあるかもしれないですけど、
いや、あるんですよ。
ちゃんと勉強したいと思います。
というわけで、早速今日これを読んでいきたいと思います。
今日の記事はですね、ストライプさんですね。
ストライプさんのソフトウェアエンジニアチームの方ですかね、
ビルドチームっていうチームがあるらしくて、
そこのとあるエンジニアの方の記事を読んでいこうと思っています。
スカラーやPythonで書かれたデータパイプラインから、
テラフォームで定義されたインフラまで、
ストライプのエンジニアは日々様々なプログラミング言語と向き合っています。
Goのソースコードをネイティブバイナリーに、
Javaをバイトコードに、
タイプスクリプトをストライプダッシュボード用のトランスファイルバンドルに変換するように、
複雑なビルドパイプラインに依存しています。
Rubyのようなインタープリター型言語でも、
コード生成プロセスによって、
RPCサービス定義からグラフQLバインディングまでの
すべてを含む何十万ものRubyファイルが作成されます。
すごいですね。
ストライプさん、いろんな技術をゴンゴン導入しているんですね。
いや、これすごいな。
そして、皆さん一瞬、レベルの高さが伺えるなという感じがしますね、既に。
だから、もちろんバックエンド系の言語が多いのかなという感じは、
なんとなく印象はありますね、今のところはですけど。
いやー、僕スカラー書いたことないですよね。
Pythonも書いたことないですよね。
見たことあるんですけど。
テラフォームは勉強し始めた途中なので、
ついていけるかなとちょっと不安ですけど、
頑張って読んでいきましょう。
継続的インテグレーション。
CIシステムというのは、これらのビルドパイプラインをオーケストレーションし、
エンジニアが変更検証するために依存する何万ものテストスイートを
実行する役割となっています。
エンジニアに快適な開発体験を提供するためには、
CIのパフォーマンスを維持することが非常に重要です。
また、CIシステムは最終的に毎日何十億ドルも
処理する成果物を生成するため、
非常に高いセキュリティレベルを満たすことは不可欠です。
スライドでオープンソースの技術と新しいエンジニアリングの組み合わせによって、
これらの2つの要件を満たすCIシステムを提供しています。
03:01
さすが決済のサービスをやられているだけであって、
しかも毎日何十億ドルの処理をやっている。
そういうようなシステムをメンテナンスが作っているというエンジニアチームなので、
そりゃそうよね。
いや、すごいわ。
ちょっと桁が違ったので完全に圧倒されています。
僕はその決済サービスを作ったことはなくて、
今までにECサイトを作ったことがあって、
その時にいろんな決済サービスを使ったことがありますね。
厳密に言うと決済代行サービスですね。
GMOとかGMO後払い、ベリトランス、SNBC、黒猫大和、大和なんたらみたいな。
いろんなものをそのECサイトに連携させるみたいなことをやったことがあります。
APIとか組み込み方って2種類あるんですけど。
実は僕、Stripeさんはその当時僕がやっている頃にまだ知らなかったというか、
日本でも全然聞いたことなくて導入できなかったという事例もあって、
実際僕は触ったこと一回もないので、
いい加減触ってみたいなとずっと思っています。
やっぱ決済周り、何らかの関心はあるんですよね。
興味はあるのでやってみたいと思うんですけど、
Stripeさんはまだ触っていなかったので、
今日改めてこういうエンジニアさんのブログを読んで知れるのは面白そうだなと思いました。
本当はセキュリティバーにもそうですし、
決済で時間を食われるとユーザーの不安がものすごく上がりまして、
システムの信頼性が下がっちゃうので、
ここもしっかり授与しているんだなと思いますね。
FASTとセキュアというのは決済代行サービスではどっちを求められるか確かにそうだなと改めて認識しましたね。
というところで続いていきましょう。
Common Framework for Defining Buildsですね。
ビルドを定義するための共通のフレームワークというところに入ります。
コードベースの量と種類が増えるにつれ、
Stripeというのはビルドとテストのパイプラインを管理するためにバゼルを活用しています。
名前は聞いたような気がしますけど使ったことないですね。
バゼルは特定のスタックでコードをビルドし、
テストするためのルールレシピを定義するための多言語、マルチプラットフォームのフレームワークを提供します。
RulesDockerとかRulesGoとかバゼルに直接組み込まれたJavaルールなど、
多くのルールがオープンソースのコミュニティによって維持されています。
インフラチームというバゼルのカスタムルールセットのヘッドラインサポートを基に、
Ruby、JavaScript、Terraform用の内部ルールセットを定義しています。
私たちのエンジニアはこれらのルールセットを使って、
自分たちのコードに固有のターゲットを宣言し、
ライブラリやサービスの構築とテストを行っています。
各ターゲットは入力ファイルやその他の属性のセットを持つルールをインスタンス化します。
例えば、JavaLibraryルールはGreaterTargetを定義することができます。
GreaterTargetはルールで定義された様々なアクションを読み出して、
libGreater.jarというファイルを構築します。
この場合、JavaLibraryルールはJavaCompilerを読み出すアクションを生成します。
一応サンプルコードが後に載っています。
ロードしてJavaLibraryとかバゼルのファイルを読み込んで、
06:03
JavaLibraryのメソッドを実行しています。
Name.Greaterで総数のファイルをここで指定するという感じですね。
とてもシンプルな一つの例でした。
エンジニアがターゲットを定義した後、
バゼルはその変更を構築し、
テストするために必要な全てのアクションを実行する責任があります。
しかし、この実行フェーズは決して些細なことではありません。
ストライプの規模では急成長するJavaコードベースの構築には
20万以上のアクションを実行する必要があります。
すごいな。20万もアクションがあるんですね。
これらのアクションを一台のマシンでゼロから実行すると、
最大限のコモディティEC2インスタンスであっても数時間かかります。
まあ、そうよね。
バゼルはこの課題を解決するために、
リモートキャッシングとリモート実行という2つの機能を提供しています。
リモートキャッシングは、あるアクションが先に実行されたときの出力を再利用できる機能です。
リモート実行との複数のマシンにアクションを分散させることができます。
やっぱり結局キャッシュは使うんですね。どんなとこ行っても。
以前、サークルCIを結構使ったことがあって、
そのときにもしっかりフローのパイプラインの中で、
前の実行結果とかを次のところにそのまま渡すときがあって、
それを毎回毎回実行するとめちゃめちゃ時間かかったという記憶があるので、
やっぱり実行結果をキャッシュするのはそうですし、
一回一回テストするためにまたインスタンス起動しなきゃいけないので、
内部的に多分コンテナ管理してるんでしょうけど、
そのためにまたまたインストールするところもキャッシュしておいて、
利用するライブラリとかのバージョンも固定しておいて、
であれば最初からインストールしたものを残してそれを使うみたいなことをやってました。
そうしないと一個一個手順全部手続き的にゼロからやり直すと、
リモートマシンでも結構時間かかると思いますので。
なのでキャッシュをすると。
あとはリモートマシンの中で分散してやることができるところですね。
分散で処理を分けるのは結構ですけど、
ちゃんと一連のパイプラインとして最終的に処理の結果を統合できるのかというのが難しそうではあるんですけど、
多分リモートでうまいことやれたなと思いますね。
続いてリモートキャッシングとリモート実行によるBazelのスケーリングというところですね。
確かに次はスケーリングか。
気になりますね。
Bazelのリモートキャッシングと実行サブシステムというのは、
CIシステムのパフォーマンスと効率を向上するための魅力的な機械というのを提供します。
私たちのエンジニアはワークフローにおいて高速なビルドが重要であると常に考えています。
ビルドのパフォーマンスを維持すること、例としては5分以内に終わらせたいと思っていると。
この何ですか、マーク、何だっけ、マークダウンじゃなくて、
まあいいや、指標ですね。
エンジニアの生産性を維持するための核となりますと。
私たちは長手にわたりセキュリティや信頼性と機械にすることなく、
パフォーマンスと効率を向上させるリモートキャッシュと
実行のためのプラットフォーム化を構築するために
多大なエンジニアリングリソースを投入していきました。
これは結構大事ですよね。
1回転のビルドとか実行にめちゃめちゃ時間がかかると
エンジニアとしては開発の時間も遅くなりますし
エンジニア自身のヘイトが溜まってくるんですよね。
09:02
どっちにしろ負のループに入るので
ここに最初に時間をかけて高速化するというのを整備したのは結構いい話だと思いました。
単純な実装に伴うリスクを説明するために
CIビルドがリモートキャッシュに書き込むことを許可した場合の
影響をちょっと考えてみましょう。
悪意のある行為者というのは
ストライプの顧客の請求書を完全に処理するために
信頼されているビジネスクリティカルなバイナリーを
個人の銀行口座に資金を振り分ける破損したバージョンに
置き換えることができちゃうのです。
アクションキャッシュポイズニングから身を守るには
信頼できるソースからのキャッシュへの書き込みのみを
許可することが必要になります。
信頼できるソースというのはアクションを忠実に実行し
その真の出力をアップロードしなければなりません。
幸いなことにリモート実行というのは
バゼルがアクションの実行を信頼できるソースに
委任することを可能にすることで
救いの手を出して述べます。
信頼されたソースのアクションの結果を
リモートキャッシュにアップロードすることを
排他的に許可しますよということですね。
一応それの画像がガッと貼られてますね。
サッドパスとハッピーパスと2つ貼られてますね。
ちゃんとそこで赤いのところも担保してますよと
信頼してる人しか実行できないようになってますよとですね。
具体的にどんなコードになっているかとか
設定になっているかはさすがに
ちょっと述べられなさそうですけど。
続けていきましょう。
信頼できるビルドワーカーを作ることは
言うは安く行うは過多しです。
これは本当その通りですよね。
信頼できるワーカーにバゼルアクションを実行させることは
信頼できるマシンで信頼できない2位のコードを
評価することを意味します。
信頼できないアクションがアクションキャッシュに
直接書き込まれたり
他のコーテナントアクションに
影響を与えたりするのを防ぐことが重要ですと。
リモート実行サービスの最初の実装では
ユーザー空間におけるリナックスカーネルの
オープンソースであるGvisorを使用しました。
またアクションを実行するコンテナイメージを
管理するためにコンテナードと組み合わせています。
Gvisorを利用したサンドボックスにより
権限昇格だけでなく
リナックスカーネルのバグにも強くなりました。
悪意のあるコードを本番環境に送り込むには
複数の強固な保護レイヤーを突破する必要があるため
安心して利用することができました。
またGvisorは最初のワークロードである
GOコードベースの構築では
素晴らしい性能を発揮しましたが
新しいワークロードに直面した時に失速しました。
遅くなったんですね。
JavaScriptのバンドル、Rubyのコード生成、
そしてJavaのコンパイルは
全てGvisorで大きな性能劣化を示しました。
結構デカいですね。
特にGvisorのファイルシステムのエミュレーションは
崩壊なオーバーヘッドを追加することを確認しました。
GOのコンパイルは
主にユーザー空間のCPU計算に拘束されますが
新しいスタックでは一般的なワークロードが
何千ものファイルシステムのシステムコールを発生させます。
この動作はRubyとJavaが数十から数百の
ディレクトリのリスト
それぞれ $loadpath と $classpath を検索して
コードをインポートする方法に大きく起因しています。
12:03
なるほど。
例えば空のRubyユニットテストスイート2を実行すると
500以上のディレクトリからなるロードパスを検索しながら
5.5秒間に60万以上の
ファイルシステムのシステムコールを発生させます。
そういうことですよね。
結局、総あたりで一回ガッとチェックしなきゃいけないってことですよね。
ロードパスに指定されたもの。
なので、毎回毎回それを実行するって本当に
シャレにならないですよね。
しかも、今見た通りですけど
空のユニットテストスイートを実行しても
同じことが行われるのはかなり無駄コストです。
その辺をちゃんと検知するように
裏で設定したんだなと思います。
超高速サンドボックスの探求というのが次のセクションですね。
JVisor のようなアプリケーションカーネルというのは
高いコーバーヘッドを加し
LinuxコンテナのようなOSレベルの仮想化プリミティブは
十分なセキュリティー障壁を持たないため
我々はハードウェア仮想化の検討を開始しました。
まあまあいいよ、結局そこにたどり着くと。
私たちのパフォーマンス目標というのは
数百ミリ秒の起動時間と
IOオーバーヘッドの大幅な削減を特徴とする
KVMベースのマイクロVMソリューションで
ファイヤークラッカーに導かれました。
KVMはLinuxカーネルをハイパーバイザーとして機能させ
ハードウェア仮想化を用いて仮想マシン、VMを実行することができます。
私たちの最初の実験では
有望な結果を得られましたが
ファイヤークラッカーは
ドロップインソリューションには程遠いものでした。
最も興味深い課題は
アクションに入力ファイルを提供することでした。
以前、GVizorさんのBOXでは
オーバーレイFSファイルシステムでアクションを実行し
そのベースには固定のコンテナイメージを
その上のディレクトリ、execルートにアクションの入力
例えば実行するテストファイルなどを配置していました。
アクションには知られていませんが
execルートローカルのブロブキャッシュ
すべての入力ファイルを格納するディレクトリへの
ハードリンクだけで構成されています。
この設計により
ファイルシステムのセットアップのオーバーヘッドを
最初にすることができました。
例えば多くのJavaScriptアクションを実行する場合
各アクションがノードモジュレーションを使って
ファイルシステムのオーバーヘッドを
ファイルシステムのオーバーヘッドを
JavaScriptアクションを実行する場合
各アクションがノードモジュレーションに
同じ150KBのファイル
150Kって書いてあるだけだから
ファイル数かもしれないですね。
2.5GBを必要とする場合を考えてみましょう。
各アクションで2.5GBのデータを繰り返し
コピーするのではなくて
各ファイルを一度ブロブキャッシュにダウンロードしました。
そして各アクションは150Kのハードリンクで構成された
独立したノードモジュレーションを受け取りました。
そういうことをしたんですね。
実態とパスみたいなところですかね。
続いていきましょう。
15:01
しかしFirecrackerまたは一般的なKVMは
ディレクトリを共有するために
OverlayFSに依存する類似の設計をサポートしません。
その代わりにKVMはゲストVMに
ブロックデバイス全体をアタッチすることだけを可能にする
読み方がわからん。
ベースのAPIを公開します。
ハードリンクは同じファイルシステム間でしか有効ではないので
ブロブキャッシュを持つブロックデバイスを各
マイクロVMに直接アタッチする必要があります。
これは単一の同時実行マイクロVMで
うまくいかないかもしれませんが
物理ブロックデバイス
特に同時書き込みを受けるものは
複数回安全にマウントすることはできないです。
各アクションでブロブキャッシュからコピーするという
単純なアプローチでは
急なパフォーマンスペナルティも発生します。
私たちはリモート実行サービスが
1台のマシンで何十もの同時実行アクションを
ピンパックできるような代替手段を必要としていました。
幸いなことにLinuxのLVM
ロジカルボリュームマネージャーは
説得力のあるソリューションを提供してくれています。
現在私たちのリモート実行サービスは
LVMに依存して実行プロセスをオーケストライクションしています。
最終的にLinuxの機能にたどり着いたんですね。
まず我々はアクションの入力を
ブロブキャッシュにダウンロードし続けます。
同時に空のプレースホルダーディレクトディスクと
Linuxカーネルの最適化されたビルドで
Firecracker MicroVM3を起動します。
次にLVMのスナップショット機能を使って
ブロブキャッシュのロンリボリュームの
コピーオンライトのスナップショットを作成します。
このスナップショットはほとんど
物理ディスク領域を占めません。
続いてブロブキャッシュのスナップショットは
RESTful APIを使用して
ブートしたFirecracker MicroVMにアタッチする
ロンリブロックデバイスを提供してくれます。
続いてコンテナードデブマッパースナップショッター
というのがあるんですね。
LVMスナップショットが抽象化するのと
同じ基盤技術で構成されています。
というコンテナードデブマッパースナップショッター
というのを使って
アクションのコンテナイメージ用の
ブロックデバイスを作成しアタッチします。
次にカスタムのイニットプロセスに
VMソケットを介してGRPCリクエストを送信し
両方のブロックデバイスをマウントして
アクションを実行するように指示します。
アクションはオーバーレイFSを使用して
構築された最小限のファイルシステムを公開する
CHルートで実行されます。
最後にブロックキャッシュのスナップショット
というのはマイクロVMの終了後に
実行サービスがアクションの出力にアクセスできるように
二重の目的を提供します。
これもしかして自分たちでやっているとしたら
すさまじい技術力になって
さらに共感をしていますね。
いろんなクラウドサービスも導入しながら
うまいこと連携していると思いますけど
でもコアなところを自分たちで作って
ここの中の人たち
いわゆるDevOps系のことを手掛けている人たちは
なかなか技術レベルが高そうですね。
ここまでコアでやったことに全然ないし
18:01
そういう話をなかなか周りで聞いたこともないので
本当はそういうイベントに参加したら
全然いるのかもしれないですけど
かなりコアなことをやっているなという印象がありました。
小学生かというコメントですね。
続いてはチャンスに満ちた海へ飛び込む
Diving into an Ocean of Opportunities
この新しいサンドボックス戦略というのは
リモートビルドシステムがパフォーマンスを向上させるために
活用する無数のテクニックの一つにすぎません。
私たちのリモートキャッシュサービスというのは
指定されたルートディレクトリから
ファイルとディレクトリの最適的にフラット化されたリストを返すことで
GETツリーRPGに応用しています。
サートパーティーの依存関係でいっぱいの大規模なディレクトリでは
フラット化処理に非常にコストがかかることがあります。
これらのディレクトリはほとんど変更されないので
リモートキャッシュサービス自体がフラット化の結果を
特注のツリーキャッシュにキャッシュします。
そしてGETツリーハンドラーは
ツリーの各レベルの項を並走して操作し
可能な限りツリーキャッシュから取得して
キャッシュされたブランチの評価を短絡的に開票しますよと。
なるほどですね。
しかも今図があるんですけどすごく分かりやすくていいですね。
インディス・イグザンポーであるんですけど
音読しても多分伝わるか分からないですけど
一応どんな例かというと
ソース、クリミネイト、コンポーネンツ、バッジ.tsxファイルを
個別に変更することでGETツリーレスポンの99%以上を
ツリーキャッシュから取得することができますみたいなことが一応書いてます。
ルートディレクトリがトップにいてそこから
フローズみたいな感じの分岐がバーッと下に書いてあって
結果最終的に一番下にいるツリーキャッシュというところから
いろんなものを取ってきてますよということを言って
それをすることで
それぞれの作業を高速化してますよという例の図が載ってます。
後ほどこの記事のリンクも共有しますので見てみてください。
続きましょう。
大規模なディレクトリについて私たちは
アクションが頻繁に変更されないアクションの依存関係をバンドする
スクラッシュFSイメージに依存するという大体戦略の実験を開始しました。
例えばパッケージ.jsonです。
大きなノードモジュールディレクトリの必要な入力ですね。
パッケージ.jsonに対する変更はほとんどありません。
バゼルクライアントというのはアクションのダイジェスト構築に
費やす時間を減らし
キャッシュサービスはGETツリーRPCに費やす時間を減らし
実行サービスはハードリンクの作成数をオーバーメイアス化できました。
これいいですね。結果をハードリンクに依存しなきゃいけないので
作成の時間も大幅に減らすことができた。それはいい話でした。
リモート実行サービスには他にもいくつかのトリックがあります。
例えばディストリビューション層がエグゼキューター上でアクションをスケジュールするときに
他のエグゼキューターがすでに同じアクションを実行しているかどうかをチェックします。
もしそうならリソースを確保してアクションを実行するのではなく
2番目のエグゼキューターが最初の実行の完了時にブロックし
その結果を再利用します。
アクションのマージは特に長いアクションの場合一貫して
21:00
ビルドのパフォーマンスと効率を向上させるのに役立ちます。
バゼルクライアントはアクションの開始後にリモートキャッシュをチェックしないので
この最適化は我々のリモート実行サービスに依存していますよと。
マージするんじゃなくてノーアクションマージってことですね。
一応その図も比較が載ってますよということでした。
本当にそもそもアクションの数が膨大に多いから
いろいろ考えなきゃいけないところがかなり大きいと思います。
それについてさらにパフォーマンスとセキュリティ観点をしなきゃいけないので
ストライプさんまでのデカいシステムとか規模になってくると
なかなかクラウド依存だけじゃどうしても無理だし
最後は自分たちでメンテしなきゃいけないんだろうなって考えると
これぐらい求められるんだろうなっていうところですね。
やっぱりデカい会社に入れば入ると求められる技術レベルも結局は高くなったりするし
見てるものが全世界だったり規模が大きいので
こうなるんだろうなっていうのがあるので
やっぱりデカい会社に技術力が固まるとか集中するイメージは結局僕はあります。
結果論ですけど、余談でした。
これ最後ですかね。
私たちはリモートビルドサービスのパフォーマンスを
信頼性・効率性を向上させるための新しい技術を常に探しています。
例えば、最近LVMのスナップショット性能に匹敵するログ構造ファイルシステムである
NILFSというのを調査しました。
また、システムの成長に伴い
異種混在環境におけるロードバランシングの新しい戦略
つまり、低遅延分散スケジューリング問題の本質的な解決策を探っています。
私たちはFirecrackerのスナップショットサポートについて熱心に研究しており
JVMの起動が重要であるワークロードのレイテンションを低減するのに役立つ可能性があります。
例えば、既にJVMを起動したマイクロVM上でアクションをスケジューリングすることによって
Javaコンパイルを高速化することができます。
エンジニアの変更に対して迅速なフィードバックを提供し
開発ループを強化するCIシステムを提供することはStripeの最優先事項です。
私たちのソリューションはWazelなしでは成り立ちません。
WazelのPrimitiveは当社のエンジニアとプラットフォームチームに
リッチでドメイン固有のビルドおよびテストパイプラインを表現するための基盤を与えてくれます。
組織全体のエンジニアは共有された語彙とツールキットの恩恵を受け
サポート体験を合理化するだけでなく
生産チームにも非常に高いレバレッジのシングルポイントを提供します。
特にビルド結果のキャッシュやビルドの分散実行などの機能は
何千人ものエンジニアをサポートするために必要な機能です。
各言語のビルド・テストツールチェーンに
特注のキャッシングや分散モデルの投資を動作させるのではなく
Wazelのリモートキャッシングおよび実行APIの実装に深く投資しています。
サブスクリプションAPIの変更をテストするStripe社から
当社のインフラのセキュリティ姿勢を評価するStripe社まで
すべての人が満足できるリモートキャッシュおよび実行サービス構築をすることは
重要な課題となっています。
私たちのアプローチはセキュリティのバランスを取りながら
パフォーマンスの目標を達成するために
24:01
ユニークな技術の組み合わせに依存しています。
私たちはまだ完成していません。
毎朝私たちはStripeのエンジニアリング生産性の水準を高める機会に
駆けつけられています。という言葉で締められております。
はい、なんかもうお腹いっぱいです。
もちろん僕は全然専門じゃない技術の話ばっかりだったので
正直今読んでいて、僕は半分も理解できないんですけど正直な話
ただやろうとしていること、とにかく早く高速にビルドすることと
セキュアなビルドをすること
この両方を担保するためにいろんな施策をしているということは
十分に伝わってきたし
そのために自分たちも日々研究もしているし調査もするし
どんどんどんどん実験をしていて
手を動かしているということもよくわかりました。
ただただクラウドサービスとかいろんなサービス
ライブラリツールに頼るだけじゃなくて
コアのところに自分たちも普通に介入していって
ガリガリ書いていくというところまで
本当にあらゆることに手をつけて
やれることをどんどんやっていこうという姿勢が
まさにエンジニアとしての模範となるような動き方で
圧倒されたというよりも自分たちヤバくないかというのを
ちょっと感じたくらいでしたね。
僕全然技術者として本当に弱いなということを
突きつけられた感じがしますね。
でもめちゃめちゃモチベーション上がったし
僕は本職ではもう第一線で書かなくなったんですけど
書かないからといって別にアグラを書くのはちょっと違うなと思ったので
しっかり書かないんだけどめちゃくちゃ勉強しているこの人みたいな
やっぱ第一線でいつでもやりますよぐらいのスタンスで
また勉強していくのは全然いいかなと思ったりはしましたね。
以上、すいません。僕のくだらない雑談で終わりますが
こんな感じでした。
ストライプ社のエンジニアブログの中で今日は
ファストビルズ、セキュアビルズ、チューズ2という記事を
読ませていただきましたということです。
ちょっと面白かったんで、明日以降もストライプさんのブログ
いくつか読もうかなと思いました。
これぐらいな技術力高いお話が
しかも抽象的にちゃんとまとめられているのは
すごく学びが大きいと思うので
今後もちょっと読んでいこうかなと思いましたし
皆さんにも参考になれば幸いです。
ということで、今日の朝方はちょっとオーバーしたので
ここで以上にしたいかなと思います。
今日もたくさんの方に参加いただき
大変にありがとうございました。
また明日も何か緩やかに読んでいきたいと思いますので
興味があれば参加してみてください。
では終了したいと思います。お疲れ様でした。