GH GambleHub

Event Sourcing: негиздери

Event Sourcing деген эмне

Event Sourcing (ES) - бул домендик объектилердин абалын "учурдагы сап" түрүндө эмес, окуяларды сүрөттөгөн өзгөрүлбөс журнал катары сактоо ыкмасы. Агрегаттын учурдагы абалы анын окуяларынын бүктөлүшү (replay) менен алынат, ал эми ар кандай окуу сунуштары бул журналдын үстүндөгү проекциялар катары түзүлөт.

Негизги натыйжалары:
  • Тарых - "чындыктын баштапкы булагы", мамлекет - тарыхтын проекциясы.
  • Ар кандай абал кайра, текшерүү жана түшүндүрүү (аудит) болот.
  • Жаңы идеяларды жана аналитиканы кошуу эски "сүрөттөрдүн" миграциясын талап кылбайт - окуяларды жоготуу жетиштүү.

Негизги терминдер

Агрегат - так инварианттар менен шайкештик домен бирдиги (Order, Payment, UserBalance).
Окуя - өткөн ('payment. authorized`, `order. shipped`).
Event Store - агрегаттын ичинде окуялардын тартибин камсыз кылуучу аппенд-онли журналы.
Агрегаттын версиясы - акыркы колдонулган окуянын номери (optimistic concurrency үчүн).
Снапшот - ороону тездетүү үчүн мезгил-мезгили менен түзүлгөн абал.
Проекция (read-model) - окуу/издөө/отчеттуулуктун материалдаштырылган түрү (көбүнчө - асинхрондук).

Кантип иштейт (командалардын агымы → окуялар → проекциялар)

1. Кардар ('CapturePayment', 'PlaceOrder') командасын жөнөтөт.
2. Агрегат инварианттарды тастыктайт жана, эгерде баары жакшы болсо, окуяларды жаратат.
3. Events атомдук версия текшерүү менен Event Store кошулат (optimistic concurrency).
4. Проекция процессорлору окуялардын агымына жазылышат жана окуу моделдерин жаңыртышат.
5. Агрегатты төмөнкү команда үчүн жүктөөдө абал калыбына келтирилет: снапшот (эгерде бар болсо) → снапшоттон кийинки окуялар.

Окуялардын дизайны

Милдеттүү атрибуттар (негизги)

json
{
"event_id": "uuid",
"event_type": "payment. authorized. v1",
"aggregate_type": "Payment",
"aggregate_id": "pay_123",
"aggregate_version": 5,
"occurred_at": "2025-10-31T10:42:03Z",
"payload": { "amount": 1000, "currency": "EUR", "method": "card" },
"meta": { "trace_id": "t-abc", "actor": "user_42" }
}
Сунуштар:
  • Аталышы: 'домен. action. v{major}`.
  • Кошумча: жаңы талаалар - эски маанисин өзгөртпөстөн, кошумча.
  • Минимализм: жөн гана маалымат, эч кандай кайталоо жонокой калыбына келтирүү.

Келишимдер жана схемалар

Схемаларды бекитүү (Euro/JSON схемасы/Protobuf) жана CI боюнча шайкештигин текшерүү.
"Бузуучу" өзгөрүүлөр үчүн - окуянын жаңы негизги версиясы жана миграция мезгилине параллелдүү 'v1 '/' v2' жарыялоо.

Атаандаштык жетүү: optimistic concurrency

Эреже: жаңы окуяларды жаздыруу 'expected _ version = = current_version' гана мүмкүн.

Псевдокод:
pseudo load: snapshot(state, version), then apply events > version new_events = aggregate. handle(command)
append_to_store(aggregate_id, expected_version=current_version, events=new_events)
//if someone has already written an event between load and append, the operation is rejected -> retray with reload

Ошентип, биз бөлүштүрүлгөн бүтүмдөр жок инварианттардын бүтүндүгүн кепилдик берет.

Snapshots (топтомун тездетүү)

Ар бир N окуяларды же таймер боюнча снапшот жасаңыз.
Храните `snapshot_state`, `aggregate_id`, `version`, `created_at`.
Ар дайым текшерүү жана snapshot кийин окуяларды кууп (бир гана мөөр ишенбегиле).
Снапшотторду казыктан кайра түзө тургандай кылып алып салыңыз ("сыйкырдуу" талааларды сактабаңыз).

Проекциялар жана CQRS

ES табигый CQRS менен айкалышат:
  • Write модели = агрегаттар + Event Store.
  • Read-моделдер = окуялар менен жаңыланган проекциялар (Redis карталары, издөө үчүн OpenSearch, отчеттор үчүн ClickHouse/OLAP).
  • Проекциялар идемпотенттик: ошол эле 'event _ id' кайра иштетүү натыйжаны өзгөртпөйт.

Схемалардын эволюциясы жана шайкештиги

Additive-first: талааларды кошуу; түрлөрүн/семантикасын өзгөртүүгө болбойт.
Татаал өзгөрүүлөр үчүн: окуялардын жаңы түрлөрүн чыгарыңыз жана проекциялардын миграторлорун жазыңыз.
Өткөөл мезгилге кош жазууну ('v1' + 'v2') колдоп, бардык проекциялар даяр болгондо 'v1' тасмасын тартыңыз.

Коопсуздук, PII жана "унутуу укугу"

Тарых көп учурда сезимтал маалыматтарды камтыйт. Ыкмалары:
  • Окуяларда PII минималдаштыруу (маалыматтардын ордуна идентификаторлор, деталдар - корголгон тараптарда).
  • Крипто-өчүрүү: талааларды шифрлөө жана өчүрүүнү суранганда ачкычты жок кылуу (окуя кала берет, бирок маалыматтар жок).
  • Окуялар-өзгөртүүлөр: 'user. piiredacted. v1 'проекцияларда сезгич талааларды алмаштыруу менен (тарых редакциялоо фактысын сактайт).
  • Retence саясаты: Кээ бир домендер үчүн кээ бир окуялар WORM сактагычта архивделиши мүмкүн.

Аткаруу жана масштабдоо

Партиялаштыруу: агрегаттын ичиндеги тартип маанилүү - партиялаштыруу 'aggregate _ id'.
муздак баштоо: snapshots + мезгил-мезгили менен "мөөрлөнүп" оролгон.
Batch Appand: бир бүтүм менен окуяларды топтоо.
Backpressure жана DLQ проекция процессорлору үчүн; убакытты өлчөө (убакыт жана билдирүүлөрдүн саны).
Event Store индекстөө: тез жетүү '(aggregate_type, aggregate_id)' жана убакыт.

Сыноо

агрегаттар үчүн Specification tests: скрипт "команда → күтүлгөн окуялар".
Projection tests: окуялардын агымын берүү жана материалдык абалын/индекстерин текшерүү.
Replayability tests: текчедеги "нөлдөн" проекцияларды кайра карап чыгуу - натыйжасы дал келерин текшериңиз.
Chaos/latency: injected кечигүүлөр жана эки, текшерип турууга.

Домендик мисалдар

1) Төлөмдөр

Окуялар: 'payment. initiated`, `payment. authorized`, `payment. captured`, `payment. refunded`.
Инварианттар: 'authorized' жок 'capture' болбойт; суммалар терс эмес; акча өзгөрбөйт.
Проекциялар: "төлөм картасы" (KV), транзакцияларды издөө (OpenSearch), отчеттуулук (OLAP).

2) Буйрутмалар (электрондук соода)

Окуялар: 'order. placed`, `order. paid`, `order. packed`, `order. shipped`, `order. delivered`.
Инварианттар: статус диаграммасы боюнча статустарды которуу; жокко чыгаруу чейин мүмкүн 'shipped'.
Проекциялар: колдонуучунун буйрутмаларынын тизмеси, статус боюнча SLA-дашборддор.

3) Баланстар (финансы/iGaming)

Окуялар: 'balance. deposited`, `balance. debited`, `balance. credited`, `balance. adjusted`.
Катуу invariant: баланс <0; буйруктар 'operation _ id' демпотенттик.
Критикалык операциялар түздөн-түз агрегаттан (катуу ырааттуулук), UI - проекциядан (eventual) окулат.

Event Store типтүү түзүмү (DD менен параметр)

events

`event_id (PK)`, `aggregate_type`, `aggregate_id`, `version`, `occurred_at`, `event_type`, `payload`, `meta`

Индекси: '(aggregate_type, aggregate_id, version)'.

snapshots

`aggregate_type`, `aggregate_id`, `version`, `state`, `created_at`

Индекси: '(aggregate_type, aggregate_id)'.

consumers_offsets

'consumer _ id', 'event _ id '/' position', 'updated _ at' (проекциялар жана ретлейлер үчүн).

Көп суроолор (FAQ)

Бардык жерде ES колдонуу зарылбы?
Жок. ES маанилүү аудит, татаал инварианттар, кайра ойнотуу жана ар кандай маалыматтарды берүү үчүн пайдалуу болуп саналат. Жөнөкөй CRUD үчүн бул ашыкча.

"Учурдагы абалдын" суроо-талаптары жөнүндө эмне айтууга болот?
Же проекциядан окуңуз (тез, eventual), же агрегаттан (кымбатыраак, бирок катуу). Оор операциялар адатта экинчи жолду колдонот.

Кафка/стрим брокери керекпи?
Event Store - чындыктын булагы; брокер долбоорлорду жана тышкы системаларды окуяларды жайылтуу үчүн ыңгайлуу болуп саналат.

"Унутулуу укугу" менен эмне кылуу керек?
PII минималдаштыруу, сезгич талааларды шифрлөө жана проекцияларда крипто-өчүрүү/редакцияны колдонуу.

Эски маалыматтарды кантип көчүрүү керек?
Окуялардын retrospective генерациясынын сценарийин жазыңыз ("ре-хайстори") же "абал-кандай" менен баштаңыз жана жаңы өзгөрүүлөр үчүн гана окуяларды жарыялаңыз.

Антипаттерндер

Event Sourcing "адат боюнча": домендик пайдасыз системаны татаалдаштырат.
Fat events: PII жана дубль менен шишип Payload - тормоз жана комплаенс көйгөйлөрү.
Оптимисттик concurrency жоктугу: жарыш учурунда инварианттарды жоготуу.
Өндүрүлбөгөн проекциялар: реплика/снапшот → кол фикстер жок.
Чийки CDC домен окуялар катары: DD схемалар жана катуу байланыш агып.
Ички жана интеграциялык окуяларды аралаштыруу: туруктуу "витринаны" жарыялаңыз.

Production үчүн чек тизмеси

  • Агрегаттар, инварианттар жана окуялар (аталыштар, версиялар, схемалар) аныкталган.
  • Event Store агрегат жана optimistic concurrency ичинде тартипти камсыз кылат.
  • Snapshots жана аларды кайра түзүү планы киргизилген.
  • Проекциялар идемпотенттик, DLQ жана лаганын метриктери бар.
  • Схемалар CI боюнча тастыкталат, версиялар саясаты - документтештирилген.
  • PII минималдаштырылган, талаалар шифрленген, "унутуу" стратегиясы бар.
  • Проекциялардын репликасы стендде текшерилди; авариялык калыбына келтирүү планы бар.
  • Dashboard: Append ылдамдыгы, проекция артта, колдонуу каталар, retrains үлүшү.

Жыйынтык

Event Sourcing системанын тарыхын биринчи класстагы артефакт кылат: биз фактыларды каттайбыз, алардын абалын кайталайбыз жана ар кандай идеяларды эркин курабыз. Бул аудитти, өзгөрүүлөргө туруктуулукту жана аналитиканын ийкемдүүлүгүн берет - схемаларда тартип, атаандаштык контролдоо жана сезимтал маалыматтар менен компетенттүү иштөө шартында.

Contact

Биз менен байланышыңыз

Кандай гана суроо же колдоо керек болбосун — бизге кайрылыңыз.Биз дайым жардам берүүгө даярбыз!

Интеграцияны баштоо

Email — милдеттүү. Telegram же WhatsApp — каалооңузга жараша.

Атыңыз милдеттүү эмес
Email милдеттүү эмес
Тема милдеттүү эмес
Билдирүү милдеттүү эмес
Telegram милдеттүү эмес
@
Эгер Telegram көрсөтсөңүз — Emailден тышкары ошол жактан да жооп беребиз.
WhatsApp милдеттүү эмес
Формат: өлкөнүн коду жана номер (мисалы, +996XXXXXXXXX).

Түшүрүү баскычын басуу менен сиз маалыматтарыңыздын иштетилишине макул болосуз.