- Move padding from .insertr-button-frame to .insertr-style-btn.insertr-style-preview
- Add align-items and justify-content to button container for proper centering
- Remove width: 100% from button frame to prevent unnecessary stretching
- Fix off-center text in default Bold, Italic, and Link buttons
- Maintain style isolation while ensuring consistent button alignment
- Add margin/padding reset to .insertr-style-sample to prevent browser defaults
- Remove unused .insertr-default-preview CSS that was causing confusion
- Ensure consistent spacing across all button types (default vs detected styles)
- Clean up legacy CSS classes that are no longer used with three-layer architecture
- Add button frame isolation layer to prevent site CSS from affecting toolbar appearance
- Create style sample container for authentic style previews without layout interference
- Update CSS with proper containment boundaries and !important rules for button structure
- Preserve all authentic styling (color, weight, transform, decoration) in isolated preview
- Fix inconsistent button appearance across different site stylesheets (e.g. .brand class)
- Maintain professional toolbar UX while showing accurate style previews
Major architectural simplification removing content type complexity:
Database Schema:
- Remove 'type' field from content and content_versions tables
- Simplify to pure HTML storage with html_content + original_template
- Regenerate all sqlc models for SQLite and PostgreSQL
API Simplification:
- Remove content type routing and validation
- Eliminate type-specific handlers (text/markdown/structured)
- Unified HTML-first approach for all content operations
- Simplify CreateContent and UpdateContent to HTML-only
Backend Enhancements:
- Update enhancer to only generate data-content-id (no data-content-type)
- Improve container expansion utilities with comprehensive block/inline rules
- Add Phase 3 preparation with boundary-respecting traversal logic
- Strengthen element classification for viable children detection
Documentation:
- Update TODO.md to reflect Phase 1-3 completion status
- Add WORKING_ON.md documenting the architectural transformation
- Mark container expansion and HTML-first architecture as complete
This completes the transition to a unified HTML-first content management system
with automatic style detection and element-based behavior, eliminating the
complex multi-type system in favor of semantic HTML-driven editing.
- Add backend container transformation in engine.go following syntactic sugar specification
- Containers with .insertr get class removed and viable children get .insertr added
- Remove incorrect frontend container expansion - frontend only finds enhanced elements
- Fix StyleAwareEditor hasMultiPropertyElements runtime error
- Add addClass/removeClass methods to ContentEngine for class manipulation
- Update frontend to match HTML-first approach with no runtime container logic
- Test verified: container <section class='insertr'> transforms to individual h1.insertr, p.insertr, button.insertr
This completes the container expansion functionality per CLASSES.md:
Developer convenience (one .insertr enables section editing) + granular control (individual element editing)
- Replace value field with html_content for direct HTML storage
- Add original_template field for style detection preservation
- Remove all markdown processing from injector (delete markdown.go)
- Fix critical content extraction/injection bugs in engine
- Add missing UpdateContent PUT handler for content persistence
- Fix API client field names and add updateContent() method
- Resolve content type validation (only allow text/link types)
- Add UUID-based ID generation to prevent collisions
- Complete first-pass processing workflow for unprocessed elements
- Verify end-to-end: Enhancement → Database → API → Editor → Persistence
All 37 files updated for HTML-first content management system.
Phase 3a implementation complete and production ready.
## Library Code Cleanup (~1,200+ lines removed)
- Remove legacy markdown system (markdown.js, previewer.js)
- Delete unused EditContext code from ui/editor.js (~400 lines)
- Remove version history UI components from form-renderer.js (~180 lines)
- Clean unused CSS styles from insertr.css (~120 lines)
- Update package.json dependencies (remove marked, turndown)
## Documentation Updates
- README.md: Update from markdown to HTML-first approach
- AGENTS.md: Add current architecture guidance and HTML-first principles
- TODO.md: Complete rewrite with realistic roadmap and current status
- demos/README.md: Update for development demo server usage
## System Reality Alignment
- All documentation now reflects current working system
- Removed aspirational features in favor of actual capabilities
- Clear separation between development and production workflows
- Accurate description of style-aware editor with HTML preservation
## Code Cleanup Benefits
- Simplified codebase focused on HTML-first approach
- Removed markdown conversion complexity
- Cleaner build process without unused dependencies
- Better alignment between frontend capabilities and documentation
Ready for Phase 3a server updates with clean foundation.
- Add JavaScript-based style copying from original elements to toolbar buttons
- Use getComputedStyle() to dynamically apply color, font-weight, text-decoration, text-transform
- Preserve button clickability with protected backgrounds and hover states
- Support any CSS framework/custom styles without hardcoded mappings
- Add comprehensive documentation to TODO.md for future enhancements
Examples:
- 'Emphasis' button now shows red bold text (from .emph class)
- 'Highlight' button displays with style preview while remaining clickable
- 'Brand' button demonstrates text-transform and color changes
This provides intuitive visual feedback so users immediately understand
what each formatting button will do to their content.
- Remove clunky multi-property editor with separate text + URL inputs
- Implement single rich text editor (contentEditable) for all content
- Add popup-based link configuration: select text → click 🔗 Link → configure
- Filter out link styles from formatting toolbar (links use popup, not buttons)
- Consolidate CSS: remove separate style-aware-editor.css, integrate into insertr.css
- Clean up 200+ lines of unused multi-property form code and styles
- Fix duplicate link style detection (no more 'Fancy Link' + 'Link' buttons)
Result: Much cleaner UX similar to modern editors where formatting uses
toolbar buttons and complex elements (links) use dedicated popups.
- Add syntactic sugar for container transformation: .insertr containers → children get .insertr
- Fix discovery auto-running when disabled with site-specific config loading
- Add comprehensive styling test examples for HTML attribute preservation
- Include test input for syntactic sugar validation
- Update discovery defaults to respect developer intent (disabled by default)
- Rebuild JavaScript library with delayed control panel initialization
- Update server assets to include latest UI behavior changes
- Ensure built assets reflect invisible UI for regular visitors
The control panel now only appears after gate activation, maintaining
the invisible CMS principle for end users.
- Create InsertrControlPanel class for unified UI management
- Separate business logic from presentation layer
- Remove DOM manipulation from auth.js and editor.js
- Add comprehensive CSS for status indicators and editing effects
- Implement consistent kebab-case file naming
- Add event-driven communication between core and UI layers
UI Architecture:
- Unified control panel with status indicator and action buttons
- Color-coded status dots (gray/blue/green for visitor/auth/editing)
- Professional editing hover effects with tooltips
- Responsive design for mobile devices
- Proper z-index and accessibility management
Business Logic:
- Pure auth.js focused on authentication state and OAuth flows
- Pure editor.js focused on content editing workflow
- Event emitters for state changes between modules
- Clean separation of concerns and testable architecture
- Remove @layer declarations and complex hybrid approach
- Eliminate all !important usage - rely on natural CSS specificity
- Add explicit color declarations to prevent inheritance issues
- Class selectors (0,0,1,0) naturally beat universal selectors (0,0,0,0)
- Fixes white-on-white modal issues on sites with CSS resets
- Works in all browsers without 2022+ cascade layer requirements
- Cleaner, more maintainable CSS architecture
- Add production Norwegian sales training website demo
- Create placeholder CSS files for Hugo @import statements
- Update .gitignore to exclude *_enhanced/ directories
- Fix CSS MIME type issues for extensionless files in /css/ paths
- Restructure demo directory from test-sites/ to demos/ with flattened layout
- Add auto-enhancement on server startup for all sites with auto_enhance: true
- Fix inconsistent content ID generation that prevented dan-eden-portfolio content persistence
- Update server configuration to enhance from source to separate output directories
- Remove manual enhancement from justfile in favor of automatic server enhancement
- Clean up legacy test files and unused restore command
- Update build system to use CDN endpoint instead of file copying
- Remove obsolete cmd/auto_enhance.go command (replaced by unified enhance)
- Implement EnhanceInPlace method using unified pipeline
- Remove generated demo files from git tracking
- Verify all functionality works after cleanup:
* go build successful
* enhance command working correctly
* unified pipeline (discovery → ID generation → content injection) verified
* clean command structure (only enhance, serve, restore commands)
The codebase is now clean with no legacy auto-enhance references or stub implementations. All functionality consolidated into the unified Discoverer + Enhancer architecture.
- Rename AutoEnhancer to Discoverer with clear element discovery focus
- Implement unified enhancement pipeline in Enhancer:
* Phase 1: Element Discovery (configurable, respects existing insertr classes)
* Phase 2: ID Generation via engine
* Phase 3: Content Injection via engine
- Add EnhancementConfig and DiscoveryConfig for flexible configuration
- Update all method names and references (discoverNode, DiscoveryResult, etc.)
- Support both manual class insertion and automatic discovery
- Maintain single enhance command interface while providing unified internal pipeline
- Update all constructors to use new configuration-based approach
This establishes the clean Discoverer + Enhancer architecture discussed, with discovery as configurable first phase and enhancement as unified pipeline.
- Move all ContentItem, ContentClient, ContentResponse types to engine/types.go as single source of truth
- Remove duplicate type definitions from content/types.go
- Update all imports across codebase to use engine types
- Enhance engine to extract existing data-content-id from HTML markup
- Simplify frontend to always send html_markup, let server handle ID extraction/generation
- Fix contentId reference errors in frontend error handling
- Add getAttribute helper method to engine for ID extraction
- Add GetAllContent method to engine.DatabaseClient
- Update enhancer to use engine.ContentClient interface
- All builds and API endpoints verified working
This resolves the 400 Bad Request errors and creates a unified architecture where the server is the single source of truth for all ID generation and content type management.
Database Structure Cleanup:
- Move all SQL files from ./db/ to ./internal/db/
- Update sqlc.yaml to use new paths (preserving schema+setup.sql hack)
- Consolidate database-related code in single directory
- Remove empty ./db/ directory
Injector Migration:
- Move injector.go from content package to engine package
- Update ContentClient interface to return map instead of slice for GetBulkContent
- Update database client implementation to match interface
- Remove injector dependency from enhancer (stub implementation)
Demo-Site Consolidation:
- Move demo-site to test-sites/demo-site for better organization
- Update build scripts to use new demo-site location
- Maintain all functionality while improving project structure
This continues the unified architecture consolidation by moving core content
processing logic to the engine and organizing related files properly.
- Remove internal/parser package and all legacy ID generation logic
- Update enhancer and auto_enhancer to use unified engine functions
- Migrate utility functions (FindViableChildren, HasEditableContent) to engine
- Create stub enhancer implementation that uses unified engine architecture
- Ensure all enhancement workflows now go through single unified system
- Remove parser dependencies and consolidate content processing logic
This completes the cleanup phase - all components now use unified engine
instead of fragmented ID generation systems.
• Add /insertr.js endpoint to serve JavaScript library from API server
• Implement demo gate auto-injection for sites without existing gates
• Add dynamic site ID injection using per-demo configuration files
• Fix CORS middleware to support localhost origins on any port
• Update demo commands to use individual insertr.yaml configs
• Resolve content persistence issues by matching site IDs between injection and enhancement
• Enable complete edit/save workflow for demo sites with proper namespace isolation
- Add intelligent auto-enhancement that detects viable content elements
- Replace manual enhancement with automated container-first detection
- Support inline formatting (strong, em, span, links) within editable content
- Streamline demo workflow: just demo shows options, auto-enhances on demand
- Clean up legacy commands and simplify directory structure
- Auto-enhancement goes directly from source to demo-ready (no intermediate dirs)
- Add Dan Eden portfolio and simple test sites for real-world validation
- Auto-enhanced 40 elements in Dan Eden portfolio, 5 in simple site
- Achieve true zero-configuration CMS experience
Critical fixes:
- Fixed HTML injection to preserve original element attributes, classes, and styling
- Updated markdown processor to generate inline content instead of wrapped paragraphs
- Enhanced content type handling: database type now takes precedence over parser detection
- Eliminated nested <p> tags issue that was causing invalid HTML
Key improvements:
- Elements like <p class='lead insertr' style='color: blue;'> now maintain all attributes
- Markdown **bold**, *italic*, [links](url) inject as inline formatted content
- Database content type (markdown/text/link) overrides parser auto-detection
- Clean HTML output without structural corruption
Before: <p class='lead'><p>**bold**</p></p> (broken)
After: <p class='lead'>**bold text**</p> (clean)
Server remains source of truth for markdown processing with zero runtime overhead.
Backend implementation:
- Add goldmark dependency for markdown processing
- Create MarkdownProcessor with minimal config (bold, italic, links only)
- Update content injector with HTML injection capabilities
- Add injectHTMLContent() for safe DOM manipulation
- Server now converts **bold**, *italic*, [links](url) to HTML during enhancement
Frontend alignment:
- Restrict marked.js to match server capabilities
- Disable unsupported features (headings, lists, code blocks, tables)
- Update turndown rules to prevent unsupported markdown generation
- Frontend editor preview now matches server output exactly
Server as source of truth:
- Build-time markdown→HTML conversion during enhancement
- Zero runtime overhead for end users
- Consistent formatting between editor preview and final output
- Raw markdown stored in database, HTML served to visitors
Tested features:
- **bold** → <strong>bold</strong> ✅
- *italic* → <em>italic</em> ✅
- [text](url) → <a href="url">text</a> ✅
- Problem: Element ID collisions between similar elements (logo h1 vs hero h1)
causing content to be injected into wrong elements
- Root cause: Enhancer used naive tag+class matching instead of parser's
sophisticated semantic analysis for element identification
Systematic solution:
- Enhanced parser architecture with exported utilities (GetClasses, ContainsClass)
- Added FindElementInDocument() with content-based semantic matching
- Replaced naive findAndInjectNodes() with parser-based element matching
- Removed code duplication between parser and enhancer packages
Backend improvements:
- Moved ID generation to backend for single source of truth
- Added ElementContext struct for frontend-backend communication
- Updated API handlers to support context-based content ID generation
Frontend improvements:
- Enhanced getElementMetadata() to extract semantic context
- Updated save flow to handle both enhanced and non-enhanced elements
- Improved API client to use backend-generated content IDs
Result:
- Unique content IDs: navbar-logo-200530 vs hero-title-a1de7b
- Precise element matching using content validation
- Single source of truth for DOM utilities in parser package
- Eliminated 40+ lines of duplicate code while fixing core bug
- Add manual enhance API endpoint (POST /api/enhance?site_id={site}) for triggering file enhancement
- Implement enhance button in JavaScript library status indicator (🔄 Enhance)
- Disable auto-enhancement in development mode to prevent live-reload conflicts
- Add dev mode parameter to SiteManager to control enhancement behavior
- Update API routing structure to support /api/enhance endpoint
- Include enhance button styling and user feedback (loading, success, error states)
- Button triggers file enhancement and page reload to show updated static files
Development workflow improvements:
- Content edits → Immediate editor preview (no unwanted page reloads)
- Manual enhance button → Intentional file updates + reload for testing
- Production mode maintains automatic enhancement on content changes
This resolves the live-reload conflict where automatic file enhancement
was causing unwanted page reloads during content editing in development.
- Add dev_mode parameter to SiteManager constructor
- Modify IsAutoEnhanceEnabled() to return false when dev_mode is true
- Update serve.go to pass dev_mode flag to SiteManager
- Add ForceEnhanceEnabled() method for testing production behavior in development
- Update documentation to explain development vs production mode behavior
This fixes the development workflow where content updates would trigger
file modifications that caused unwanted page reloads in live-server.
Development mode: Content saved to database only, editor loads dynamically
Production mode: Content saved + files enhanced for immediate static deployment
- Add SiteManager for registering and managing static sites with file-based enhancement
- Implement EnhanceInPlace method for in-place file modification using database content
- Integrate automatic file enhancement triggers in UpdateContent API handler
- Add comprehensive site configuration support in insertr.yaml with auto-enhancement
- Extend serve command to automatically register and manage configured sites
- Add backup system for original files before enhancement
- Support multi-site hosting with individual auto-enhancement settings
- Update documentation for server-hosted enhancement workflow
This enables real-time content deployment where database content changes
immediately update static files without requiring rebuilds or redeployment.
The database remains the single source of truth while maintaining static
file performance benefits.
- Remove mock_content setting (working database loop makes it unnecessary)
- Change server.dev_mode to global dev_mode setting for consistency
- Update CLI to use cli.site_id and cli.output for scoped configuration
- Implement database client for CLI enhance command (complete static site loop)
- Update justfile to use INSERTR_DATABASE_PATH environment variable
- Enable multi-site architecture: server is site-agnostic, CLI is site-specific
- Unified insertr.yaml now supports both server and CLI with minimal config
🏗️ **Major Architecture Refactoring: Separate CLI + Server → Unified Binary**
**Key Changes:**
✅ **Unified Binary**: Single 'insertr' binary with subcommands (enhance, serve)
✅ **Preserved Database Architecture**: Maintained sophisticated sqlc multi-DB setup
✅ **Smart Configuration**: Viper + YAML config with CLI flag precedence
✅ **Updated Build System**: Unified justfile, Air, and npm scripts
**Command Structure:**
- `insertr enhance [input-dir]` - Build-time content injection
- `insertr serve` - HTTP API server (dev + production modes)
- `insertr --config insertr.yaml` - YAML configuration support
**Architecture Benefits:**
- **Shared Database Layer**: Single source of truth for content models
- **Flexible Workflows**: Local DB for dev, remote API for production
- **Simple Deployment**: One binary for all use cases
- **Better UX**: Consistent configuration across build and runtime
**Preserved Features:**
- Multi-database support (SQLite + PostgreSQL)
- sqlc code generation and type safety
- Version control system with rollback
- Professional API endpoints
- Content enhancement pipeline
**Development Workflow:**
- `just dev` - Full-stack development (API server + demo site)
- `just serve` - API server only
- `just enhance` - Build-time content injection
- `air` - Hot reload unified binary
**Migration:** Consolidated insertr-cli/ and insertr-server/ → unified root structure