次のイベント データ スキームがあるとします。
event_record_unique_id: long
event_timestamp: long
session_id: long
event_id: int
event_data: data # concrete type depends on event_id
...そのため、データの内容は、たとえば 500 の event_id に依存する可能性があり、「データ」の具体的なデータ型は 200 種類になります。例えば:
{
event_record_unique_id: 17126721
event_timestamp: 1234
session_id: 3452
event_id: 50
event_data: {
user_id: 123
page_id: 789
}
}
{
event_record_unique_id: 1712672123
event_record_unique_id: 17126723
event_timestamp: 1234
session_id: 3454
event_id: 51
event_data: {
user_id: 124
button_id: 789
}
}
{
event_timestamp: 1234
session_id: 3454
event_id: 51
event_data: {
crash_report: "text"
device_id: "12312"
}
}
また:
- event_data 属性の多くは、具体的な event_data オブジェクトの多くに表示されます
- 一部の event_data 属性でインデックス検索を実行する必要があります (たとえば、 user_id=X のすべてのレコードを見つけます)
- イベントの種類と新しい属性を追加し続ける必要があります
- 上記のデータ構造は、単一のレコードを N 列の行として同等に表すことができるように、常に簡単にフラット化されます (属性の名前/タイプの衝突は、属性の名前を変更することによって解決されます)。
単純な RDBMS アプローチでは、約 500 個のテーブル (「データ」の具体的なタイプごとに 1 つ) を作成する必要がありました。私はこのアプローチを軽視しました (= モデリングにおける人間の労力の過度の浪費)。さらに、user_id を介してすべてのレコードを簡単に検索することはできません (user_id は非常に多くのテーブルに表示されるため)。
RDBMS で構造をフラット化することも非常にコストがかかります (要素の N-8 は NULL であり、情報が含まれていません)。
Mongodb タイプのドキュメント データベース ソリューションは優れているように見えますが、属性名が各レコードで保持される場合、スペース コストが非常に高く、RDBMS よりもはるかに優れているとは言えません。ただし、これにより、データ オブジェクト内のフィールドごとにインデックスを作成できます。
私にとって、これの理想的なデータ表現は、多くの null 要素を持つ行を許可するように最適化されたテーブルです (たとえば、行ごとにアクティブな列ビットマスクを保持することによって)。または、ドキュメント コレクションが使用されるドキュメント スキーマのライブラリを維持するドキュメント DB は、データ (およびそのスキーマへの参照を持つ各ドキュメント) の圧縮を可能にします。
上記の例の場合、人々はどのようなデータベースを推奨しますか?