【イベント駆動アーキテクチャ】
はじめに
SOCKET-MANAGER Framework は、ステートマシンをビルトインしたイベントループを中核に据えた、極めて堅牢かつ安全なリアルタイム通信基盤です。
一般的なイベント駆動フレームワークでは、I/O 多重化により高いスループットを実現できる一方で、非同期処理中に別イベントが割り込むことで状態が破壊されるという構造的な問題を抱えています。
これは、イベントループとビジネスロジックが別々のモデルで動作していることが原因です。
また、外付けのステートマシンライブラリをビジネスロジック側に組み込んでも、イベントループ側の割り込みや非同期競合を制御することは不可能であり、根本的な解決にはなりません。
本フレームワークは、イベントループそのものがステートマシンとして動作するという独自構造により、他のソリューションでは実現できない高信頼なイベント駆動処理を提供します。
本ページでは、SOCKET-MANAGER Framework の基盤思想の一部である イベント駆動アーキテクチャについて解説します。
フレームワーク全体の構成や主要機能については、 ▶フレームワークのご紹介 をご覧ください。
一般的なイベント駆動フレームワークでは、I/O 多重化により高いスループットを実現できる一方で、非同期処理中に別イベントが割り込むことで状態が破壊されるという構造的な問題を抱えています。
これは、イベントループとビジネスロジックが別々のモデルで動作していることが原因です。
また、外付けのステートマシンライブラリをビジネスロジック側に組み込んでも、イベントループ側の割り込みや非同期競合を制御することは不可能であり、根本的な解決にはなりません。
本フレームワークは、イベントループそのものがステートマシンとして動作するという独自構造により、他のソリューションでは実現できない高信頼なイベント駆動処理を提供します。
本ページでは、SOCKET-MANAGER Framework の基盤思想の一部である イベント駆動アーキテクチャについて解説します。
フレームワーク全体の構成や主要機能については、 ▶フレームワークのご紹介 をご覧ください。
三層構造のステートマシン
SOCKET-MANAGER Framework は、UNIT → Queue → Module の三層構造を持つステートマシンを基盤としています。
内部はこの共通モデルで統一されており、通信方式や利用シーンが異なっても、同じ抽象モデルで扱えるように設計されています。
この三層構造により、内部は強固な統一モデル、外部は疎結合で柔軟という理想的なアーキテクチャが成立します。
モジュールごとに役割を分離しつつも、UNIT / Queue という共通の状態モデルの上で動作させることで、イベント駆動の柔軟性と状態遷移の安全性を両立させています。
UNIT / Queue の使い方のバリエーションについては、▶イベントハンドラについて を参照してください。
内部はこの共通モデルで統一されており、通信方式や利用シーンが異なっても、同じ抽象モデルで扱えるように設計されています。
UNIT(最小処理単位)
- ステートマシンの 1 ステップを表す最小処理単位
- 非同期で実行されるコルーチンとして動作
- UNIT の終了時点でのみ状態が確定し、中断しても状態は保持される
Queue(UNIT の集合)
- UNIT が連続した 1 本のシーケンスを形成
- Queue が完了するまで、同一コンテキストに属する次のイベントは処理されない
- 新しいイベントは FIFO キューに積まれ、順序が厳密に管理される
Module(Queue の集合)
- プロトコル処理やサーバーコンテンツ(コマンド部)をクラスとして定義した単位
- 共通インターフェースで統一的に扱える
- ストラテジーパターンとして差し替え可能で、依存性注入(DI)と相性が良い
この三層構造により、内部は強固な統一モデル、外部は疎結合で柔軟という理想的なアーキテクチャが成立します。
モジュールごとに役割を分離しつつも、UNIT / Queue という共通の状態モデルの上で動作させることで、イベント駆動の柔軟性と状態遷移の安全性を両立させています。
UNIT / Queue の使い方のバリエーションについては、▶イベントハンドラについて を参照してください。
抽象化されたステートマシン
SOCKET-MANAGER Framework のイベントループは、CycleDrivenManager によって抽象化されたステートマシンとして動作します。
CycleDrivenManager は、プロトコル部(TCP / UDP / WebSocket / 独自プロトコルなど)とコマンド部(サーバーコンテンツ)を、同じアプリケーションレイヤーで統一されたインターフェースとして扱えるように設計されています。
これにより、以下のような高度な構造が実現されています。
特に重要なのは、プロトコル部/コマンド部を含めて統一されたインターフェースでビジネスロジックを組めるという点です。
これにより、通信方式の違いに依存しない柔軟なアプリケーション設計が可能になります。
CycleDrivenManager の詳細な構造やレイヤー図については、▶アーキテクチャ(レイヤー概念図) を参照してください。
CycleDrivenManager は、プロトコル部(TCP / UDP / WebSocket / 独自プロトコルなど)とコマンド部(サーバーコンテンツ)を、同じアプリケーションレイヤーで統一されたインターフェースとして扱えるように設計されています。
これにより、以下のような高度な構造が実現されています。
- プロトコル部/コマンド部を同一モデルで扱える
- 独自プロトコルを含めたプロトコル汎用化が可能
- プロトコル部/コマンド部を自由に差し替え可能
- アプリケーションロジックを統一された抽象モデルで記述できる
特に重要なのは、プロトコル部/コマンド部を含めて統一されたインターフェースでビジネスロジックを組めるという点です。
これにより、通信方式の違いに依存しない柔軟なアプリケーション設計が可能になります。
CycleDrivenManager の詳細な構造やレイヤー図については、▶アーキテクチャ(レイヤー概念図) を参照してください。
CUEI各要素との相関関係
本ページで解説しているイベント駆動アーキテクチャは、CUEI アーキテクチャにおける
E(Event) の役割を担う中心的な要素です。
特に重要なのは、イベントループが UNIT / Queue / Module の統一モデルをビルトインしているため、 サーバー本体のモジュール(SocketManager など)と IPC モジュールを同じイベントループ内で共存させられる という点です。
これにより、複数の通信モジュールを同一プロセス内で安全に動作させることができ、 CUEI の各要素が自然に連携する構造が実現されています。
このように、イベント駆動アーキテクチャは CUEI の E を中心に、 C・U・I の要素を統合する役割を担っています。
CUEI 全体像については、▶アーキテクチャ を参照してください。
特に重要なのは、イベントループが UNIT / Queue / Module の統一モデルをビルトインしているため、 サーバー本体のモジュール(SocketManager など)と IPC モジュールを同じイベントループ内で共存させられる という点です。
これにより、複数の通信モジュールを同一プロセス内で安全に動作させることができ、 CUEI の各要素が自然に連携する構造が実現されています。
- C(Communication):プロトコル部が抽象化され、さらに通常通信と IPC を同じモデルで扱える
- U(Union):共有基盤(UNITパラメータ)が全モジュールに渡され、状態管理が統一される
- E(Event):複数モジュールを同一イベントループで安全に共存させる
- I(IPC):E の上で自然に動作し、追加の仕組みなしでプロセス間通信を構成できる
このように、イベント駆動アーキテクチャは CUEI の E を中心に、 C・U・I の要素を統合する役割を担っています。
CUEI 全体像については、▶アーキテクチャ を参照してください。
UNITの安全保留処理
UNIT は「中断可能な処理ブロック」として動作し、UNIT が中断中に別イベントが到着しても、必ず FIFO キューで安全に保留されます。
従来の「イベントハンドラがその場で全て処理する」モデルとは異なり、SOCKET-MANAGER Framework では「処理を UNIT に細分化し、Queue として順序付けて実行する」ことで、複雑な非同期処理でも状態遷移の破綻を防ぎます。
- UNIT の区切りでのみ状態が確定するため、割り込みで状態が壊れない
- UNIT 実行中のイベントはすべて安全に待機し、順序が保証される
- UNIT チェーンが完了するまで同一シーケンス上の状態遷移は一貫して維持される
従来の「イベントハンドラがその場で全て処理する」モデルとは異なり、SOCKET-MANAGER Framework では「処理を UNIT に細分化し、Queue として順序付けて実行する」ことで、複雑な非同期処理でも状態遷移の破綻を防ぎます。
シーケンス外イベント処理
UNIT の途中であっても、「現在の状態に応じて受け入れるべきイベントかどうか」を検証する仕組みを備えている点も、このアーキテクチャの特徴です。
これにより、「本来このタイミングでは受け取るべきでないメッセージが紛れ込む」といった状況でも、状態モデルに基づいて安全に検証・制御することができます。
複雑なプロトコルや状態依存の処理でも、シーケンス破綻を防ぎながら運用することが可能です。
- 現在の UNIT / Queue の状態に基づき、次に許可されるイベントを判定できる
- シーケンス外のイベントは拒否・保留・別 Queue への振り分けなど、意図したルールで制御可能
- プロトコルレベルで厳密なシーケンス管理を行いつつ、柔軟なイベント受信を両立できる
これにより、「本来このタイミングでは受け取るべきでないメッセージが紛れ込む」といった状況でも、状態モデルに基づいて安全に検証・制御することができます。
複雑なプロトコルや状態依存の処理でも、シーケンス破綻を防ぎながら運用することが可能です。
ストラテジーパターンとDI
Module 層では、プロトコル部/コマンド部を、それぞれ独立したクラスとして定義できます。
どちらも UNIT / Queue モデルの上に構築されるため、状態管理の抽象モデルは共通ですが、実装は疎結合に保たれます。
これにより、「状態モデルは共有するが、ロジックは交換可能」 という構造が実現されています。
プロトコルの違いにかかわらず、同じ UNIT / Queue モデルの上にビジネスロジックを載せられるため、システム全体の一貫性を保ちながら拡張していくことができます。
どちらも UNIT / Queue モデルの上に構築されるため、状態管理の抽象モデルは共通ですが、実装は疎結合に保たれます。
- プロトコル部/コマンド部を別クラスとして分離可能
- 共通インターフェースにより、複数モジュールを統一的に扱える
- ストラテジーパターンとして差し替え可能で、要件に応じてモジュール構成を切り替えられる
- 依存性注入(DI)と組み合わせることで、柔軟な構成変更やテストが容易
これにより、「状態モデルは共有するが、ロジックは交換可能」 という構造が実現されています。
プロトコルの違いにかかわらず、同じ UNIT / Queue モデルの上にビジネスロジックを載せられるため、システム全体の一貫性を保ちながら拡張していくことができます。
提供される主なメリット
SOCKET-MANAGER Framework のイベント駆動アーキテクチャは、高信頼なリアルタイム通信や高負荷環境において、以下のような強力なメリットを提供します。
- 状態遷移の整合性をイベントループレベルで保証できる
- 非同期処理中のイベント競合を、UNIT / Queue モデルで完全に制御できる
- プロトコル部/コマンド部を疎結合に保ちつつ、共通の状態モデルで統一できる
- ストラテジーパターンと依存性注入により、モジュール構成の差し替えや拡張が容易
- 高負荷環境や長時間接続のシナリオでも安定した動作を維持しやすい
- シーケンス外イベントの検証により、複雑なプロトコルでも安全に運用できる
- UNIT / Queue / Module の統一モデルにより、新しい通信方式やサービスを追加しやすい
参考資料(外部リンク)
本ページで扱った「ステートマシン」「イベントループ」「ノンブロッキング処理」について、 一般的な概念を確認したい場合は以下の資料も参考になります。
-
ステートマシンの一般的な概念:
Finite-state machine(Wikipedia) -
イベントループの一般的な仕組み:
MDN Web Docs – イベントループ -
ノンブロッキング I/O の一般概念:
Non-blocking I/O(Wikipedia)
おわりに
SOCKET-MANAGER Framework のイベント駆動アーキテクチャは、ステートマシンをビルトインしたイベントループという独自構造により、従来のイベント駆動フレームワークが抱える「非同期処理と状態遷移の整合性」の問題を根本から解決します。
この高信頼なイベント駆動アーキテクチャは、REST-API 環境におけるステートマシン型実装や、Chunked Transfer / SSE / Range 送信の安定動作、さらには IPC(プロセス間通信)やマルチサーバー構成とも密接に結びついています。
各トピックについては、▶アーキテクチャ、▶IPC(プロセス間通信) などの関連ページもあわせてご参照ください。
この高信頼なイベント駆動アーキテクチャは、REST-API 環境におけるステートマシン型実装や、Chunked Transfer / SSE / Range 送信の安定動作、さらには IPC(プロセス間通信)やマルチサーバー構成とも密接に結びついています。
各トピックについては、▶アーキテクチャ、▶IPC(プロセス間通信) などの関連ページもあわせてご参照ください。