Deploying QuickDumpNow's Multi-Stage Dispatch System: CloudFront Rewrites, S3 Job State, and Real-Time Tracking

This post details the production deployment of QuickDumpNow's dispatch tool—a system that required coordinating CloudFront function rewrites, Lambda-backed job state management, and multi-environment promotion strategies. We'll walk through the exact infrastructure changes, explain the architectural decisions, and cover the operational patterns that made safe, reliable deployment possible.

What We Deployed

QuickDumpNow needed two critical updates delivered to production:

  • A CloudFront function rewrite for both /track/ and /book/ paths to properly route traffic to the correct S3-backed pages
  • A new job record for Mark (Soderblom Ave pickup, $600 all-in) with tracking token generation and real-time status flow
  • Status flow updates to the tracking and dashboard pages to reflect accurate job state transitions

The issue that prompted this work: Mark's tracking link returned "Job not found, or this tracking link is no longer valid" despite the job existing in S3. This pointed to a CloudFront routing problem rather than a data problem.

Infrastructure Architecture

QuickDumpNow uses a multi-layered approach across AWS services:

  • CloudFront Distribution (quickdumpnow.com): Caches static pages, runs edge functions, routes requests
  • S3 Buckets: Stores job JSON state and HTML pages (staging and production versions)
  • CloudFront Functions (viewer request): Rewrites URLs at edge before hitting origin, zero added latency
  • DynamoDB (backend): Stores crew roster, event assignments, and first mate claims
  • Lambda (API endpoints): Handles job creation, status updates, SMS/email confirmations
  • SES (email): Sends crew confirmations with verified identities

The key insight: by running the URL rewrite at CloudFront's edge (not in Lambda), we avoid cold starts and ensure every request gets fast routing.

The CloudFront Function Rewrite Problem

The existing CloudFront function at /Users/cb/Documents/repos/sites/quickdumpnow.com/cf/qdn-track-rewrite.js only handled /track/ requests. When customers visited /book/, the rewrite didn't fire, causing routing failures.

We updated the function to handle both paths:

// Rewrite /track/{token} to /track.html with token preserved
// Rewrite /book/{step} to /book.html with step preserved
// Pass token/step as query parameters for JavaScript to parse

Why CloudFront Functions instead of Lambda@Edge? Functions are:

  • Synchronous and sub-millisecond (no cold start penalty)
  • Limited to 10KB, forcing simple logic (good constraint)
  • Charged per-million requests (cheaper than Lambda)
  • Deployed to 250+ global edge locations instantly

Job State Management in S3

Mark's job needed to be created with:

  • Unique job ID: Generated from timestamp + random bytes
  • Tracking token: Cryptographically random for URL-safe tracking links
  • Initial status: ready_for_pickup (Mark texted he'd be ready this afternoon)
  • Location: Soderblom Ave
  • Price: $600 all-in

The jobs are stored in S3 at a predictable path (not disclosed here for security), with this structure:

{
  "jobs": {
    "{jobId}": {
      "id": "{jobId}",
      "token": "{trackingToken}",
      "status": "ready_for_pickup",
      "location": "Soderblom Ave",
      "price": 600,
      "createdAt": "2024-05-23T...",
      "statusHistory": [...]
    }
  }
}

We fetched the current jobs.json from S3, merged Mark's record, and re-uploaded atomically. This avoids race conditions better than individual PUT operations.

Multi-Environment Promotion Strategy

Changes moved through three stages:

  1. Staging: Updated files uploaded to S3 staging prefix
  2. Testing: Human verification that track page parsed token correctly, dashboard displayed status pills, API endpoints returned valid responses
  3. Production: Promoted staging files to prod prefix
  4. Cache Invalidation: Cleared CloudFront distributions to force fresh content

The workflow protected us in two ways:

  • Staging S3 prefix is invisible to customers; we could iterate without breaking live service
  • CloudFront cache invalidation patterns ensure edge nodes serve fresh content within seconds

We invalidated two distributions:

  • quickdumpnow.com dashboard and customer track pages: /track/*, /book/*, /index.html
  • API domain (separate distribution for API Gateway): specific endpoint paths

Status Flow and Real-Time Updates

The tracking page and dashboard both needed updates to reflect accurate job state:

  • Track page (track.html): Fetches job via token, displays current status, shows location and next action
  • Dashboard (dashboard.html): Lists all jobs, shows kanban columns for each status, allows crew to update status

We patched both with:

// STATUS_FLOW definition: which statuses can transition to which
// statusLabel() function: human-readable status text
// statusColor() function: color coding (green = ready, yellow = in_progress, blue = completed)
// nextStatusLabel() function: shows crew what status comes next

The dashboard kanban board uses CSS classes to position jobs dynamically:

.status-column.ready_for_pickup { /* column 1 */ }
.status-column.in_progress { /* column 2 */ }
.status-column.completed { /* column 3 */ }

This lets crew drag cards between columns, with JavaScript updating the job status in S3 when dropped.

Verification and Fallback Steps

After pushing to production, we verified:

  • Hit the track API endpoint directly with Mark's token; confirmed job returned with correct status
  • Pulled the production track page; verified it parsed the token from URL and fetched job correctly
  • Pulled the production dashboard; verified status pills rendered with correct colors and transitions
  • Updated Mark's job status to ready_for_pickup and confirmed it persisted in S3

If any step failed, we could revert by re-promoting the previous staging version and re-invalidating CloudFront.

Operational Patterns and Lessons