
بکاندوبFocalPay
FocalPay Inventory Service
جدا کردن مدیریت موجودی از یک سرویس بزرگتر و ساختن سرویسی مستقل برایش، از برنامهی مهاجرت و معماری تا سازوکارهایی که درستی کار را تضمین میکنند
- سال
- اوت 2026
- نوع
- بکاند
- فناوریها
- 12
- مسیر
- وب
جزئیات
مدیریت موجودی در FocalPay بخشی از یک سرویس بزرگتر بود. آن سرویس دیگر برای این کار مناسب نبود و کمکم خطا در دادههای موجودی دیده میشد. من مسئول جدا کردن این بخش شدم: برنامهی مهاجرت را نوشتم، سرویس جدید را طراحی کردم و خودم ساختمش. هدف این بود که سرویس جدید کمکم کار را به دست بگیرد، نه اینکه یک روز همهچیز یکجا عوض شود.
تصمیمهای اصلی را خودم گرفتم و برای هرکدام یک ADR نوشتم. مهاجرت مرحلهبهمرحله و با الگوی strangler انجام میشود و هر مرحله راه برگشتی دارد که از قبل تمرینش کردهایم. موجودی از روی دفتری حساب میشود که فقط چیزی به آن اضافه میشود و هیچ رکوردی در آن پاک یا بازنویسی نمیشود؛ یعنی برای هر عدد میشود نشان داد از کجا آمده. عدد موجودی با آپدیت اتمیک تغییر میکند تا دو فروش همزمان هیچوقت کار همدیگر را خراب نکنند. رویدادها از طریق outbox فرستاده میشوند و گیرندهها idempotent هستند، پس هیچ رویدادی نه گم میشود و نه دو بار اثر میگذارد. معماری سرویس هم hexagonal است و قواعدش در خود بیلد چک میشود تا منطق اصلی به فریمورک و زیرساخت وابسته نشود.
از نظر امکانات، این سرویس موجودی انبار، سفارش خرید از تأمینکننده با خروجی اکسل، ورود کالا با شمارهی بچ و تاریخ انقضا، هشدار نزدیک شدن به تاریخ انقضا، انبارگردانی، کالاهای وزنی، گزارشها و تطبیق تحویلها با سفارشها را پوشش میدهد.
برای من اطمینان از درست کار کردن سیستم بخشی از خود تحویل بود. سرویس بیش از هزار تست خودکار دارد و بخش بزرگی از آنها روی دیتابیس و message broker واقعی داخل کانتینر اجرا میشوند. کنارش تست end-to-end بین سرویسها و تست بار هم هست، و هر کدام از گاردها را عمداً شکستم تا مطمئن شوم بیلد واقعاً قرمز میشود. runbook، راهنمای رفع اشکال و نقشهی راه را هم نوشتم تا تیم بتواند سرویس را نگه دارد. سرویس آماده و تستشده است و منتظر شروع مهاجرت مرحلهای.
فناوریها
- Java
- Spring Boot
- MongoDB
- Kafka
- Event-Driven Architecture
- Transactional Outbox
- Hexagonal Architecture
- DDD
- ArchUnit
- Testcontainers
- k6
- ADR