Hotel management.

Hotel Management is an internal system that takes a hotel's operations from reservation to checkout without anything falling through the cracks. Front desk staff handle walk-in and online bookings, check guests in and out, log services as they're requested, and generate invoices automatically at the end of each stay. Every role in the hotel — receptionist, cashier, manager — sees and interacts with only what their position requires. Every data change carries a full audit trail with before and after states, so nothing goes unrecorded.

Year2025 — 2026
RoleSolo · fullstack (BE + FE)
Timeline8 weeks (MVP)
Status● Live · in production

01.Overview

The big picture

Hotel-management came out of a very real problem: a 30-room hotel running on Excel and Zalo to take reservations, log check-in / check-out times, tally up ancillary services, and write invoices by hand. Every room change or extra service call meant the receptionist had to remember it, jot it down, then re-enter it into the accounting file at the end of the shift — mistakes weren't the exception, they were routine.

I built hotel-management to wrap the entire lifecycle of a stay into a single flow: from reservation and check-in, through adding services (spa, food and beverage, laundry, transfers), to checkout and invoice generation — nothing entered twice. Granular RBAC ensures front desk staff can't touch the accounting module, and a full audit log records every action with enough detail to trace back anything when needed. This project currently running internally at 1 hotel with ~12 daily users

02.Features

What it does
  • 01
    Bookings & lifecycleWalk-in & online · PENDING → CHECKED_OUT

    The system accepts reservations through two channels: walk-in at the front desk or from an online source, storing full guest details — name, phone number, national ID — along with the number of adults, children, and any notes. Each booking moves through the lifecycle PENDING → CONFIRMED → CHECKED_IN → CHECKED_OUT; cancellations transition to CANCELLED with a cancellation fee recorded and factored into the final invoice.

  • 02
    Realtime room mapStatus by floor · hourly or daily

    Each room carries one of four states: AVAILABLE / OCCUPIED / MAINTENANCE / CLEANING, grouped by floor and room type so front desk staff can see the full picture at a glance. The system supports both rental modes — hourly or nightly — and automatically calculates the charge based on the room type's base rate multiplied by the actual duration of the stay, no manual entry needed.

  • 03
    Add-on servicesPer-booking service lines

    Throughout the stay, front desk staff can attach additional services to a booking at any time: spa, food and beverage, laundry, transfers. Each service is recorded as a separate booking_services row, with quantity and unit price locked in at the moment it's added. If the price list changes afterwards, existing rows are unaffected — past invoices always reflect the exact rate at the time the service was incurred.

  • 04
    Auto invoicesGenerated on check-out · PDF / Excel

    At checkout, the system automatically builds an invoice from all booking data: room charges + total services + tax − discount. The invoice is snapshotted at the moment it's generated — any subsequent changes to room rates or the service price list have no effect on invoices already issued. Front desk staff can print directly at the counter or export to PDF / Excel; both go through a Bull queue so the main flow isn't blocked when multiple invoices are generated simultaneously.

  • 05
    RBAC + audit logPer-action permissions · before/after diff

    Permissions are controlled down to individual actions: front desk staff only see the rooms and bookings module, while accounting staff are the only ones who can access invoices and reports. Each permission group is scoped by action — create, edit, cancel, refund — not by broad screen access. Every data-mutating operation passes through AuditInterceptor, automatically saving the before and after state into audit_logs — enough to trace who did what, when, and what the data looked like before the change.

03.Tech stack

Tools used
FrontendNext.js 16 · React 19 · TypeScript · Redux Toolkit · Tailwind 4 · react-hook-form · zod · sonner
BackendNestJS 11 · TypeScript · TypeORM · Passport JWT · class-validator · Socket.IO · Bull
DatabaseMySQL 8 (rooms, bookings, booking_services, invoices, audit_logs JSON) · Redis 7 (cache, queues, socket adapter)
InfraDocker · GitHub Actions · Caddy reverse proxy · VPS (4GB)
ObservabilityIn-DB audit logs · Pino · request id middleware
TestingJest unit (booking lifecycle + RBAC guards) · Supertest e2e (booking → invoice flow) · ~62% coverage

04.How it works

Architecture

The core of hotel-management is the booking lifecycle. Each booking holds a reference to exactly one room and can carry multiple booking_services. When a booking is created, the service checks room availability using a transaction + row lock on the rooms table — preventing double-booking even when two receptionists act on the same room simultaneously. Room state syncs automatically with the booking: CHECKED_IN pushes the room to OCCUPIED, CHECKED_OUT pushes it to CLEANING.

At checkout, a single transaction handles everything: (1) move the booking to CHECKED_OUT, (2) calculate room charges based on actual duration multiplied by the room type rate, (3) sum up booking_services using unit prices snapshotted at the time each service was added, (4) create the invoices record, (5) move the room to CLEANING. Every step is accompanied by a before/after audit record. End-to-end latency from checkout to printed invoice measured on prod: ~180ms.

Design decision

"Hotel-management currently handles the full operational flow well — reservations, check-in, services, invoicing. Two directions are being developed next: a more complete guest profile with national ID photos attached at check-in — currently the ID number is stored as text only with no image, while in practice many hotels are required to keep document copies when inspections occur. The second direction is webhook integration to receive bookings directly from external platforms — Booking.com, Airbnb, or any OTA — eliminating the need for receptionists to manually re-enter reservations from multiple channels."

05.Comments

Leave a few words

No comments yet.

Xem tiep
mysql-manager-mobile preview
M
MySQL Manager

A Flutter-based MySQL admin client — saved connections, browse databases → tables → rows, primary-key-safe CRUD, plus a free-form SQL shell; runs on Android, iOS, macOS, Linux and Windows from a single Dart codebase.

python-ocr preview
O
Captcha OCR

CaptchaOCR is a FastAPI micro-service that accepts a 4-digit captcha image in base64 and returns the corresponding integer. The ddddocr pretrained model is loaded once at process startup — every subsequent request is pure inference, with latency in the range of a few tens of milliseconds per image. The service is deployed via PM2 with auto-restart and a hard RAM cap, keeping it stable over long periods without manual oversight.

chatgpt-auto-login preview
G
GPT Login

A NestJS API that auto-logs into ChatGPT via puppeteer-real-browser (Cloudflare anti-bot bypass), supports email OTP, persists the session for route /ask reuse and directly promt promt, and runs an hourly cron that pings Telegram when the session expires. This allows me to send prompts and receive responses directly through the API without needing to open a browser.

zoom-bot preview
Z
Zoom Bot

ZoomBot is a pool of Chrome bots that automatically join Zoom meetings and wait for remote commands via HTTP API. Each bot runs on its own isolated Chrome instance with its own lock, fully thread-safe — bots don't interfere with each other even when running in parallel. A single API call can instruct any bot to send a chat message, toggle the mic, toggle video, leave the room, or rejoin. When a bot crashes, the system detects it automatically and restarts without any manual intervention. The entire stack is written in Python, Selenium, and Flask — lean enough to run on a standard server without complex infrastructure.