ShortURL
ShortURL copied to clipboard
A distributed and highly available URL Shortener built on MERN stack, using Apache Zookeeper, cached using Redis, containerized by Docker.
ShortURL: A URL Shortening service 🔗
A distributed and highly available URL Shortener.
📚 | Introduction
- ShortURL is a distributed and highly available URL Shortening service, built on the MERN stack.
- It uses Redis as a cache, and MongoDB as a NoSQL database.
- It uses Nginx that acts as a load balancer, and a reverse proxy for the backend server.
- It uses Apache ZooKeeper to provide tokens for hash generation, and eliminates race conditions between nodes.
- The entire application is containerized by Docker, and orchestrated by k8s.
Disclaimer
- This is a demo application of a URL Shortener following the guidelines of efficient System Design.
- This is a project demonstrating the entire development process and is meant to be run in a local environment.
🚀 | Usage
- Install Docker Desktop and enable Kubernetes for a quick setup.
- Clone this repository:
git clone https://github.com/muKaustav/ShortURL.git
- Create a .env file with the following variables:
REACT_APP_MONGODB_URI="<enter your MongoDB URI>"
REACT_APP_REDIS_PORT=1111 (defaults to 6379)
REACT_APP_REDIS_HOST='redis-server' (name it as you like, but change the same in the docker-compose.yml file)
- Open the project folder and start the container with docker compose:
docker compose up --build
# We can also scale instances of an image for higher scalability or distribution.
Example: docker compose up --build --scale node-server=3
- Enjoy the project! 😉
🌐 | API Endpoints
GET:
/url/:identifier : Get the shortened URL from DB
/del : Delete the Zookeeper token
POST:
/url [body : {"OriginalUrl" : "url"}] : Shorten the URL and store in DB
Access the API using the following URLs:
Client: http://localhost:3000/
Load Balanced Server: http://localhost:4000/
📺 | Demonstration
📘 | System Design Schematic
⌛ | Architectural Discussion
- The availability of the application can be improved by using multiple Zookeeper instances, replicas of the DB, and a distributed cache, thus increasing the fault tolerance of the architecture.
- Adding load balancers in between the following improves the performance of the application, and reduces the load on any particular instance:
- client and server
- server and DB
- server and cache
-
CAP Theorem:
- We opt for an eventually consistent approach, as in case of a network partition, a URL Shortener should have low latency and high throughput at all times.
- Redirection of the user to the original URL should always have low latency as it directly impacts the business aspect of the application.
- We don't opt for a strongly consistent approach, as we would have to wait for the data to be replicated across the cluster, which decreases the availability and increases the latency of the application, thus impacting the user experience negatively.
- We opt for an eventually consistent approach, as in case of a network partition, a URL Shortener should have low latency and high throughput at all times.
💻 | References
- TinyURL System Design
- System Design : Scalable URL shortener service like TinyURL
- An Illustrated Proof of the CAP Theorem
- What is eventual consistency and why should you care about it?
- Redis Documentation
- Apache Zookeeper Documentation
- Nginx HTTP Load Balancing Documentation
- Docker Documentation
- Kompose Documentation
🍻 | Contributing
Contributions, issues and feature requests are welcome.
Feel free to check issues page if you want to contribute.
🧑🏽 | Author
Kaustav Mukhopadhyay
- Linkedin: @kaustavmukhopadhyay
- Github: @muKaustav
🙌 | Show your support
Drop a ⭐️ if this project helped you!
📝 | License
Copyright © 2021 Kaustav Mukhopadhyay.
This project is MIT licensed.