React 19 TypeScript FastAPI Python 3.12 PostgreSQL Redis Tailwind CSS Docker

Quoting System

A production-ready, multi-tenant quoting SaaS that streamlines the full quote lifecycle — from creation and line-item configuration to rules-engine pricing, client approval, branded PDF export, and CRM integrations. Built for speed, accuracy, and professional delivery.

The Challenge

Businesses waste significant time generating quotes manually across spreadsheets and disconnected tools — leading to inconsistencies, slow turnaround, and a poor client experience. Tracking quote status, managing revisions, and collecting approvals compounds the operational overhead.

The goal was to build a unified platform that manages the complete quoting workflow — from drafting and line-item configuration to client-facing delivery, digital approval, and branded PDF export — removing friction at every stage while supporting multi-tenancy from day one.

The Solution

Quodate is a full-stack, multi-tenant quoting SaaS. The React 19 + Vite frontend delivers a fast, responsive UI with TanStack React Query for server state and Zustand for local state. The FastAPI backend (Python 3.12, async SQLAlchemy) owns all business logic — quote lifecycle, rules engine, approval routing, and PDF generation via WeasyPrint.

The rules engine supports discount, tax, and pricing adjustment logic with condition/action schemas and a dry-run simulation endpoint — so pricing changes are previewed before going live. Redis powers caching, and the entire platform is containerised with Docker Compose.

Technical Implementation

Frontend Stack

React 19 + TypeScript + Vite. TanStack React Query for data fetching, Zustand for global state, Tailwind CSS + Shadcn/ui for styling, React Hook Form + Zod for validation, and Axios with JWT interceptors.

Backend Stack

FastAPI with Python 3.12 and async SQLAlchemy. PostgreSQL 16 with Alembic migrations, Redis for caching, WeasyPrint for PDF generation, Jinja2 for templates, and pytest for the test suite.

Rules Engine — Dry-Run Simulation

# Condition/action schema — priority-ordered rule stack
class PricingRule(BaseModel):
    condition: RuleCondition  # product_type, qty, segment, date
    action: RuleAction        # discount, tax, adjustment
    priority: int
    active: bool

# Dry-run: preview totals before rules go live
@router.post("/rules/simulate")
async def simulate_rules(payload: SimulateRequest):
    result = await rules_engine.dry_run(
        quote_id=payload.quote_id,
        rules=payload.rules,
    )
    return {"before": result.before, "after": result.after}

Core Features

Quote Lifecycle

Full pipeline: Draft → Review → Approved → Accepted / Rejected / Expired with revision lineage and snapshot pricing.

Rules Engine

Self-serve discount, tax, and pricing rules with condition/action schema, priority stacks, and dry-run simulation.

PDF & Templates

10 built-in branded layouts (Clean, Corporate, Bold, Minimal…) with per-tenant customisation and one-click preview.

Approvals & Audit

Configurable approval routing, persistent event timeline, and full async audit log across every mutation.

Product Catalog

Supply, Services, and Goods types with template-driven attribute schemas and validation on every quote line item.

Multi-Tenant Platform

Full data isolation per tenant, onboarding flow, role management, global search, and live pipeline dashboard.