Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
ChatWorkのリアクティブシステム導入事例から学ぶActor設計プラクティス
Search
かとじゅん
March 15, 2017
Programming
9
2.8k
ChatWorkのリアクティブシステム導入事例から学ぶActor設計プラクティス
Actorの設計プラクティスに関して簡単にまとめた資料です
かとじゅん
March 15, 2017
Tweet
Share
More Decks by かとじゅん
See All by かとじゅん
AIコーディングエージェントの現実と設計品質の重要性
j5ik2o
0
87
なぜイベント駆動が必要なのか - CQRS/ESで解く複雑系システムの課題 -
j5ik2o
15
7.4k
アクターシステムに頼らずEvent Sourcingする方法について
j5ik2o
8
1.3k
メッセージとイベントを中核に置いたシステム設計の有用性について
j5ik2o
12
4k
私のキャリアの旅路: 技術をきっかけに変化を楽しむ
j5ik2o
3
940
いかに開発効率と品質を高めるか: ドメイン駆動設計と組織パターンの視点から考える
j5ik2o
5
3k
社内のメンバーに「関数型プログラミングの学習・教育」についていろいろ聞いてみた
j5ik2o
2
2.1k
AWS データベースブログの記事 「Amazon DynamoDBによる CQRSイベントストアの構築」 を勝手に読み解く
j5ik2o
2
3.3k
EIPとAkkaについて
j5ik2o
3
2.9k
Other Decks in Programming
See All in Programming
After go func(): Goroutines Through a Beginner’s Eye
97vaibhav
0
400
Server Side Kotlin Meetup vol.16: 内部動作を理解して ハイパフォーマンスなサーバサイド Kotlin アプリケーションを書こう
ternbusty
3
200
ALL CODE BASE ARE BELONG TO STUDY
uzulla
25
6.1k
アメ車でサンノゼを走ってきたよ!
s_shimotori
0
230
The Past, Present, and Future of Enterprise Java
ivargrimstad
0
400
CSC509 Lecture 05
javiergs
PRO
0
300
3年ぶりにコードを書いた元CTOが Claude Codeと30分でMVPを作った話
maikokojima
0
380
NixOS + Kubernetesで構築する自宅サーバーのすべて
ichi_h3
0
950
その面倒な作業、「Dart」にやらせませんか? Flutter開発者のための業務効率化
yordgenome03
1
130
詳しくない分野でのVibe Codingで困ったことと学び/vibe-coding-in-unfamiliar-area
shibayu36
3
5.1k
Goで実践するドメイン駆動開発 AIと歩み始めた新規プロダクト開発の現在地
imkaoru
4
850
CSC305 Lecture 05
javiergs
PRO
0
220
Featured
See All Featured
The Power of CSS Pseudo Elements
geoffreycrofte
79
6k
Automating Front-end Workflow
addyosmani
1371
200k
Dealing with People You Can't Stand - Big Design 2015
cassininazir
367
27k
Exploring the Power of Turbo Streams & Action Cable | RailsConf2023
kevinliebholz
35
6.1k
For a Future-Friendly Web
brad_frost
180
10k
Templates, Plugins, & Blocks: Oh My! Creating the theme that thinks of everything
marktimemedia
31
2.5k
Docker and Python
trallard
46
3.6k
Product Roadmaps are Hard
iamctodd
PRO
54
11k
Visualization
eitanlees
149
16k
Visualizing Your Data: Incorporating Mongo into Loggly Infrastructure
mongodb
48
9.7k
Done Done
chrislema
185
16k
Design and Strategy: How to Deal with People Who Don’t "Get" Design
morganepeng
132
19k
Transcript
ChatWorkのリアクティブシステム導入事 例から学ぶActor設計プラクティス Junichi Kato (@j5ik2o)
自己紹介 • Scala歴 6年 • サーバサイド開発・設計担当 • 最近やってること ◦ TISさんやセプテーニさんでDDD基礎講座(有償)
◦ OAuth2/OpenID Connectのプロバイダ実装
アジェンダ • Falconで採用したアクターの設計がテーマ ◦ Falconのドメインモデル ◦ FYI: CQRS+ESアーキテクチャ ◦ Falcon
の アーキテクチャ概要 ◦ Falcon の レイヤ化アーキテクチャ ▪ API(Write or Read) ▪ SparrowForwarder ◦ FYI: Actorの特徴 ◦ FYI: Actorヒエラルキーの考え方 ◦ SparrowForwarderのActorヒエラルキー ◦ FYI: レジリエントを作り込む方法 ◦ BackOffSupervisorとその拡張
Falconのドメインモデル • 集中と選択でメッセージとそれにまつわるドメインイベントのみ • すでに成熟しており、議論が紛糾することがなかったので、Actor を使ったモデル駆動設計の議論が主戦場だった。 Message MessageCreated MessageUpdated
FYI: CQRS+ESアーキテクチャ
Falconのアーキテクチャ概要
Falconのレイヤ化アーキテクチャ
API(Write/Read)のアプリケーションアーキテクチャ DAS = Data Access Stream DIPを適用したレイヤ化アーキテクチャ= ヘキサゴナルアーキテクチャ
SparrowForwarderのアプリケーションアーキテクチャ
FYI:Actorの特徴
Actorの特徴(1/2) • メッセージを受信して初めて、利用可能なスレッドを使って反応する。メッセージに反応しないコンポーネントは 貴重なCPU資源を消費しない。 • メッセージに反応するかどうかはコンポーネントが選択でき、送信側と受信側のコンポーネントは、インターフェ イスと時間から分離される。 • アクターは一度に決まった単位のメッセージを処理する。 CPUを頻繁に消費するポーリングとブロッキングを採
用せず、高スループットにフォーカスするために CPUを解放する。必要に応じた反応が低レイテンシーを導く。
Actorの特徴(2/2) • DispatcherはMailboxにImmutableなメッセージを追加する (Shard Nothing)。ActorはMailboxを経由してメッ セージを順番に取得する 。開発者はDispatcherが利用するスレッドを意識しない。決まった単位のメッセージ を処理している際中は、別のメッセージを処理しないので、非同期境界を意識していれば、同一アクター内で はシングルスレッドのように見える。 •
Actor数分のスレッド数が必要になるわけではない。 ライトウェイト。2.7百万Actorは1GB程度。スレッドモデル では1GB=4096スレッド程度と考えると大きな差がある。 • DispatcherやMailboxは必要に応じて適切な種類と設定を選ぶことでチューニングが可能。
FYI:Actorヒエラルキーの考え方
ActorSystemのヒエラルキー • 最初にActorSystemが作られる。ActorSystemを使ってSupervisorを作る。 Supervisorが 子アクターを作ることでヒエラルキーを構築する。 • 実際には、アプリケーション用のアクターはuser guardian配下に所属する。
アクターヒエラルキーの目的 • スーパバイザのライフタイムは、子アクターが存 在する間と同じ。親によって作られた子アクター は、スーパバイザの監督下に置かれる。スーパ バイザの責任はすべての子アクターが終了した 時に終わる。 • クラッシュする可能性が高いアクターは、可能な 限りヒエラルキーの下層に配置すべき。下層で
起きた障害は、上位までのヒエラルキーが管理 ・エスカレーションが可能。最上位が障害を起こ した場合は、最上位のアクターの再起動もしく はアクターシステムのシャットダウンが必要にな る。
アクターヒエラルキーの実装パターン1 • 利点は、各アクターが相互に直接通信するこ と。スーパバイザは監督業務とインスタンス作 成のみ。 • 欠点は、再起動しか使えないことと、メッセージ がデッドレターに送られて失われてしまうこと。 親のスーパーバイザはメッセージフローから分 離してしまう。
アクターヒエラルキーの実装パターン2 • スーパバイザは単なる生成や監督ではなく、間 接参照として、すべてのメッセージを単に透過 的にフォワードする。スーパバイザは子を終了 したり、他のアクターとは無関係に新しいもの を生み出したりできる。 • 先の例と比べてメッセージフローのギャップが ない。
SparrowForwarder内部設計 ココの話
SparrowForwarderのActorヒエラルキー • このモデルは、SQSなどでも利用できる。 • Exponential BackOff機能を備えた Supervisorを経由してメッセージを透過的 に扱う。 • 下位層のActorはいつでもクラッシュしても
よい。上位はクラッシュしてはならない。 • KafkaComsumerActorがエラーを起こした 場合はSupervisorが指数関数的な BackOffを掛けてリトライを自動的に行う。 • APIExecutorも同様に振る舞うが、 Kafka へのポーリング間隔が延びると Consumer に異常があったと見なされセッションタイム アウトが起こり、リバランスが起こってしま う。この場合はAPIExecutor側でBackOff せずに全体のフローを最初からやり直す 方がよい。現在はAPIExecutorSupervisor は利用していない。
FYI:レジリエントを作り込む方法
Supervisorを実装する
子アクターを実装する
Supervisor経由で実行する
Supervisor経由での実行結果
akkaのBackOff Supervisor • データ送信処理が失敗して再送信するときに、失敗回数が増えるに連れて再送信す るまでの待ち時間を指数関数的に増やす仕組みを exponential backoff という。 • SupervisorにExponential
Backoffを付加するakka標準API ◦ 子アクターが停止もしくは再起動した時にBackoffする ◦ Supervisorにメッセージを送ると子アクターに転送される ◦ ただし、子アクターが開始・停止のイベントがとれない
BackOffSupervisorの拡張(1/3) • akkaからフォークした拡張(本家でも改善中なのでご参考程度に) → https://git.io/vyotj • 子アクターの開始と停止をフックできる • 以下はハンドラーを指定する方法
BackOff Supervisorの拡張(2/3) • ハンドラーの代わりにアクターを指定する方法
BackOff Supervisorの拡張(3/3) • Backoff機能付きSupervisor を自前で作る方法 • Supervisor自身がBackoff Retryが可能
まとめ • ActorRefは疎結合になるので、依存の方向性に気をつけながら、レイ ヤー化アーキテクチャを作る(Propsファクトリとメッセージの依存を間 違えなければまず問題が起きることはない)。静的型配線したいなら、 akka-streamを検討する価値はある。 • Actorの自己回復力(BackOffSupervisor)をいかした設計は、運用負 荷が下がる。これがActorのすべてと言ってもいいすぎではない。 •
でもActorの設計は難しい。Actorヒエラルキーなしはあまり意味がな い。歯を食いしばってActorのコンセプトを学びましょう…。
ご静聴ありがとうございました。