なぜCRUDを超える必要があるのか?
PostgreSQLやMySQLのような従来のデータベースは、オブジェクトの「現在の状態」を保存することに長けています。しかし、なぜその状態に変化したのかという「経緯」を説明するのは苦手です。顧客が配送先住所を更新した場合、標準的なUPDATE文は古いデータを永久に破壊してしまいます。複雑でメンテナンス負荷の高い監査用テーブルを構築しない限り、履歴は失われます。EventStoreDBは、すべての変更を「不変のイベント」として扱うことで、データに対して異なるアプローチをとります。
銀行の台帳を想像してみてください。銀行は単に「最終残高5,000ドル」を保存するわけではありません。100ドルの入金と50ドルの出金のすべてを記録します。
現在の残高は、これら過去の事実の積み重ねに過ぎません。これがイベントソーシング(Event Sourcing)です。EventStoreDBは、これを大規模に処理するために構築された専用のデータベースエンジンであり、控えめなハードウェア構成でも秒間15,000件以上の書き込みを維持できます。また、複雑なマイクロサービスのスケールに不可欠な**CQRS(Command Query Responsibility Segregation:コマンドクエリ責務分離)**をネイティブにサポートしています。
RDBMSを無理やりイベントストアとして使うよりも、EventStoreDBのような専用ツールを選択する方が賢明です。ストリームのアトミック性や楽観的排他制御をネイティブに管理できるため、アプリケーションコード内に複雑なロックロジックを記述する必要がなくなります。
インストール:最初のノードをデプロイする
Dockerはローカルインスタンスを立ち上げるための最も効率的な方法です。開発に必要なRAMは2GB未満のサンドボックス環境を提供するため、ノートPCでのテストに最適です。
Dockerでの実行
最新の24.10 LTSイメージを取得し、シングルノードクラスターを起動するには次のコマンドを実行します。ここではローカルテスト用にSSL証明書の設定をスキップするため、--insecureフラグを使用しています。
docker run --name esdb-node -it \
-p 2113:2113 -p 1113:1113 \
eventstore/eventstore:latest --insecure --run-projections=all
パラメータの詳細を見ていきましょう:
- -p 2113:2113: 管理UIとgRPC API用のポートをマッピングします。最新のEventStoreDBは、すべてのデータ操作にHTTP/2を使用します。
- –insecure: TLSを無効にします。ローカル開発では大幅な時間短縮になりますが、本番環境では重大なセキュリティリスクとなります。
- –run-projections=all: イベントデータの集約や変換を行う内部エンジンを有効にします。
Linuxへのネイティブインストール
DebianやUbuntuを使用しており、ネイティブサービスとして実行したい場合は、PackageCloudから公式パッケージを直接取得できます:
curl -s https://packagecloud.io/install/repositories/EventStore/EventStore-OSS/script.deb.sh | sudo bash
sudo apt-get install eventstore-oss
インストールが完了したら、systemdでサービスを起動します:
sudo systemctl start eventstore
重要なネットワーク設定
EventStoreDBはeventstore.confファイルの設定に従って動作します。デフォルトではトラフィックを127.0.0.1に制限しています。クラウドの仮想マシンにデプロイし、リモートアクセスが必要な場合は、バインディングインターフェースを調整する必要があります。
設定ファイルを以下の設定で更新してください:
# パス: /etc/eventstore/eventstore.conf
IntIp: 0.0.0.0
ExtIp: 0.0.0.0
HttpPort: 2113
Insecure: true
RunProjections: All
最近の物流プロジェクトで、接続のデバッグに2時間を費やした結果、ファイアウォールがgRPCトラフィックをブロックしていたことに気づきました。セキュリティグループでポート2113のインバウンド許可を確認してください。このポートは、ブラウザベースのダッシュボードと高速データストリームの両方を処理します。
Pythonで最初のイベントを書き込む
モダンなSDKのおかげで、データベースとのやり取りは非常にシンプルです。.NETが第一級市民(最優先)ですが、Pythonも迅速なプロトタイピングには最適です。まずはクライアントをインストールしましょう:
pip install esdbclient
以下のスクリプトは、特定のユーザーのストリームを作成し、サインアップイベントを追加します。これにより、ユーザーのシステムへの登録に関する、永続的で変更不可能な記録が作成されます。
from esdbclient import EventStoreDBClient, NewEvent
import json
# ローカルインスタンスに接続
client = EventStoreDBClient(uri="esdb://localhost:2113?tls=false")
# ペイロードを定義
event_payload = {
"user_id": "u-789",
"action": "account_created", # アカウント作成
"email": "[email protected]"
}
# イベントをパッケージ化
event = NewEvent(
type="UserCreated", # ユーザー作成
data=json.dumps(event_payload).encode("utf-8")
)
# 'user-789' ストリームに追加
client.append_to_stream(
stream_name="user-789",
current_version=-1, # ストリームが新規であることを保証
events=[event]
)
print("イベントがレジャーにコミットされました。")
スプレッドシートからレガシーデータを移行する場合、フォーマット変換が面倒になることがあります。私は行をクリーンなJSONオブジェクトに変換するために toolcraft.app/ja/tools/data/csv-to-json を使用しています。これは完全にブラウザ上で動作するため、変換プロセス中に機密性の高い顧客データがローカルマシンから流出することはありません。
データストリームの検証
データベースに強力なWebインターフェースが含まれているため、検証は簡単です。内部で何が起きているかを確認するために、別途CLIツールを用意する必要はありません。
- ブラウザで
http://localhost:2113にアクセスします。 - ユーザー名
admin、デフォルトパスワードchangeitを使用してサインインします。 - サイドバーから 「Stream Browser」 を選択します。
すぐに user-789 ストリームが表示されます。それをクリックすると、タイムスタンプやメタデータを含む個々のイベントが表示されます。この透明性は、イベント駆動型のレースコンディション(競合状態)をデバッグする際の救世主となります。
ヘルスチェックとパフォーマンス監視
本番環境ではUI以上のものが必要です。EventStoreDBは、メトリクスをJSONで出力する /stats エンドポイントを提供しています。多くのチームはこれをPrometheusに渡しています。ディスクI/O、メモリ使用量、イベントスループットを追跡する構築済みのGrafanaダッシュボードも存在します。
管理UIの「Scavenging(スカベンジング)」プロセスを注意深く監視してください。スカベンジングは、削除されたイベントや期限切れのストリームバージョンをクリーンアップしてディスク容量を回収するデータベースの機能です。ストレージ使用量が急増した場合は、ディスク容量を増やす前にまずスカベンジログを確認しましょう。
プロジェクションによる状態の派生
プロジェクションは、このエンジンの秘密兵器です。これらはサーバーサイドで実行されるJavaScriptのスニペットで、イベントの到着に反応します。すべてのユーザーイベントをクエリして合計数を算出する代わりに、リアルタイムでカウンターを維持するプロジェクションを記述できます。
$by_category システムプロジェクションを有効にすると、データが自動的に整理されます。これは user-1、user-2、user-3 からのイベントを $ce-user という単一の仮想ストリームにグループ化します。この単一のストリームを購読することで、ダウンストリームのサービスは、手動でフィルタリングすることなく、プラットフォーム全体のすべてのユーザー関連の変更に反応できるようになります。
まとめ
EventStoreDBを使用するには、「スナップショット」から「タイムライン」への思考の転換が必要です。データを一連のイベントとして扱うことで、完璧な監査ログが得られ、任意の時点のシステム状態を再構築できるようになります。まずはショッピングカートのようなシンプルなワークフローのモデリングから始めて、ストリームがどのように成長するか観察してみてください。一度アペンドオンリー(追記専用)アーキテクチャの信頼性を体験すると、従来のCRUDはまるで目隠しをして作業しているように感じられるでしょう。

