QueueLess is a comprehensive, multi‑tenant queue management platform designed for businesses of all types – hospitals, banks, shops, restaurants, and more. It allows administrators to create and manage multiple locations (places), providers to handle queues in real time, and users to join queues, track their position, receive notifications, and provide feedback. The system features live updates via WebSocket, email/push notifications, Razorpay payment integration, role‑based access control, and detailed analytics.
- Features
- Tech Stack
- Architecture Overview
- Screenshots & Demo
- Getting Started
- API Documentation
- WebSocket Real‑Time Updates
- Testing
- Deployment
- Troubleshooting
- Future Roadmap
- Contributing
- License
- Code of Conduct
- Search & Discover: Find places by name, type, location, or rating.
- Join Queues: Choose regular, group, or emergency tokens (with provider approval).
- Real‑time Updates: Live position, wait time, and status changes via WebSocket.
- Notifications: Email and push notifications before your turn, and when a queue becomes short.
- Feedback: Rate your experience with detailed dimensions (staff, service, wait time).
- Favorites: Save favourite places for quick access.
- Token History: View past tokens and ratings.
- Per‑Queue Notification Preferences: Customise when and how you are notified for each queue.
- Queue Management: Create, pause, resume, and reset queues.
- Token Handling: Serve next, complete, cancel tokens; view user details for each token.
- Emergency Approvals: Approve or reject emergency tokens with optional reason.
- Dashboard: Real‑time statistics, drag‑and‑drop reorder, export reports (PDF/Excel).
- Analytics: Token volume over time, busiest hours, average wait time trends.
- Place Management: Create and update places with images, location, contact info, business hours.
- Service Management: Define services under each place (e.g., cardiology, haircut) with average service time.
- Provider Management: Add providers (via token purchase), update their details, assign places, enable/disable accounts, reset passwords.
- Dashboard: Overview of all places, queues, providers, payment history, and analytics charts.
- Export: Generate admin reports in PDF/Excel.
- Alert Configuration: Set wait time thresholds to receive email alerts.
- Geographic Heat Map: Visualise queue load across all places.
- Authentication & Authorization: JWT‑based with roles:
USER,PROVIDER,ADMIN. Email verification via OTP. - Payments: Razorpay integration for purchasing admin/provider tokens.
- Audit Logging: All critical actions are logged for compliance and debugging.
- Rate Limiting: Per‑user and IP‑based limits to prevent abuse.
- Caching: Redis cache for places, services, queues.
- Monitoring: Prometheus metrics, Grafana dashboards, Loki logs.
| Layer | Technology |
|---|---|
| Backend | Java 25, Spring Boot 3.5, Spring Security, Spring Data MongoDB, Spring WebSocket, JWT, Lombok |
| Frontend | React 18, Vite, Redux Toolkit, React Bootstrap, React Router, Formik & Yup, React Toastify, Recharts, STOMP.js, SockJS, Firebase Cloud Messaging |
| Database | MongoDB (primary), Redis (caching, OTP store) |
| Messaging | WebSocket (STOMP) |
| Payments | Razorpay |
| Notifications | Firebase Cloud Messaging (push), JavaMail (SMTP) |
| Monitoring | Prometheus, Grafana, Loki, Promtail |
| DevOps | Docker, Docker Compose, Maven |
QueueLess follows a client‑server architecture with a Spring Boot backend and a React frontend.
- Backend: Exposes RESTful API and STOMP WebSocket endpoints. Business logic is encapsulated in services. Data persistence uses MongoDB (with geospatial queries). Redis is used for caching and temporary OTP storage.
- Frontend: Single‑page application built with React and Redux for state management. WebSocket client maintains live connections for queue updates.
- Real‑time Updates: When a queue changes (token added, served, completed), the backend broadcasts the updated queue via WebSocket to all subscribed clients.
- Security: All endpoints except public ones require a JWT token. Role‑based access is enforced with method‑level annotations (
@AdminOnly,@ProviderOnly, etc.). - Payments: Admin/Provider tokens are purchased via Razorpay; the backend generates and validates the tokens.
- Push Notifications: Firebase Cloud Messaging is used for sending notifications when a user’s turn is approaching or when a queue becomes short.
- User – can be USER, PROVIDER, or ADMIN.
- Place – represents a physical location (hospital, shop) with geo‑coordinates.
- Service – a specific service offered at a place (e.g., “Cardiology Consultation”).
- Queue – linked to a service and provider, contains a list of tokens.
- Token – represents a user’s spot in a queue; can be regular, group, or emergency.
- Feedback – submitted for completed tokens, includes multi‑dimensional ratings.
- AuditLog – records important actions for traceability.
- NotificationPreference – per‑queue notification settings for users.
(All screenshots are from the running application. Click on each collapsible section to view.)
Home Page (Click to expand)
Hero Section

Landing page with call‑to‑action, statistics, and live queue status.
Features & Testimonials




Overview of key features and user testimonials.
Places List & Place Details
Places List

All active places displayed with images, ratings, and addresses.
Place Detail

Main view with services, business hours, and location map.
Place Detail – Feedback & Best Time

User reviews, average ratings, and best‑time recommendations.
Advanced Search
Search Filters

Filter by location, rating, wait time, and features.
Search Results – Queues

Paginated results with place details and queue status.
Authentication & Registration
Login Page

All roles login with email and password.
Register Page – User


User registration – no payment required.
Email Verification
All roles receive a verification email after registration.
Example email (responsive):

Verification page:

Forgot Password

Enter email, receive OTP, then reset password.
Admin Token Purchase & Registration
Pricing Page (Admin)



Razorpay checkout for purchasing admin tokens.
Admin Token Generated

Copy the token and use it during registration.
Admin Registration


Choose “ADMIN” role and paste the purchased token. Token works once and expires.
Dashboard Overview
Personal dashboard showing active queues, favourite places, and token history.
Joining a Queue & Token Flow
Feedback Prompt (after token completion)

Users can choose regular, group, or emergency tokens, provide details, and give feedback after completion.
Notification Preferences
Per‑queue settings for reminder time, status changes, and best‑time alerts.
User Profile
Update name, phone, password, upload profile image, and manage preferences.
Provider Queue List
List of all queues with status and quick actions.
Queue Management
Drag‑and‑drop reorder, serve next, complete/cancel tokens, view user details, and reset.
Analytics & Exports
Charts for token volume, busiest hours, average wait time, and PDF/Excel exports.
Admin Overview
Statistics cards, quick actions, and tabs for places, queues, payments, providers, analytics.
Place Management
Create and edit places with images, location, business hours, and contact info.
Service Management
Add services under a place, set average service time, and enable group/emergency support.
Provider Management
List all providers, view performance, edit details, assign places, and reset passwords.
Payment History
Record of all token purchases (admin and provider) with transaction details.
Admin Queues
Admins can see all queues managed by their providers and toggle active status.
Analytics Charts
Token volume over time and busiest hours across all places.
Heat Map (Queue Load)
Geographic visualisation of queue load per place.
Alert Configuration
Set wait time thresholds; receive email alerts when exceeded.
About Us
Our mission, problem statement, solution, differentiators, and technologies used.
How to Use
Step‑by‑step instructions for each role, plus tips for best experience.
Privacy Policy & Terms of Service
Legal information page containing both privacy policy and terms of service.
Interactive OpenAPI documentation for all controllers and models.
Visualise metrics and logs from Prometheus and Loki.
Live Queue Updates
Watch as tokens are added, served, and completed – the queue updates instantly on all connected clients.
All screenshots are from the running application.
- Java 25 (or newer)
- Node.js 20+ and npm
- MongoDB (local or Atlas)
- Redis (local or cloud)
- Razorpay account (for payments)
- Firebase project (for push notifications)
- SMTP server (e.g., Gmail) for emails
-
Clone the repository
git clone https://github.com/harman-04/QueueLess.git cd QueueLess -
Backend setup
cd backend/backend ./mvnw clean install -
Frontend setup
cd .. cd ../frontend/queue-less-frontend npm install
Create a .env file in both backend and frontend directories.
MONGODB_URI=mongodb://localhost:27017/queueless REDIS_HOST=localhost JWT_SECRET=your_jwt_secret_key_here JWT_EXPIRATION=86400000 RAZORPAY_KEY=rzp_test_xxxxxxxxxx RAZORPAY_SECRET=your_razorpay_secret MAIL_USERNAME=your_email@gmail.com MAIL_PASSWORD=your_app_password SSL_KEY_STORE_PASSWORD=changeit APP_FRONTEND_URL=https://localhost:5173Note: For Gmail, use an App Password if 2FA is enabled.
VITE_API_BASE_URL=https://localhost:8443/api VITE_FIREBASE_API_KEY=your_firebase_api_key VITE_FIREBASE_AUTH_DOMAIN=your_firebase_auth_domain VITE_FIREBASE_PROJECT_ID=your_firebase_project_id VITE_FIREBASE_STORAGE_BUCKET=your_firebase_storage_bucket VITE_FIREBASE_MESSAGING_SENDER_ID=your_firebase_messaging_sender_id VITE_FIREBASE_APP_ID=your_firebase_app_id VITE_FIREBASE_VAPID_KEY=your_firebase_vapid_key VITE_RAZORPAY_KEY_ID=rzp_test_xxxxxxxxxxWhen running the full stack with Docker Compose, place a third .env file in the project root (the same directory as docker-compose.yml). This file supplies environment variables to the containers. It typically contains a superset of the variables needed by both backend and frontend, plus any additional configuration for the containers themselves.
Example docker-compose.env (or simply .env at the root):
# Backend MONGODB_URI=mongodb://mongodb:27017/queueless JWT_SECRET=your_jwt_secret_key_here JWT_EXPIRATION=86400000 RAZORPAY_KEY=rzp_test_xxxxxxxxxx RAZORPAY_SECRET=your_razorpay_secret MAIL_USERNAME=your_email@gmail.com MAIL_PASSWORD=your_app_password SSL_KEY_STORE_PASSWORD=changeit APP_FRONTEND_URL=https://localhost:5173 # Frontend VITE_API_BASE_URL=https://backend:8443/api VITE_FIREBASE_API_KEY=your_firebase_api_key VITE_FIREBASE_AUTH_DOMAIN=your_firebase_auth_domain VITE_FIREBASE_PROJECT_ID=your_firebase_project_id VITE_FIREBASE_STORAGE_BUCKET=your_firebase_storage_bucket VITE_FIREBASE_MESSAGING_SENDER_ID=your_firebase_messaging_sender_id VITE_FIREBASE_APP_ID=your_firebase_app_id VITE_FIREBASE_VAPID_KEY=your_firebase_vapid_key VITE_RAZORPAY_KEY_ID=rzp_test_xxxxxxxxxxcd backend/backend ./mvnw spring-boot:run The backend will start on `https://localhost:8443` (SSL enabled). You can access the API at `https://localhost:8443/api`. #### Frontend ```bash cd frontend/queue-less-frontend npm run devThe frontend will be available at https://localhost:5173.
The application uses HTTPS (port 8443 for backend, 443 for frontend in Docker) with self‑signed certificates. To avoid browser warnings, you can generate trusted certificates using mkcert.
- macOS:
brew install mkcert - Windows:
choco install mkcertor download from github.com/FiloSottile/mkcert - Linux:
sudo apt install libnss3-toolsthencurl -JLO "https://dl.filippo.io/mkcert/latest?for=linux/amd64" && chmod +x mkcert-v*-linux-amd64 && sudo mv mkcert-v*-linux-amd64 /usr/local/bin/mkcert
-
Create a local CA (one‑time):
mkcert -install
-
Generate certificates for localhost:
cd backend/src/main/resources mkcert localhost 127.0.0.1 ::1This creates
localhost+2.pemandlocalhost+2-key.pem. Rename them:mv localhost+2.pem localhost.pem mv localhost+2-key.pem localhost-key.pem
-
Convert to PKCS12 format (required by Spring Boot):
openssl pkcs12 -export -in localhost.pem -inkey localhost-key.pem -out localhost.p12 -name localhost -password pass:changeit
The password
changeitmatches the default inapplication.properties. -
Place the
.p12file insidesrc/main/resources/.
The application.properties already contains:
server.ssl.key-store=classpath:localhost.p12 server.ssl.key-store-password=${SSL_KEY_STORE_PASSWORD:changeit} server.ssl.key-store-type=PKCS12Make sure the password matches the one used when generating the .p12 file.
For the Vite dev server to trust the certificate, add this to vite.config.js:
import { defineConfig } from 'vite'; import react from '@vitejs/plugin-react'; export default defineConfig({ plugins: [react()], server: { https: { key: 'path/to/localhost-key.pem', cert: 'path/to/localhost.pem', }, port: 5173, proxy: { '/api': { target: 'https://localhost:8443', changeOrigin: true, secure: false, }, }, }, });Replace the paths with the actual location of your .pem files. The proxy ensures API requests are forwarded to the backend without CORS issues.
In the provided docker-compose.yml, the backend uses the localhost.p12 file mounted from the host. Ensure you have generated the .p12 file and placed it in the expected location (backend/src/main/resources/localhost.p12).
Note: For production, use certificates from a trusted CA like Let’s Encrypt.
The project includes a docker-compose.yml that runs the entire stack (backend, frontend, MongoDB, Redis, Prometheus, Grafana, Loki, Promtail). Make sure you have Docker and Docker Compose installed.
-
Build and start all services
docker-compose up --build
-
Access the application
- Frontend:
https://localhost:5173 - Backend API:
https://localhost:8443 - Grafana:
http://localhost:3000(admin/admin) - Prometheus:
http://localhost:9090 - Loki:
http://localhost:3100
- Frontend:
Note: SSL certificates are self‑signed for development; browsers will show a warning – proceed anyway.
Interactive API documentation is available via Swagger UI when the backend is running:
https://localhost:8443/swagger-ui.html | Category | Endpoint | Description | Roles |
|---|---|---|---|
| Auth | /api/auth/register | Register a new user | Public |
/api/auth/login | Login, receive JWT | Public | |
/api/auth/verify-email | Verify email with OTP | Public | |
| Password | /api/password/forgot | Request password reset OTP | Public |
/api/password/verify-otp | Verify OTP | Public | |
/api/password/reset | Reset password (with OTP) | Public | |
| Payments | /api/payment/create-order | Create Razorpay order | Public |
/api/payment/confirm | Confirm payment (admin token) | Public | |
/api/payment/confirm-provider | Confirm provider token | Public | |
| Places | /api/places | CRUD operations for places | Admin / Public |
| Services | /api/services | CRUD for services | Admin / Public |
| Queues | /api/queues | Manage queues and tokens | Mixed |
| Feedback | /api/feedback | Submit and retrieve feedback | User / Public |
| Search | /api/search | Comprehensive search with filters | Public |
| Admin | /api/admin | Admin dashboard, provider management, reports | Admin |
| Provider | /api/providers | Provider‑specific data and analytics | Provider |
| User | /api/user | Profile, favorites, token history | User |
| Export | /api/export | Export queue reports (PDF/Excel) | Admin/Provider |
| Notifications | /api/notifications/preferences | Manage per‑queue notification settings | User |
| PasswordResetToken | /api/password-reset-token | Admin‑initiated password reset (token) | Admin |
For a complete list, refer to the Swagger UI.
QueueLess uses WebSocket (STOMP over SockJS) to provide live queue updates. The WebSocket endpoint is /ws.
import { Client } from '@stomp/stompjs'; import SockJS from 'sockjs-client'; const client = new Client({ webSocketFactory: () => new SockJS('https://localhost:8443/ws'), connectHeaders: { Authorization: `Bearer ${token}` }, onConnect: () => console.log('Connected'), }); client.activate();Subscribe to /topic/queues/{queueId} to receive updates whenever the queue changes (token added, served, completed, cancelled).
client.subscribe('/topic/queues/' + queueId, (message) => { const queue = JSON.parse(message.body); // update UI });/user/queue/emergency-approved– emergency token approval/rejection./user/queue/token-cancelled– token cancellation notifications./user/queue/provider-updates– (for providers) updates when they serve a token.
/app/queue/serve-next– serve next token (provider only)./app/queue/add-token– add a regular token (user)./app/queue/status– toggle queue active status (provider).
All commands require authentication and appropriate role.
Run unit and integration tests with Maven:
cd backend ./mvnw testThe tests cover services, controllers, and some integration flows. A local MongoDB instance is automatically started/stopped via embedded MongoDB for tests.
Frontend tests are not yet implemented, but the architecture is ready for them using Jest and React Testing Library.
-
Build an executable JAR:
cd backend ./mvnw clean package -DskipTests -
Copy the JAR (
target/backend-0.0.1-SNAPSHOT.jar) to your server. -
Run with Java:
java -jar backend-0.0.1-SNAPSHOT.jar
Use a process manager like
systemdorsupervisorto keep it running.
-
Build the production bundle:
cd frontend npm run build -
Serve the
distfolder with a web server (e.g., Nginx).
For a full stack deployment, use the provided docker-compose.yml on a server with Docker installed. Adjust environment variables in the compose file or in a .env file.
- Ensure MongoDB is running locally or the
MONGODB_URIis correct. - If using embedded MongoDB for tests, it starts automatically.
- Verify Redis is installed and running (
redis-server). - If Redis is not needed, you can disable caching by setting
spring.cache.type=noneinapplication.properties.
- For Gmail, enable 2FA and generate an App Password.
- Check that
MAIL_USERNAMEandMAIL_PASSWORDare correct. - If using a different SMTP provider, adjust
spring.mail.hostand port.
- Ensure Firebase project is configured correctly and
VAPID_KEYis set. - In the browser, check that notifications are allowed for the site.
- Verify that FCM tokens are being stored in the database (user's
fcmTokensarray).
- Make sure the
uploads/directory exists and is writable. - The backend serves static files under
/uploads/**. If you get 404, check thatWebConfigis properly configured.
- Check that the backend is running and the WebSocket endpoint
/wsis accessible. - Ensure the JWT token is valid and passed in the
Authorizationheader. - If using self‑signed certificates, the browser may block the connection. In development, you can temporarily disable SSL verification or use a valid certificate.
- Adjust
rate.limit.*properties inapplication.properties. For example, increasecapacityandrefillfor development.
- The JWT expiration is set to 24 hours by default. If your system clock is skewed, tokens may appear expired. Synchronize time via NTP.
While QueueLess already provides a robust set of features, the following enhancements are planned for upcoming releases:
- Multiple Active Tokens per User: Allow users to join queues in different places simultaneously.
- Per‑Service Multiple Queues: Let users choose from multiple providers offering the same service (e.g., different doctors at the same hospital).
- Emergency Toggle for Providers: Enable/disable emergency support for an existing queue.
- Export Cleanup: Automatic removal of old export files from the cache.
- Admin Audit Log Viewer: Interface for administrators to inspect audit logs.
- Internationalization (i18n): Support for multiple languages.
- Mobile App: React Native or Flutter version for native push notifications and offline support.
- Advanced Analytics: Predictive wait time models using historical data.
We welcome contributions! To ensure a smooth process, please follow these guidelines:
- Fork the repository and create your branch from
main. - Write tests for any new functionality. We aim for high test coverage.
- Ensure all tests pass by running
mvn testin the backend and (if applicable)npm testin the frontend. - Follow coding conventions:
- Backend: Use standard Java naming conventions, include Javadoc for public methods, and format code with your IDE's default settings.
- Frontend: Use ESLint and Prettier (configuration included).
- Commit messages should be clear and follow Conventional Commits (e.g.,
feat: add user profile image upload). - Open a pull request against the
mainbranch. Describe your changes in detail and link any related issues.
- Backend: Run
./mvnw spring-boot:runfor hot reload. - Frontend: Run
npm run devfor Vite dev server with HMR.
Use the GitHub issue tracker to report bugs or suggest features. Include as much detail as possible: steps to reproduce, expected behavior, screenshots, and environment details.
This project is licensed under the Apache License, Version 2.0.
You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0.
Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License.
We as members, contributors, and leaders pledge to make participation in our community a harassment‑free experience for everyone, regardless of age, body size, visible or invisible disability, ethnicity, sex characteristics, gender identity and expression, level of experience, education, socio‑economic status, nationality, personal appearance, race, caste, color, religion, or sexual identity and orientation.
We pledge to act and interact in ways that contribute to an open, welcoming, diverse, inclusive, and healthy community.
Our full Code of Conduct is available in the CODE_OF_CONDUCT.md file. By participating, you are expected to uphold this code.
- Thanks to all contributors and open‑source libraries that made this project possible.
- Special thanks to the Spring Boot and React communities for excellent documentation and tools.



























































































































