Marketplace10 weeks

ENEZ MarketMarketplace for Ukrainian Sellers

Separate apps for buyers, sellers and administrators

Multi-vendor marketplace: a storefront for buyers, a seller workspace and an admin panel — separate apps on a shared API. Search on OpenSearch, real-time chat, 200+ tasks in 5 sprints.

ENEZ Market — Marketplace for Ukrainian Sellers
Challenge

Buyers, sellers and administrators need entirely different interfaces, and a catalogue of thousands of products has to be searchable by any attribute instantly.

Result

Separate React frontends for each role on top of one NestJS API, faceted search on OpenSearch and chat over Socket.io with Redis. The project is going into production.

Key features

  • Storefront, seller workspace & admin
  • Faceted search & filters
  • Real-time chat
  • Orders & payments
  • Media storage
  • CRM integrations
  • Admin panel

How it's built

A multi-vendor marketplace where several sellers compete on one product card: a storefront, a seller cabinet and an admin panel on a single API, with search, delivery, payments and fiscal receipts wired in. These are the decisions that shaped it.

3
Frontends, one API
11
Order states
4
Delivery carriers
103
Schema migrations

A product is not an offer

The catalogue product and the seller's offer are separate entities. One card describes the thing; each seller attaches an offer to it with its own price, stock, media and wholesale price tiers.

Everything difficult about a marketplace follows from that split: matching an incoming item to an existing product, merging duplicates that slipped through, and deciding which offer a buyer sees first. Getting it wrong the other way — one product row per seller — produces a catalogue where the same item appears forty times and no filter can fix it.

Search that does not hand the page to one seller

Search runs on OpenSearch, with product attributes indexed as nested documents so filters can be built per category instead of per field, and with the full category path indexed so a filter on a parent category still finds everything underneath.

Results are not a flat relevance list. Offers are bucketed by seller, buckets are ordered by their best offer, and then interleaved — so a marketplace with one large seller and fifty small ones still shows the small ones. A marketplace that lets its biggest seller own every result page stops attracting new sellers.

Sellers upload feeds, not spreadsheets by hand

Catalogue growth comes from an import pipeline: raw items land first, field mappings are saved per seller as presets, media problems are recorded per item instead of failing the batch, and matching proposes the catalogue product each item belongs to.

New brands and categories wait for approval before they reach search facets. Without that gate, one careless feed renames a whole branch of the catalogue.

Eleven states, and who moved them

An order goes from created through paid, processing, awaiting shipment, shipped, delivered and completed, with cancellation, refund and return as first-class states rather than flags.

Every transition records what caused it and who did it: order creation, a payment webhook, a refund job, a Nova Poshta tracking push, an admin, a seller's manager or a scheduler. When a buyer asks why an order says what it says, the answer is in the row, not in the logs.

Money, delivery and the tax office

Payments run through LiqPay, monobank and Hutko behind one provider interface, so adding an acquirer is a new file rather than a new branch through checkout. Cash on delivery stays a payment method like any other.

Delivery covers Nova Poshta, Ukrposhta, Meest and Delivery Auto — branch and locker directories, label printing, and tracking that pushes status back into the order. Fiscal receipts go through Checkbox, Cashalot or Vchasno, because in Ukraine a receipt is not a feature request, it is the law.

Built to be operated

Buyer-to-seller chat runs over websockets with Redis behind it. Notifications, reviews, complaints, audit trails, CMS blocks for the footer and static pages, seller analytics and an advertising module all live as their own modules on the same API.

One hundred and three migrations is the honest measure of a marketplace: the schema keeps moving because the business keeps discovering what it actually sells.

The result

A working multi-vendor marketplace at enez.com.ua — buyer storefront, seller cabinet and admin panel on one API, with faceted search, four carriers, three acquirers and fiscal receipts in production.

Next project
Platform

Services Helper

Clients post jobs, specialists pick them up

View case
Services Helper — Services Marketplace

Want something similar?

Tell us about your project and we'll build it with the same care and attention to detail.

Start a project →