The Ops Community ⚙️

Saar Ryan Cohen
Saar Ryan Cohen

Posted on

How to build your own “DoorDash” app

Apractical, (relatively) easy-to-do tutorial for developing an event-driven, distributed food delivery app, just like “Uber Eats” or “Wolt”.

Many thanks to Dhanush Kamath for the use case and supporting article.

Meet Fastmart — The fastest and most reliable food delivery app ever built.

Fastmart

The technology stack we will use -

Technologies

  • Node.js as our primary dev-lang
  • MongoDB for order persistency
  • Memphis is a message broker for developers
  • Kubernetes will host our microservices

Event-driven architecture using Message Broker

High-Level Plan

  1. Install Minikube using brew package manager.
  2. Install Memphis over Minikube.
  3. Clone “Fastmart” GitHub repo.
  4. Review the code, the different services, and how they interact with each other.
  5. Deploy “Fastmart” over Kubernetes.
  6. Order food!

Let’s start!

1.Install Minikube
For the installation commands, please head here: https://minikube.sigs.k8s.io/docs/start/

minikube is local Kubernetes, focusing on making it easy to learn and develop for Kubernetes.

All you need is Docker (or similarly compatible) container or a Virtual Machine environment, and Kubernetes is a single command away: minikube start

What you’ll need

  • 2 CPUs or more
  • 2GB of free memory
  • 20GB of free disk space
  • Internet connection

Container or virtual machine manager, such as Docker, Hyperkit, Hyper-V, KVM, Parallels, Podman, VirtualBox, or VMware Fusion/Workstation

Output -

output

Verify minikube is health —

kubectl get ns

Output —

NAME STATUS AGE
default Active 31h
kube-node-lease Active 31h
kube-public Active 31h
kube-system Active 31h

2.Install Memphis

helm repo add memphis https://k8s.memphis.dev/charts/ && helm install memphis memphis/memphis — set connectionToken=”memphis” — create-namespace — namespace memphis

Let’s wait a minute or two, allowing the different components to reach “Running” state.

kubectl get pods -n memphis

Output -

NAME                           READY   STATUS             RESTARTS      AGE
k8s-busybox-68867bb9b7-sqdql   0/1     CrashLoopBackOff   4 (68s ago)   3m13s
memphis-broker-0               3/3     Running            4 (55s ago)   3m13s
memphis-ui-fd54f5bd6-zzqd4     0/1     CrashLoopBackOff   4 (79s ago)   3m13s
mongodb-replica-0              1/1     Running            0             3m13s
Enter fullscreen mode Exit fullscreen mode
NAME                           READY   STATUS             RESTARTS      AGE
k8s-busybox-68867bb9b7-sqdql   0/1     CrashLoopBackOff   4 (76s ago)   3m21s
memphis-broker-0               3/3     Running            4 (63s ago)   3m21s
memphis-ui-fd54f5bd6-zzqd4     1/1     Running            5 (87s ago)   3m21s
mongodb-replica-0              1/1     Running            0             3m21s
Enter fullscreen mode Exit fullscreen mode

k8s-busybox can be ignored. It will be fixed in the coming versions

3.Clone the Fastmart repo

git clone https://github.com/yanivbh1/FastMart.git

4.System Architecture, Code, and Flow

architecture

Follow the numbers to understand the flow.

FastMart has three main components:

order-service - Exposes REST endpoints that allow clients to fetch the food menu, place an order and track the order in real-time.

A new order will be saved in mongo with the status “Pending” and will be produced (Pushed) into the “orders” station

GET: /<orderId>
Example: curl http://order-service:3000/30
POST: /<order_details>
Example: curl -X POST http://order-service:3000/api/orders -d ‘{“items”:[{“name”:”burger”,”quantity”:1}], “email”:”yaniv@memphis.dev”}’ -H ‘Content-Type: application/json’

example

The code responsible for communicating with Memphis will be found on -

./order-service/src/services/mqService.js

const memphis = require(“memphis-dev”);
const { logger } = require(‘./loggerService’)
const MEMPHIS_HOST = process.env.MEMPHIS_HOST || ‘localhost’; // create MQ connection string using environment variable
const MEMPHIS_USERNAME = process.env.MEMPHIS_USERNAME;
const MEMPHIS_TOKEN = process.env.MEMPHIS_TOKEN;
let ordersStation_producer = null;
const memphisConnect = async () => {
try {
logger.info(
Memphis — trying to connect)
await memphis.connect({
host: MEMPHIS_HOST,
username: MEMPHIS_USERNAME,
connectionToken: MEMPHIS_TOKEN
});
logger.info(
Memphis — connection established)
ordersStation_producer = await memphis.producer({
stationName: “orders”,
producerName: “order_service”,
});
logger.info(
ordersStation_producer created)
} catch(ex) {
logger.log(‘fatal’,
Memphis — ${ex}`);
memphis.close();
process.exit();
}
}
/**

  • Publish order to station
  • @param {Object} order — order object containing order details / const publishOrderToStation = (order) => { ordersStation_producer.produce({message: Buffer.from(JSON.stringify(order))}); logger.info(Memphis — order ${order._id} placed); } /*
  • An express middleware for injecting queue services into the request object.
  • @param {Object} req — express request object.
  • @param {Object} res — express response object.
  • @param {Function} next — express next() function. */ const injectPublishService = (req, res, next) => { // add all exchange operations here const stationServices = { publishOrderToStation: publishOrderToStation } // inject exchangeServices in request object req.stationServices = stationServices; next(); } module.exports = { injectPublishService: injectPublishService, memphisConnect: memphisConnect, }`

email-service - Responsible for notifying the client of the different stages.

email-service consumer messages from two stations: orders and notifications.

As soon as an order is inserted into the station, the email service notifies the client with an order confirmation.

At the same time listens for new notification requests of other services

stations

resturant-service - Responsible for fulfilling an order.

  1. Consume an order
  2. Process the order
  3. Change order status at the MongoDB level to “Accepted”
  4. Using constant sleep time to mimic the preparation of the food by the restaurant
  5. Change order status at the MongoDB level to “Delivered”
  6. Sending notification to the client

order

5.Deploy “Fastmart” over Kubernetes

Fastmart repo tree -

Fastmart files tree

To deploy Fastmart namespace and different services,

please run kubectl apply -f k8s-deployment.yaml

kubectl get pods -n fastmart

Output -

READY   STATUS             RESTARTS   AGE
email-service-5ddb9b58d6-bq2xd       0/1     CrashLoopBackOff   3          103s
fastmart-ui-5c9bc497bd-kn4lk         1/1     Running            0          11m
orders-service-5b689b66-4h8t9        0/1     CrashLoopBackOff   7          11m
resturant-service-6d97cf6fdc-c9mvs   0/1     Completed          4          103s
Enter fullscreen mode Exit fullscreen mode

Let’s understand why Fastmart services cant start

kubectl logs email-service-5ddb9b58d6-bq2xd -n fastmart

Output -

> email-service@1.0.0 start
> node ./index.js

17-05-2022 07:10:09 PM - info: Sleeping for 300ms before connecting to Memphis.
17-05-2022 07:10:09 PM - info: Memphis - trying to connect
17-05-2022 07:10:09 PM - info: email-service started
17-05-2022 07:10:09 PM - fatal: Memphis - User is not exist
Enter fullscreen mode Exit fullscreen mode

It appears that the services try to connect to “Memphis” with the user “fastmart” which does not exist and we require to create it.

The simplest way to add a new user would be through the UI, but let’s do it via CLI.

Please install Memphis CLI via here.

$ mem
Usage: index <command> [options]
Options:
-V, — version output the version number
-h, — help display help for command
Commands:
connect Connection to Memphis
factory Factories usage commands
station Stations usage commands
user Users usage commands
producer Producers usage commands
consumer Consumer usage commands
init Creates an example project for working with Memphis
help display help for command
Factory is the place to bind stations that have some close business logic
Factory Commands:
ls List of factories
create Create new factory
edit Edit factory name and/or description
del Delete a factory
Station is Memphis’ queue/topic/channel/subject
Station Commands:
ls List of stations
create Create new station
info Specific station’s info
del Delete a station
Manage users and permissions
User Commands:
ls List of users
add Add new user
del Delete user
Producer is the entity who can send messages into stations
Producer Commands:
ls List of Producers
Consumer is the entity who can consume messages from stations
Consumer Commands:
ls List of Consumers

To connect the CLI with Memphis control plane we need —

  • root password

kubectl get secret memphis-creds -n memphis -o jsonpath=”{.data.ROOT_PASSWORD}” | base64 — decode
OqEO9AbncKFF93r9Qd5V

  • memphis control-plane url

kubectl port-forward service/memphis-cluster 7766:7766 6666:6666 5555:5555 — namespace memphis > /dev/null &

Now, connect the CLI

mem connect — user root — password bpdASQlhwWNzFt4JwLQo — server localhost:5555

cli

Add the user “fastmart”

mem user add -u fastmart — type application

Or via the UI

ui

details

**Soon after we will create the user,

the pods will restart automatically and reconnect with Memphis.**

List of factories encapsulate stations

Station overview

overview

6.Order food!
To expose the orders-service through localhost, run -

kubectl port-forward service/orders 9001:80 — namespace fastmart > /dev/null &

Get the menu

curl localhost:9001/api/menu

Output -

{“items”:[{“name”:”burger”,”price”:50},{“name”:”fries”,”price”:20},{“name”:”coke”,”price”:10}]}

Make an order

curl -X POST localhost:9001/api/orders -d ‘{“items”:[{“name”:”burger”,”quantity”:1}], “email”:”test@gmail.com”}’ -H ‘Content-Type: application/json’

An email should arrive shortly at the email address specified above.

Thanks!

app

Latest comments (72)

Collapse
 
magis_tvs profile image
Magis TVs

Mantente al día con tus programas favoritos descargando Magis TV APK gratis y disfruta de contenido sin límites en tu dispositivo.

Collapse
 
loranzobb profile image
LoranzoBB

Thanks for the fantastic walkthrough! If anyone's planning U/X testing alongside app development, you might also like our Bounce and Slide rentals in Santa Clara — we keep the coding workflow fun with a bit of playtime. Check it out at yoyojump.com/party-rental-santa-cl...

Collapse
 
loranzobb profile image
LoranzoBB

good

Collapse
 
loranzobb profile image
LoranzoBB

This is the kind of dev content I wish I had when starting coc mod apk (cocmodapk.org). Your focus on clean API flow and UI structure aligns perfectly with the challenges we faced. Thanks for sharing this!

Collapse
 
loranzobb profile image
LoranzoBB

Super helpful guide! I recently worked on braums menu with prices (braums-menu.com), and while it’s food-based too, your structured approach to delivery logic would’ve saved me hours. Bookmarked this!

Collapse
 
loranzobb profile image
LoranzoBB

Awesome breakdown! I love how clearly you’ve mapped out the backend logic. I tried building something similar for a prank app — fake phonepe apk (fakephonepeapks.com) — and your post really validates some of the architecture decisions we made. Great stuff!

Collapse
 
njpaycheck01 profile image
Eliza Beth

The online portal is super easy to navigate—just enter your ticket details and you're good to go. No more waiting in line at the courthouse or stressing about missed deadlines. It’s a reliable and efficient service for anyone dealing with minor violations. Proceed to pay your ticket

Collapse
 
loranzobb profile image
LoranzoBB

Building a food delivery app like DoorDash can be enhanced with an event-driven architecture using technologies such as Node.js and MongoDB, just like Fastmart. now lets talk about great food menu site braum menu​, and if you wana manage your files on your phone then download mt manager apk​, and you can prank your friends with fake phonepe apk​ if you wana get gta 6 related updates then visit gta6updates​ and follow tech bigo​ for tech related updates ​

Collapse
 
loranzobb profile image
LoranzoBB

waiting, **Soon after we will create the user,

the pods will restart automatically and reconnect with Memphis.**
now lets talk about coc mod apk, clash of clans mod apk is a modefied apk for coc apk that give unlimited gold gems and everything

Collapse
 
maryvang profile image
MaryVang

This guide on building your own “DoorDash”‑style app is super insightful—breaking it down into frontend, backend, real-time delivery tracking, and even user roles like drivers, restaurants, and customers really made it feel doable. I especially liked how you touched on scalability and the importance of intuitive UX design. It reminded me of Fajr time in Karachi—those peaceful, focused early hours are perfect for diving into app architecture or refining a tricky bit of code without distractions. Do you find you’re more productive and creative when working on technical projects in the calm of the pre-dawn hours?

Some comments may only be visible to logged-in visitors. Sign in to view all comments.