# V1.2.0 Media Upload - Final Design Summary ## Design Status: COMPLETE ✓ This document summarizes the finalized design for v1.2.0 media upload feature based on user requirements and architectural decisions. ## User Requirements (Confirmed) 1. **Image limit**: 4 images per note 2. **Reordering**: Not needed (display order = upload order) 3. **Image optimization**: Yes, automatic resize for large images 4. **Captions**: Yes, optional caption field for each image ## Architectural Decisions ### ADR-057: Media Attachment Model - Social media style attachments (not inline markdown) - Media displays at TOP of notes - Text content appears BELOW media - Junction table for flexible associations ### ADR-058: Image Optimization Strategy - **Max file size**: 10MB per image - **Max dimensions**: 4096x4096 pixels - **Auto-resize**: Images >2048px resized automatically - **Processing library**: Pillow - **Formats**: JPEG, PNG, GIF, WebP only ## Technical Specifications ### Image Processing - **Validation**: Size, dimensions, format, integrity - **Optimization**: Resize to 2048px max, EXIF correction - **Quality**: 95% JPEG quality (high quality) - **Storage**: data/media/YYYY/MM/ structure ### Database Schema ```sql -- Media table with dimensions CREATE TABLE media ( id INTEGER PRIMARY KEY, filename TEXT NOT NULL, original_name TEXT NOT NULL, path TEXT NOT NULL UNIQUE, mime_type TEXT NOT NULL, size INTEGER NOT NULL, width INTEGER, height INTEGER, uploaded_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP ); -- Junction table with captions CREATE TABLE note_media ( id INTEGER PRIMARY KEY, note_id INTEGER NOT NULL, media_id INTEGER NOT NULL, display_order INTEGER NOT NULL DEFAULT 0, caption TEXT, -- For accessibility created_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP, FOREIGN KEY (note_id) REFERENCES notes(id) ON DELETE CASCADE, FOREIGN KEY (media_id) REFERENCES media(id) ON DELETE CASCADE, UNIQUE(note_id, media_id) ); ``` ### User Interface - Multiple file input (accept images only) - Caption field for each uploaded image - Preview thumbnails during upload - Remove button per image - No drag-and-drop reordering - Maximum 4 images enforced ### Display Layout - 1 image: Full width - 2 images: Side by side (50% each) - 3 images: Grid layout - 4 images: 2x2 grid ### Syndication Support - **RSS**: HTML with images in description - **ATOM**: Both enclosures and HTML content - **JSON Feed**: Native attachments array - **Microformats2**: Multiple u-photo properties ## Implementation Guidance ### Dependencies - **Pillow**: For image processing and optimization ### Processing Pipeline 1. Check file size (<10MB) 2. Validate MIME type 3. Load with Pillow (validates integrity) 4. Check dimensions (<4096px) 5. Correct EXIF orientation 6. Resize if needed (>2048px) 7. Save optimized version 8. Store metadata in database ### Error Handling Clear user-facing messages for: - File too large - Invalid format - Dimensions too large - Corrupted file - Maximum images reached ## Acceptance Criteria - ✓ 4 image maximum per note - ✓ No reordering interface - ✓ Automatic optimization for large images - ✓ Caption support for accessibility - ✓ JPEG, PNG, GIF, WebP support - ✓ 10MB file size limit - ✓ 4096x4096 dimension limit - ✓ Auto-resize at 2048px - ✓ EXIF orientation correction - ✓ Display order = upload order ## Related Documents - `/docs/decisions/ADR-057-media-attachment-model.md` - `/docs/decisions/ADR-058-image-optimization-strategy.md` - `/docs/design/v1.2.0/feature-specification.md` - `/docs/design/v1.2.0/media-implementation-guide.md` ## Design Sign-off The v1.2.0 media upload feature design is now complete and ready for implementation. All user requirements have been addressed, technical decisions documented, and implementation guidance provided. ### Key Highlights - **Simple and elegant**: Automatic optimization, no complex UI - **Accessible**: Caption support for all images - **Standards-compliant**: Full syndication feed support - **Performant**: Optimized images, reasonable limits - **Secure**: Multiple validation layers, Pillow verification ## Next Steps 1. Implement database migrations 2. Create MediaProcessor class with Pillow 3. Add upload endpoint to admin routes 4. Update note creation/edit forms 5. Implement media display in templates 6. Update feed generators for media 7. Write comprehensive tests