Skip to content

yashwanth2706/list-app

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

60 Commits
 
 
 
 
 
 
 
 
 
 

Repository files navigation

List App: Understanding DOM as State

A learning project exploring the challenges and limitations of treating the DOM as the single source of truth, with a planned evolution toward modern state management patterns.

📚 Project Purpose

This project is an intentional learning exercise to understand:

  1. DOM as State Pain Points - Why managing application state directly through DOM manipulation becomes problematic
  2. State Management Complexity - How to handle multiple modes (edit, delete), confirmations, and side effects
  3. Frontend Framework Requirements - Why frameworks like React exist and what problems they solve
  4. DOM Diffing Concepts - How minimal diffing algorithms work before adopting a full framework
  5. Architecture Evolution - The migration path from DOM-as-state to state-first to component-based approaches

🎯 Learning Roadmap

Phase 1: DOM as State (Current)
    ↓
Phase 2: State-First with Minimal DOM Diffing
    ↓
Phase 3: React Implementation (Same Functionality)

📋 Features

Core CRUD Operations

  • Add Items: Add single or multiple items (comma-separated input)
  • Edit Items: Click to edit, with fallback to previous value on cancel
  • Delete Items: Toggle delete mode, select items, confirm deletion
  • Clear List: Clear all items with confirmation dialog

State Modes

  • Normal Mode: Default interaction mode
  • Edit Mode: Inline editing with original text preservation
  • Delete Mode: Multi-select mode with visual feedback

User Experience

  • Real-time feedback messages with color coding
  • Input validation and sanitization (alphanumeric + spaces)
  • Confirmation dialogs for destructive actions
  • Visual indicators for active modes (color changes)

🏗️ Architecture Overview

File Structure

assets/
├── css/
│   └── edit-mode.css          # Minimal CSS for edit mode visibility
├── js/
│   ├── stateVariables.js      # Global state variables
│   ├── stateManager.js        # State management functions
│   ├── domRefferences.js       # Cached DOM element references
│   ├── functions.js           # Core utility functions
│   ├── modes.js              # Mode management (edit, delete)
│   └── eventListeners.js     # Event delegation and handlers
└── index.html                # Simple HTML structure

State Variables

// Item being edited
editingItem          // null | HTMLLIElement
originalText         // null | string

// Mode flags
isInEditMode         // boolean
isInDeleteMode       // boolean

// Confirmation flags
confirmClear         // boolean
confirmDelete        // boolean

🚨 Pain Points of DOM as State

1. State Scattered Across Multiple Places

  • Some state in global variables (editingItem, isInEditMode)
  • Some state in DOM attributes (data-marked)
  • Some state in DOM structure (nested editRow inside li)
  • Difficult to see the big picture at a glance

2. Tight Coupling Between State and UI

  • Can't change UI without changing state logic
  • State updates are scattered throughout event handlers
  • No clear data flow or lifecycle

3. Complex State Synchronization

  • Must manually keep DOM in sync with global variables
  • Editing requires moving DOM elements (editRow) between parents
  • Deleting requires updating classes, styles, and attributes
  • No single source of truth

4. Mode Management Complexity

// These states must all be manually managed and kept in sync:
- isInEditMode, editingItem, originalText, editRow visibility
- isInDeleteMode, marked data attribute, color styling
- confirmClear vs confirmDelete flags with different behaviors

5. Difficult Testing and Debugging

  • State is implicit (hidden in DOM/JS variables)
  • Hard to trace state changes
  • Debugging requires inspecting multiple locations
  • Event handlers have side effects on global state

6. Re-rendering Inefficiency

  • Manual DOM manipulation for every state change
  • No automatic diffing - must remember all side effects
  • Style changes, attribute updates, and structural changes are separate

7. Validation and Constraints

  • Business logic scattered across event listeners
  • No centralized place to enforce rules
  • Easy to miss edge cases (e.g., edit while deleting)

📝 Code Organization Insights

stateVariables.js

Declares global state flags, but state is incomplete (doesn't include DOM state like root.querySelectorAll('li');

domRefferences.js

Caches DOM references to avoid repeated querySelector calls - good performance optimization with bad side effect: tight coupling

stateManager.js

Simple setter/getter functions, but they don't actually "manage" state since state is global and modified directly everywhere

functions.js & modes.js

Contains business logic, but mixed with DOM manipulation. Hard to reuse without the DOM layer

eventListeners.js

Event handlers directly manipulate global state and DOM. Complex conditionals for mode management.

🔄 Phase 2: State-First with Minimal DOM Diffing Preview

The next phase will introduce:

// Explicit state object
const appState = {
  items: ['item1', 'item2'],
  editingIndex: null,
  editingOriginal: null,
  isEditMode: false,
  isDeleteMode: false,
  markedForDeletion: new Set(),
  confirmClear: false,
  confirmDelete: false
};

// Pure functions (no side effects)
function addItem(state, itemName) {
  // return new state
}

function updateItem(state, index, newText) {
  // return new state
}

// Minimal DOM diffing
function render(prevState, nextState) {
  // Only update DOM nodes that changed
  // Similar to how frameworks like React work with Virtual DOM
}

🚀 Phase 3: React Implementation

The final phase will convert to React showing:

  • Components as reusable UI units
  • Props for data flow
  • Hooks for state management (useState, useCallback)
  • JSX as declarative UI
  • Automatic re-rendering based on state changes
  • Cleaner event handling

🛠️ How to Run

  1. Open index.html in a modern web browser
  2. Start adding, editing, and deleting items to explore the functionality
  3. Examine the DevTools Console to trace state changes
  4. Review the code to understand the current DOM-as-State approach

💡 Key Insights

Why This Approach Fails at Scale

  • Adding new features (undo/redo, persistence) becomes exponentially harder
  • Team members must understand the scattered state locations
  • Refactoring is risky (easy to miss related state updates)
  • Performance debugging requires understanding multiple systems

What Frameworks Solve

  • React: One source of truth (state), predictable re-renders via virtual DOM
  • Vue: Reactive data binding, computed properties for derived state
  • Svelte: Compiler approach, minimal runtime overhead

Universal Concepts

Regardless of framework choice, modern apps use:

  1. Explicit State - Clear data structure
  2. Pure Functions - Logic without side effects
  3. Unidirectional Data Flow - State → Render → Events → State
  4. Efficient Updates - Only update what changed

📚 Learning Activities

Experiment 1: Trace State

Open DevTools and add breakpoints. Try to answer:

  • Where does editingItem get set?
  • How many places update the DOM?
  • What happens if you edit while deleting?

Experiment 2: Add a Feature

Try adding a search/filter feature to find items by partial text match:

  • You'll quickly see why adding state is painful
  • You'll need to update multiple files
  • You'll face edge cases with existing modes (what happens if you filter while editing?)

Experiment 3: Compare Approaches

After implementing Phase 2 & 3:

  • Note the reduction in event handler complexity
  • Observe the clarity of state flow
  • See how business logic separates from UI

🎓 takeaways

By the end of this learning journey, you'll understand:

  • ✅ Why DOM as State doesn't scale
  • ✅ How state management separates concerns
  • ✅ Why React's component model is powerful
  • ✅ How virtual DOM diffing improves performance
  • ✅ The fundamental patterns in modern frontend development

📖 References


Status: Phase 1 - DOM as State ✅ | Phase 2 - Coming Soon ⏳ | Phase 3 - Coming Soon ⏳

About

Vanilla JS list app exploring DOM-as-state — a learning project on why state management matters, with a planned evolution through state-first diffing to React.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors