Open source · Self-hosted · Built in Tokyo

The delivery platform you run in your own cloud.

Your business already takes orders. Tasuki adds the delivery side: your system sends an order over the API, Tasuki finds the nearest driver, streams the driver's position to your customer's phone, and reports every status change back to you.

Early and honest: orders, live tracking and the fleet pipeline run today; dispatch is being finished. See exactly what's built.

A driver rides from the store to the customer on city streets 店 Store 家 Customer
  • Go
  • Python · Django
  • Kafka
  • PostgreSQL
  • Valkey
  • OSRM
  • React · MapLibre
  • Kubernetes
  • Terraform
  • Argo CD
  • OpenTelemetry

Why it exists

Taking orders was the easy part.

When customers start asking for delivery, you need a second system. It must track every moving driver every few seconds, assign the right one in under a minute, never lose or double-book an order, and keep each customer's map live. That is a different kind of software from a shop or an ordering app, and it should not share a server with one. Tasuki is that system, ready to deploy next to yours.

Live location at scale

GPS updates flow through Kafka, not your main database. Hundreds a second never slow your shop down.

Orders never lost or doubled

Idempotency keys, a transactional outbox and deduplicated events make every retry safe.

Customers see their delivery

A signed tracking link per order, live in any phone browser. Nothing to install. English and Japanese.

Runs in your account

Your cloud, your region, your data. No per-delivery fee to a vendor and no lock-in. MIT licensed.

Who it's for

Built for whoever runs the deliveries.

Businesses with their own drivers

Restaurant groups, grocers, pharmacies, retailers. Your checkout calls the API; your drivers get offers on their phones; your customers get a live link.

Delivery companies

Serve many merchants from one installation. Every merchant is a tenant with its own API keys and stores, and every query is scoped to its tenant.

Engineering teams

Rather not spend a year building dispatch and tracking? Start from a documented, tested design and change what your business needs.

How it works

Every order is handed on, never dropped.

A 襷 (tasuki) is the sash that ekiden relay runners hand to each other. Tasuki hands every order on the same way: your system, then dispatch, then a driver, then your customer. The platform's job is to make sure the sash is never dropped, never handed to two runners, and always visible.

  1. 1

    Your system creates the delivery

    Ask for a price and an ETA, then create the order with an Idempotency-Key. You get an order ID and a tracking link for your customer.

    POST /v1/quotes · POST /v1/orders
  2. 2

    Dispatch finds a driver

    The nearest free driver gets an offer with a 30-second timer. On a decline or a timeout, the next one does. Travel times come from real roads (OSRM).

    offers over server-sent events
  3. 3

    Drivers move, customers watch

    The driver's phone sends GPS in small batches. Your customer's tracking page moves the marker live and keeps the ETA honest.

    POST /v1/locations · GET /v1/track/…/stream
  4. 4

    Your system stays in sync

    Every change (confirmed, assigned, picked up, delivered) is an event with a full history. Signed webhooks that push it to you are next on the roadmap.

    GET /v1/orders/{id} · webhooks (next)

Integrate

A few HTTP calls, not a migration.

Keep your shop, your app and your database. Tasuki sits beside them and talks plain JSON over HTTPS. These are the real endpoints: run make up and they answer on your laptop.

# Locally (make up): ORDERS=http://localhost:8000

# 1. Ask for a price and an ETA. A quote is valid for 2 minutes.
curl "$ORDERS/v1/quotes" \
  -H "Authorization: Bearer $TASUKI_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "store_id": "str_01JA2Q…",
    "dropoff": {
      "lat": 35.6618, "lng": 139.6983, "ward": "shibuya",
      "address": "1-2-3 Jinnan, Shibuya-ku",
      "customer_name": "Sato Hana", "customer_phone": "090-1234-5678"
    }
  }'
# 201 {"quote_id": "quo_01JA2R…", "fee_yen": 742, "eta_seconds": 1920, "expires_at": "…"}

# 2. Turn the quote into an order. Retrying with the same key never creates a second one.
curl "$ORDERS/v1/orders" \
  -H "Authorization: Bearer $TASUKI_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: checkout-8812" \
  -d '{"quote_id": "quo_01JA2R…"}'
# 201 {"order_id": "ord_01JA2S…", "status": "confirmed", "tracking_url": "…/track/eyJhbGci…"}

Full reference: OpenAPI spec · every endpoint, event and stream. IDs and tokens above are shortened.

What's inside

What works today, and what comes next.

Nothing on this page is marked as working unless it is written, tested and in the repository.

  • Works today
  • In progress
  • Next
  • Planned
Works today

Orders API

Quotes, idempotent orders, cancellation and status history. Django and PostgreSQL, tested against real database races.

Works today

Transactional outbox

Order changes and their events commit together, then reach Kafka in order. No lost events, no phantom ones.

Works today

Fleet ingest

Authenticated GPS batches from drivers. Under overload it answers 503 with Retry-After instead of falling over.

Works today

Live fleet state

The latest position of every driver in Valkey, geo-indexed for nearest-driver queries, rebuilt from Kafka after a loss.

Works today

Live tracking

Server-sent event streams for one order (customers) or the whole fleet (operators), with a hosted page in English and Japanese.

Works today

Road routing

OSRM on real OpenStreetMap roads for travel times and routes, with a straight-line fallback if it is down.

Works today

City simulator

Merchants, customers and drivers through the public APIs, with repeatable scenarios such as a rainy Friday lunch.

Works today

SLOs as code

Five SLOs with burn-rate alerts, a runbook per alert, Grafana dashboards in git, and a gate that blocks risky releases.

In progress

Dispatch

Nearest-driver offers with timeouts and ETAs for quotes. Greedy first; batched matching comes later.

In progress

Cloud platform

Terraform for AWS (VPC, EKS, Karpenter) and GitOps with Argo CD: written and checked, first cluster run next.

Next

Signed webhooks

Every order event pushed to your endpoint, signed, retried, with a dead-letter queue and replay.

Next

Operations dashboard

Orders, drivers and the live map behind a login. Manual assignment, API keys and webhook settings.

Next

Driver app

Offers, navigation, pickup and proof of delivery on the driver's phone, using the same public API.

Next

Any city

Service zones from GeoJSON, any OpenStreetMap region, any currency and tax rule. Today the service area is Tokyo.

Planned

AI operations copilot

Ask "why is this order late?" and get an answer built from read-only tools over orders, dispatch and the fleet.

Planned

Delivery windows and money

Bookable windows (時間帯指定) without overbooking, a double-entry ledger, and weekly driver payouts.

Architecture

Two systems with different rules.

Orders are few and precious. Locations are many and disposable. Tasuki keeps the two apart, so a flood of GPS points can never stop an order, and the order path never trades correctness for speed.

Orders and moneyLocations and tracking
Volume at peakSingle-digit writes a second, even in a surgeAbout 750 GPS updates a second
"Correct" meansExactly-once effects: never lost, never charged twiceLatest wins: a missed point is harmless if the next one arrives
Source of truthPostgreSQL, with a transactional outboxThe Kafka log; Valkey is a cache rebuilt from it
On failureReject or queue, never guessServe the last known position and say how old it is
LanguagePython and Django: rich domain model, transactionsGo: high throughput, small memory, cheap concurrency
Tasuki architecture Your app creates orders in the orders API, backed by PostgreSQL. An outbox relay publishes order events to Kafka. Driver apps send GPS batches to fleet-ingest, which publishes to Kafka. fleet-state keeps the live fleet in Valkey; dispatch reads it, asks OSRM for travel times and sends offers to drivers; tracking streams positions to customers and the ops console. Signed webhooks to your backend are planned. ORDERS AND MONEY · Python · exactly once LOCATIONS AND DISPATCH · Go · latest wins Your appcheckout · OMS Driver appGPS · offers Your backendwebhooks · next Ops consolelive fleet map Customer's phonetracking page orders APIDjango · DRF PostgreSQLorders · outbox outbox relayin order, per order Kafkacourier.locations · orders.events · dispatch.events fleet-ingestGPS batches fleet-statelatest per driver dispatchoffers · ETAs trackingSSE fan-out Valkeylive fleet cache, rebuilt from Kafka routingOSRM · real roads REST dispatch.events orders.events GPS offers (SSE) signed webhooks SSE
What runs today, plus the webhooks (dashed) that come next. Every arrow into or out of Kafka is at-least-once, and every consumer deduplicates on event_id. Read the full system design.
Why server-sent events and not WebSockets?

Tracking only flows one way, from the platform to the screen. Server-sent events run over plain HTTP, pass through proxies and load balancers without special setup, and reconnect on their own. Drivers send GPS the other way as small batched HTTPS requests, which survive flaky mobile networks better than a long-lived socket.

Scale

Sized for 1.5 million orders a month in one city.

Every design choice has a number behind it. These are the targets for a busy city operator, with room for a rainy Friday, when demand triples and every customer is watching the map.

50,000orders a day, 12 % of them in the busiest hour
20/sorder capacity: a 3× rain surge with 4× headroom
750/sGPS updates from 3,000 drivers at peak
10,000customers watching live at the same time

These are design targets, not measurements yet. The simulator already has a design-scale rainy-Friday scenario. Load-test results will be published here with the scripts to reproduce them, and not before.

A surge is a capacity problem, not a throughput problem

At three times normal demand, orders want 18,000 deliveries an hour while drivers can do about 7,200. The servers cope easily; what breaks is the promise. So in a surge Tasuki quotes honestly: longer ETAs, fewer bookable windows, a surge fee. And it stays up.

Built to scale out

Every service is stateless and scales horizontally behind Kubernetes. Kafka is keyed by driver and by order, so each one's events stay in order while consumers spread across partitions. Karpenter adds spot nodes when load rises and removes them after.

When things break

Designed to bend, not fall over.

Every part fails eventually. Each failure below has a planned response, and each one becomes a game-day experiment with a written postmortem.

FailureWhat your customers seeWhat Tasuki does
Valkey (cache) lostNothing on orders or tracking; new assignments pause for secondsTracking reads Kafka, not the cache. fleet-state replays recent locations to rebuild it; dispatch waits for the rebuild.
Kafka unavailableOrders still accepted; status updates lateOutbox rows wait in PostgreSQL and drain later. Ingest sheds load with Retry-After.
Database failoverOrder creation fails for 1 to 2 minutesClients get 503 with Retry-After. Idempotency keys make every retry safe.
Routing (OSRM) downETAs a little less exactDispatch falls back to straight-line distance with a detour factor, and widens quotes.
Rain surge (3× demand)Longer ETAs, fewer windows, a surge feeQuotes follow driver supply. Priority shedding: orders, then dispatch, then tracking, then history.
One availability zone lostBrief retriesPods spread over three zones with disruption budgets; Multi-AZ database; Kafka replication factor 3.

Operate

Run like production from day one.

Written objectives, alerts that point to a runbook, and releases that stop themselves when reliability slips.

Service level objectives (28 days, rolling)
PromiseTarget
Quote and order requests succeed99.9 %
Orders are created in under 300 ms95 %
GPS points reach live state within 2 s99 %
Customers see positions younger than 10 s99 %
A driver accepts within 60 s of confirmation95 %
  • Error budgets with teeth. Multi-window burn-rate alerts, and a rollout gate that blocks canary releases while a budget is spent.
  • Observability as code. OpenTelemetry in every service; Prometheus, Loki, Tempo and Grafana dashboards kept in git.
  • Secure supply chain. Signed images with SBOMs, Trivy and gitleaks in CI, Kyverno admitting only signed images.
  • Least privilege. No static cloud keys (GitHub OIDC), restricted pod security, personal data encrypted per field.
  • Practised failure. A runbook for every alert, game-day plans with fault-injection scripts, and a postmortem template.

Deploy

Start on a laptop. Grow into a cluster.

Works today

One machine

Docker Compose runs PostgreSQL, Kafka, Valkey and every service, then the simulator fills the map.

cp .env.example .env
make up        # every service, healthy
make sim-up    # the city starts moving
open http://localhost:8088
Written, first run next

Kubernetes with GitOps

A Helm chart per service and an Argo CD app of apps, with Kyverno policies, Strimzi Kafka, CloudNativePG with backups, and canary releases through Argo Rollouts.

Written, first run next

AWS in one command

Terraform for the VPC, EKS and Karpenter (spot first). About $8 a day while it runs, and make aws-down takes it back to nearly zero.

Built in Tokyo

Ready for Japan. 日本の配送にも対応

The reference deployment covers Tokyo's 23 wards on real Tokyo roads. Japanese delivery has its own rules, so they are built in from the start.

  • Data stays in Japan. Everything runs in AWS Tokyo; disaster-recovery copies are designed to go only to Osaka.
  • APPI-minded. Customer names, phones and addresses are encrypted per field and never appear in events or logs.
  • Yen done right. Integer yen, 10 % consumption tax rounded down once per order (端数切り捨て).
  • Bilingual. The tracking page speaks English and Japanese.
  • Delivery windows. 時間帯指定 booking without overbooking is on the roadmap.

Roadmap

Where Tasuki is going.

Released as semantic versions with a changelog. Follow along on GitHub.

  1. Now

    Platform and the first slice

    Orders, fleet ingest, live tracking, routing, the simulator and the live map; finishing dispatch; the first cluster run on AWS; published load-test numbers; the first game day and postmortem.

  2. Next

    Open it to any business

    Service zones, currency and tax for any city; signed webhooks; an operations dashboard; a driver app; and a single-server install for smaller teams.

  3. Then

    AI operations copilot

    An assistant that explains late orders and unusual patterns, using read-only tools over orders, dispatch and the fleet.

  4. Later

    Depth

    Batched dispatch, delivery windows, an order saga on Temporal, a double-entry ledger with daily reconciliation, and OAuth2 for partners.

Questions

Before you ask.

Is it free?

Yes. Tasuki is MIT licensed: run it, change it and use it commercially. You pay only for the cloud resources you run it on.

Can I use it outside Tokyo today?

Not yet. The service area, the zones and the pricing are Tokyo's for now. Making them configurable for any city is the first item on the "Next" list.

Do I need Kubernetes?

Not to try it: Docker Compose runs the whole stack on one machine. The production path today is Kubernetes. A single-server production install for smaller teams is on the roadmap.

Where does my data live?

In your own cloud account and the region you choose. Tasuki sends nothing anywhere else.

Is there a driver app?

Not yet. The simulator plays every driver through the same public API a real app will use, so any app can integrate today. A driver app is on the "Next" list.

Is this a real company?

Tasuki is an open-source project, not a delivery company. The merchants, drivers and customers in the demo are generated by the simulator. The software, the infrastructure and the reliability work are real.

Running deliveries, or about to?

Tell me about your city, your daily order volume and the system you run today. I'd like to hear what Tasuki would need to run your deliveries.