Wedding Face Forward Project Banner

💍 Wedding Face Forward (WeddingFF)

AI-Powered Event Photography Management & Instant Guest Photo Delivery System

February 11, 2026

Ranjith Kumar

Computer and AI enthusiast

Project Vision & Philosophy

Wedding Face Forward (WeddingFF) represents a paradigm shift in event photography. Traditionally, wedding guests have to wait for weeks to see photos of themselves, often digging through thousands of images in a shared link. By the time they receive the photos, the emotional peak of the event has passed.

WeddingFF was conceived with a single realization: The value of a memory is highest at the moment of capture.

Core Philosophies

  • Instant Gratification: Photos should reach guests while they are still at the venue or traveling home.
  • Effortless Discovery: No searching, no tagging. The AI knows you.
  • Private-by-Default: You only get your photos, preserving the intimacy of the couple's big day.
  • Professional Grade: Delivering raw-quality images via automated, low-friction channels.

Executive Summary

WeddingFF is a multi-process Python application that provides comprehensive event photography management with AI-powered face recognition and automated delivery.

Zero-Manual-Effort Ingestion

Watches folders for new files from cameras (DSLR via Wi-Fi/SD or Phone).

Pro Format Support

Built-in RAW processing for high-end camera bodies (CR2, NEF, ARW).

Biometric Identity Discovery

Automatically clusters people into identities without prior input.

Selfie-to-Gallery Matching

Guests "log in" using their faces with advanced AI matching.

Cloud Mirroring

Transparently syncs photos to a private, organized Google Drive structure.

WhatsApp Push

Delivers personalized gallery links automatically using browser-level automation.

Visual Mission Control

A beautiful desktop dashboard for monitoring real-time health.

Privacy-First Design

Local-first processing with GDPR-compliant biometric handling.

System Architecture

WeddingFF employs a sophisticated three-plane architectural model that separates concerns and ensures scalability and reliability.

The Three-Plane Model

Resides in WeddingFFapp.py. Responsible for launching and monitoring sub-processes. Provides visual feedback of the "Heartbeat" of each system module.

  • Process supervision and multi-subprocess control
  • Real-time statistics and predictive analytics
  • Color-coded activity logging and diagnostic feeds
  • Built with CustomTkinter for modern UI components

Resides in backend/app/worker.py and its dependencies. Handles the "Heavy Lifting": Image conversion, AI analysis, and Routing.

  • RAW image processing and normalization
  • Face detection using RetinaFace
  • 512-dimensional embedding generation
  • Incremental centroid clustering for identity discovery
  • Intelligent photo routing to person-specific folders

Resides in backend/app/cloud.py and whatsapp_tool/db_whatsapp_sender.py. Manages external integrations (Google Drive & WhatsApp).

  • Google Drive API integration with OAuth2
  • Resumable uploads and bandwidth negotiation
  • Automated permission setting and link generation
  • WhatsApp automation via Playwright
  • Anti-ban safety protocols and rate limiting

Data Flow & Event Lifecycle

Every photo follows a well-defined journey through the system:

  1. Photo begins as an Event in the Incoming/ directory
  2. The Watcher detects the file and adds it to the Job Queue
  3. A Worker processes the image, generating a Normalized JPEG and Thumbnail
  4. The AI Analyzer extracts Embeddings
  5. The Clusterer assigns the photo to one or more Person IDs
  6. The Router copies the file to the appropriate People/Person_XXX directories
  7. The Upload Queue picks up these new files and mirrors them to Google Drive
  8. Upon Guest Enrollment, the WhatsApp Sender is triggered to send the link

The AI Core

At the heart of WeddingFF lies a sophisticated AI engine powered by state-of-the-art computer vision models.

InsightFace Buffalo_L Model

WeddingFF utilizes the Buffalo_L model package from InsightFace. This model is built using the ResNet100 architecture and is trained on the Large-scale Face Recognition (MS1M-ArcFace) dataset.

RetinaFace Detection Logic

Unlike simple Haar-cascade filters, RetinaFace uses a single-pass, multi-scale face localization method. It predicts:

  • Face Bounding Boxes: (x, y, w, h) coordinates
  • Five Facial Landmarks: Eyes, Nose, Mouth Corners
  • Face Scores: Detection Confidence

RetinaFace is particularly effective at "Small Face Detection," which is critical for wedding group photos where people might be far from the camera.

512-Dimensional Embeddings

The "Embedding" is a mathematical abstraction of a human face:

  • Input: A cropped and aligned 112x112 face image
  • Output: A 512-element array of floating-point numbers
  • Property: The distance between two vectors directly correlates to the biological similarity of the two faces

Incremental Centroid Clustering

WeddingFF uses Cosine Distance to compare faces. Unlike Euclidean distance, Cosine Distance ignores the "magnitude" (brightness/contrast) of the embedding and focuses only on the "angle" (features).

  • Distance 0.0: Identical faces
  • Distance 2.0: Completely opposite features
  • WeddingFF Match Threshold: Typically 0.45 - 0.60

As more photos of "Person A" are taken, the Centroid (the average of all their embeddings) "drifts" to better represent their true appearance. This self-correcting mechanism is what makes WeddingFF so accurate at scale.

The Data Layer

WeddingFF uses SQLite with Write-Ahead Logging (WAL) mode for robust, concurrent data management.

Database Schema

  • photos: The master registry. Fields include file_hash, status, face_count, and processed_path.
  • faces: Detail table linked to Photos. Each entry stores a pickled numpy array of the embedding.
  • persons: The identity table. Stores the Centroid and the current Face_Count.
  • enrollments: The Bridge between AI and Humans. Stores User_Name, Phone, Enrollment Selfie Path.
  • upload_queue: A persistent task list for the cloud syncer.

Concurrency Management

SQLite is traditionally single-threaded for writes. WeddingFF circumvents this using:

  • WAL (Write Ahead Logging): Allows reading while writing is in progress
  • PRAGMA busy_timeout: Set to 30,000ms to allow threads to wait for each other politely
  • @retry_on_lock Decorator: Implements randomized exponential backoff for locked database operations

Transactional Integrity

We use with conn: blocks to ensure that if a photo is successfully routed to the disk but the database update fails, the routing is "rolled back" (or the photo is re-processed) to prevent orphans.

Image Processing & RAW Workflow

Professional RAW Support

Using the rawpy library, WeddingFF accesses the "Bayer" data directly from the sensor-dump files. This allows the system to generate high-fidelity JPEGs that often look better than standard in-camera previews.

Supported Formats: CR2 (Canon), NEF (Nikon), ARW (Sony)

Normalization & Color Grading

Every image goes through a sanitation process:

  • Orientation Fix: Auto-rotated based on camera tilt sensors
  • Color Space: Converted to sRGB for consistent web display
  • Quality: Saved at 95% JPEG quality to preserve professional sharpness

Multi-Resolution Image Diversification

The system generates:

  • Full-Res (e.g. 2048px): For the guest's cloud gallery
  • Thumbnail (300px): Square crop for the Guest Portal and Admin App
  • AI-Input (640px): Specifically for the RetinaFace detection engine

Intelligent Routing & Organization

Logical Hierarchy of EventRoot

EventRoot/
  Incoming/   ← The Drop Zone
  Processed/  ← Master Normalized JPEGs
  People/     ← The Identity Mirror
    Person_A/
      Solo/   ← Just them
      Group/  ← With friends

Routing Logic (Solo vs. Group Contexts)

The system employs high-precision routing logic:

  • Exactly 1 Person: File is copied to Solo/ with a unique ID-based name (e.g., 000452.jpg)
  • 2+ Persons: File is copied to the Group/ folder of every detected person. This "Virtual Shadowing" ensures everyone sees shared moments without manual tagging
  • Hardlinks: On Windows/NTFS, the system uses os.link() to create multiple references to the same file. This means 10 copies of a group photo take 0 extra disk space

Content-Based Hashing (SHA-256)

We calculate a unique hash for every photo. If you accidentally put the same SD card in twice, the system skips those photos in milliseconds, recognizing the content hash already exists in the database.

Cloud Synchronization

OAuth2 & Service Account Authentication

WeddingFF supports both User-level OAuth (using token.json) and Service Accounts. User-level is recommended for uploading directly into the photographer's primary Google Drive account.

Mirroring Local Hierarchies to Cloud

The ensure_folder_path function recursively checks for the existence of folders in Drive (e.g. "People" → "Person_A" → "Solo"). If they don't exist, it creates them and caches the IDs to avoid redundant API calls.

Resumable Uploads

Large photo sets can saturate a venue's Wi-Fi. We use Resumable Media Uploads, allowing the system to pause and resume individual file transfers without starting over.

Automated Permission Setting

Whenever a new Person folder is created, the system calls permissions.create to make it "Anyone with link" readable. It then stores the resulting webViewLink.

Personalized Delivery

Playwright Integration

We use Playwright to drive a real browser. This is essential because standard API-based automation is often detected as "Bot behavior" by WhatsApp.

Session Persistence

Authentication data is saved in whatsapp_tool/whatsapp_user_data. This means the operator only needs to scan the QR code once per event (or even per wedding season).

Human-Simulation Delivery Logic

The system doesn't just "click send." It:

  1. Navigates to the chat
  2. Waits for the "Type a message" box to become interactive
  3. Pastes the message
  4. Simulates an "Enter" keypress
  5. Waits for the "Sent" checkmark before moving to the next guest

Anti-Ban Safety Protocols

To prevent account bans:

  • Never send more than 1 message per 10 seconds
  • Implement "Batch Pausing": after every 20 messages, the system rests for 2 minutes
  • Maintain a message_state_db.json to ensure no guest ever gets a duplicate message
  • Use randomized delays: random.uniform(8.0, 15.0) to mimic human behavior

Frontend

FastAPI Backend

The web server is built on FastAPI, the fastest modern Python web framework. All guest inputs (names, phones) are strictly validated using Pydantic models.

Selfie Matching Engine

When a guest uploads a selfie, the server extracts the embedding and compares it to the persons table. It returns a Confidence Score. If the confidence is > 50%, the guest is automatically linked to that cluster.

Design Language: Glassmorphism

The UI features "Frosty" glass effects, rose gold accents, and smooth CSS-grid-based gallery layouts. It feels like a premium app, not a simple upload form.

QR-Based Entry & Enrollment Flow

The photographer places QR codes on tables. Guests scan them, land on their private URL, and the system guides them through the 30-second enrollment process.

WeddingFFApp Dashboard

UI Component Architecture

The dashboard uses customtkinter, a modern extension for Tkinter that allows rounded corners, smooth hover effects, and full theme support.

Real-Time Statistics

The app shows:

  • Queue Depth: How many photos are waiting to be processed
  • Face Velocity: How many faces per minute the AI is currently discovering
  • Sync Health: Success/Failure ratio of cloud uploads

Process Supervision

The dashboard doesn't just "import" the workers; it runs them as separate Subprocesses. This ensures that if the AI worker crashes due to a corrupt file, the GUI remains responsive, allowing the operator to restart it with one click.

Color-Coded Activity Logging

  • Cyan: AI and Worker activity
  • Yellow: Database and file system events
  • Green: Successful WhatsApp deliveries
  • Red: Errors or failed uploads

Technology Stack

  • Core Language: Python 3.9+
    • Multi-threading and multi-processing capabilities
    • Rich ecosystem of libraries for AI and automation
  • AI & Computer Vision:
    • insightface - Face detection and recognition (Buffalo_L model)
    • onnxruntime - Neural network execution engine
    • opencv-python - Image processing operations
    • numpy - Numerical computations for embeddings
  • Image Processing:
    • rawpy - RAW image format support (CR2, NEF, ARW)
    • Pillow - Image manipulation and conversion
  • Database:
    • sqlite3 - Local database with WAL mode
    • Custom @retry_on_lock decorator for concurrency
  • Web Framework:
    • FastAPI - Modern, fast web framework
    • Pydantic - Data validation
    • uvicorn - ASGI server
  • Cloud Integration:
    • google-api-python-client - Google Drive API
    • google-auth - OAuth2 authentication
  • Automation:
    • playwright - Browser automation for WhatsApp
    • watchdog - File system event monitoring
  • Desktop UI:
    • customtkinter - Modern Tkinter UI components
    • Dark/Light theme support

Setup & Configuration

Dependency Management

WeddingFF depends on complex binary libraries. A specific requirements.txt ensures version compatibility:

pip install -r requirements.txt

Environment Configuration (.env Variables)

  • EVENT_ROOT: Absolute path to photos
  • DB_PATH: Where to store the SQLite file
  • WORKER_COUNT: Number of parallel workers (match to CPU threads)
  • CLUSTER_THRESHOLD: Face matching threshold (0.45-0.65)
  • DRIVE_ROOT_FOLDER_ID: Google Drive root folder ID
  • SCAN_INTERVAL: How often to check for new files (in seconds)
  • DRY_RUN: If "true", simulates the pipeline without moving files

Google Cloud Setup

  1. Visit the Google Cloud Console (console.cloud.google.com)
  2. Create a New Project: Name it "WeddingFF-Sync"
  3. Enable APIs: Search for "Google Drive API" and click Enable
  4. Configure OAuth Consent Screen (External)
  5. Create Credentials → OAuth Client ID → Desktop App
  6. Download the JSON and rename it to credentials.json
  7. Place the file in the project root
  8. Run python backend/setup_auth.py to generate token.json

Performance & Reliability

Performance Benchmarks

  • Memory: The system typically consumes 600MB - 1GB of RAM depending on the number of workers
  • CPU: Under full load (8 workers), it can peak to 90-100% CPU usage for short bursts during face detection
  • Scalability: The SQLite index architecture supports up to 500,000 face entries before any perceivable slowdown

Failure Mode Analysis

  • Losing Internet: The system queues everything. Once internet returns, it "burst uploads" to catch up
  • Power Loss: The SQLite database is atomic. No half-finished records will exist. The system resumes exactly where it left off
  • Database Locks: Solved using WAL mode and the custom @retry_on_lock decorator

Hardware Optimization

To run WeddingFF at peak performance:

  • CPU: Intel Core i7-12th Gen or AMD Ryzen 7 (8+ Cores)
  • RAM: 16GB Minimum (32GB for handling 8K RAW processing)
  • Storage: NVMe SSD (Very high IO throughput is needed for photo routing)
  • OS: Windows 11 or Ubuntu Desktop 22.04

Privacy, Security & GDPR Compliance

Secure Handling of Biometric Data

WeddingFF is designed to minimize the footprint of biometric data. Embeddings are anonymous mathematical vectors. There is no facial "image" stored in the database; only coordinates and numbers.

Local-First Storage

By keeping the AI on the local laptop, we ensure that guests' facial measurements never touch the public internet. Only the final, finished photos are uploaded to Google's encrypted servers.

The system records the exact timestamp and IP address when a guest checks the "I consent to my face being matched" box, creating a legal audit trail for the photographer's protection.

The "Double-Hashing" Security Model

  • Local Hashing: The actual image Content Hash (SHA-256) is only stored locally in your SQLite DB
  • Biometric Hashing: Face embeddings are randomized mathematical models. Even if the database were stolen, it is impossible to reconstruct a person's face from the 512 numbers
  • Link Obfuscation: Guest gallery links in Google Drive use a long-form randomized alphanumeric ID

Troubleshooting & Maintenance

Common Errors (Resolved)

  • DATABASE_IS_LOCKED: Solved using WAL mode and the custom @retry_on_lock decorator in backend/app/db.py
  • PERMISSION_DENIED: Usually happens when the app tries to move files already open in another program (like Lightroom)
  • PORT_8000_BUSY: A common issue solved by the cleanup_ports.bat script which kills orphaned Python processes

Maintenance Utilities

  • check_all.py - Runs a full integrity check on the DB, Filesystem, and Cloud folders
  • clear_photos.py - (DANGER) Resets the entire event root. Use only when starting a brand new wedding
  • check_hashes.py - Verifies that every file in the People/ folder matches its hash in the database
  • cleanup_ports.bat - A Windows utility to free up Port 8000 and Port 3000

Operation Checklists

Pre-Event:

  • Clear Incoming/, Processed/, and People/ folders
  • Reset data/wedding.db (or create a new one for the new event)
  • Verify .env paths are correct for the current laptop drive
  • Run python WeddingFFapp.py and verify all subsystems show "Stopped"
  • Perform a "Test Enrollment" with your own face to verify Cloud/WhatsApp

During-Event:

  • Monitor the "Queue Depth" on the dashboard
  • Ensure the laptop doesn't go to sleep (Disable Power Save)
  • Encourage guests to scan the QR codes early for "Real-time" delivery
  • Check the "Errors" folder periodically for corrupt files

Post-Event:

  • Run reupload_cloud.py to ensure 100% of files were synced
  • Backup the wedding.db and EventRoot to an external archival drive
  • Generate the "Sync Summary" for the client

Strategic Roadmap & Vision 2026

The future of WeddingFF includes:

  • Phase 3 (Summer 2026): Video face-detection support
  • Phase 4 (Winter 2026): Multi-camera synchronization over local LAN
  • Phase 5 (2027): Direct integration with Mirrorless camera FTP protocols
  • Experimental Features: Multi-system cluster merging for massive events (10,000+ photos)

Final Word

"To build the world's most seamless bridge between the camera's shutter and the attendee's heart, powered by invisible, intelligent automation."

This project is a labor of love, designed to empower event photographers to provide a level of service that was previously impossible without a team of 10 assistants.

Thank you for being part of the Wedding Face Forward journey.

Repository & Resources