Клієнт втратив 30% продажів через повільний пошук на маркетплейсі шаблонів. Elasticsearch вирішив проблему за кілька днів, але виявилися інші болі: ручна модерація тисяч файлів, заплутані виплати авторам, відсутність аналітики. Ми, команда з 5+ років досвіду та 20+ запущених проєктів, будуємо платформу, де кожен учасник отримує свій інструмент. Використовуємо перевірений стек: Laravel, PostgreSQL, Redis, Elasticsearch. Пропонуємо прозорий процес і гарантію якості. Отримайте консультацію інженера з архітектури маркетплейсу.
Маркетплейс цифрових товарів вимагає надійної модерації, швидкого пошуку та автоматичних виплат. Розберемо ключові проблеми.
Проблеми, які вирішуємо
Elasticsearch для пошуку — в 10 разів швидше за MySQL-пошук, релевантність вища на 40%. Stripe Connect для виплат — економить 40% часу на бухгалтерії. CQRS для аудиту — всі операції логуються.
Модерація контенту. Автори завантажують файли з вірусами, дублікатами або порушенням ліцензій. Автоматична перевірка на основі hash-сум та сканування на malware знижують ручну роботу на 80%. Elasticsearch documentation
Виплати авторам. Велика кількість дрібних транзакцій, утримання комісії, податкові звіти. Stripe Connect обробляє виплати автоматично, а система акумулює баланс до мінімальної суми.
Пошук і фільтрація. Користувачі залишають сайт, якщо пошук повільний або нерелевантний. Elasticsearch з кастомними аналізаторами дає результати за мілісекунди, сортування за популярністю, новизною, ціною та рейтингом.
Як ми це робимо
Backend на PHP 8.3 / Laravel 11, база — PostgreSQL з Redis для кешу, пошук — Elasticsearch. Використовуємо Repository pattern для ізоляції бізнес-логіки, CQRS для операцій виплат, Event Sourcing для аудиту всіх дій.
Модерація будується на ланцюжку перевірок:
class ProductModerationService
{
public function submit(Product $product): void
{
$product->update(['status' => 'under_review']);
$checks = [
'images_quality' => $this->checkImagesQuality($product),
'description_len' => strlen($product->description) >= 200,
'preview_exists' => $product->preview_files->isNotEmpty(),
'files_scan' => $this->scanFilesForMalware($product),
];
$autoApprove = !in_array(false, $checks);
if ($autoApprove) {
$product->update(['status' => 'active']);
} else {
ModerationTask::create([
'product_id' => $product->id,
'checks' => $checks,
'priority' => $this->calculatePriority($product),
]);
}
}
}
Способи доставки контенту покупцю
| Спосіб доставки | Затримка | Вимоги | Безпека |
|---|---|---|---|
| Пряме посилання на завантаження | Миттєво | CDN, підписані URL | Висока (токен + IP bind) |
| Посилання по email | 1-5 хвилин | Поштовий сервер, генерація посилань | Середня (посилання можна переслати) |
Пряме посилання — пріоритетний варіант: після оплати користувач отримує згенерований URL з обмеженим терміном дії та прив'язкою до IP. Повторне завантаження доступне в особистому кабінеті.
Автоматизація виплат авторам
class AuthorPayoutService
{
public function processPayout(int $authorId): PayoutResult
{
$author = User::findOrFail($authorId);
$balance = $author->payout_balance;
if ($balance < config('marketplace.min_payout')) {
return PayoutResult::belowMinimum($balance);
}
if ($author->stripe_connect_id) {
$transfer = $this->stripe->transfers->create([
'amount' => (int)($balance * 100),
'currency' => 'rub',
'destination' => $author->stripe_connect_id,
'metadata' => ['author_id' => $authorId],
]);
$author->decrement('payout_balance', $balance);
Payout::create([
'author_id' => $authorId,
'amount' => $balance,
'stripe_id' => $transfer->id,
'status' => 'completed',
]);
return PayoutResult::success($balance);
}
return PayoutResult::noPaymentMethod();
}
}
Аналітика для авторів у реальному часі
Route::get('/api/author/stats', function (Request $request) {
$author = auth()->user();
return response()->json([
'total_revenue' => Sale::where('author_id', $author->id)->sum('author_payout'),
'total_sales' => Sale::where('author_id', $author->id)->count(),
'this_month' => Sale::where('author_id', $author->id)
->whereMonth('created_at', now()->month)
->sum('author_payout'),
'top_products' => Sale::where('author_id', $author->id)
->groupBy('product_id')
->orderByRaw('COUNT(*) DESC')
->limit(5)
->with('product:id,name,thumbnail')
->selectRaw('product_id, COUNT(*) as sales_count, SUM(author_payout) as revenue')
->get(),
'pending_payout' => $author->payout_balance,
]);
})->middleware('auth');
Як автоматизувати модерацію цифрових товарів?
Використовуємо hash-файлів (md5/sha1) для пошуку дублікатів, аналіз EXIF-даних зображень, перевірку ліцензійних міток. При проходженні всіх перевірок товар публікується автоматично, інакше створюється завдання модератору з пріоритетом. Такий підхід скорочує час модерації з 2 днів до 5 хвилин.
Чому варто використовувати Elasticsearch для пошуку?
Elasticsearch дає повнотекстовий пошук з морфологією російської мови, фасетну фільтрацію, сортування за будь-якими полями. Обробляє сотні запитів за секунду без навантаження на БД. Індексуємо не лише назви, але й мета-поля, описи, теги — релевантність підвищується на 40% порівняно з LIKE-запитами.
Порівняння пошукових рішень
| Рішення | Швидкість (мс) | Релевантність | Навантаження на сервер |
|---|---|---|---|
| Elasticsearch | 5-50 | Висока | Низька (асинхронно) |
| Meilisearch | 10-100 | Середня | Низька |
| MySQL LIKE | 500-2000 | Низька | Висока (блокування) |
Процес роботи
- Аналітика — вивчаємо специфіку товарів, очікуване навантаження, вимоги до модерації.
- Проектування — архітектура БД, схема виплат, структура API.
- Реалізація — спринти по 2 тижні, daily-мітинги, code review.
- Тестування — навантажувальне тестування (k6), перевірка безпеки, юзабіліті.
- Деплой — CI/CD на Vercel або власний сервер, моніторинг помилок.
Терміни орієнтовно: 25–35 робочих днів
Вартість розраховується індивідуально після аудиту вашого ТЗ. Напишіть — оцінимо проєкт.
Приблизна архітектура мікросервісів
При високих навантаженнях розбиваємо моноліт на мікросервіси: сервіс користувачів, сервіс продуктів, сервіс виплат, сервіс аналітики. Спілкування через чергу (RabbitMQ) і API Gateway. Це дозволяє горизонтально масштабувати кожен компонент.Що входить в роботу
- Вихідний код (Laravel + Vue) в закритому репозиторії
- Повна документація API (Swagger)
- Доступи до адмінки та сервера
- Навчання команди (2-3 вебінари)
- Гарантія 3 місяці на баги
- Підтримка за SLA після запуску
Типові помилки при розробці маркетплейсу
- Відсутність захисту від повторного завантаження — зловмисники поширюють посилання. Рішення: використовувати одноразові токени.
- Ручна модерація без автоматизації — вузьке горлишко. Рішення: авто-перевірки з довірою до авторів.
- Поганий пошук — користувачі йдуть. Рішення: Elasticsearch/Meilisearch.
- Невірна архітектура виплат — проблеми з податками. Рішення: Stripe Connect з урахуванням комісій.
Отримайте консультацію інженера з архітектури маркетплейсу. Ми з досвідом 5+ років вже запустили 20+ таких платформ. Гарантуємо якість та прозору співпрацю.







