Chapter 1: React Philosophy

Components vs Templates

The Traditional PHP Approach

In PHP, you typically separate:

  • The controller: business logic
  • The view: HTML template with variables
// Controller
$users = $userRepository->findAll();
include 'views/users.php';

// View (users.php)
<ul>
    <?php foreach ($users as $user): ?>
        <li><?= htmlspecialchars($user->name) ?></li>
    <?php endforeach; ?>
</ul>

The React Approach

In React, logic and rendering are together in a component:

function UserList({ users }) {
    // Logic here if needed
    const activeUsers = users.filter(u => u.active);

    // Rendering
    return (
        <ul>
            {activeUsers.map(user => (
                <li key={user.id}>{user.name}</li>
            ))}
        </ul>
    );
}

Why? Because display logic and rendering are intrinsically linked. Artificially separating them complicates maintenance.

The Virtual DOM

The Problem with the Real DOM

Manipulating the DOM is slow. Each modification can trigger a layout recalculation and a browser repaint.

// Classic approach - each line touches the DOM
document.getElementById('name').textContent = user.name;
document.getElementById('email').textContent = user.email;
document.getElementById('role').textContent = user.role;

The React Solution

React maintains a lightweight copy of the DOM in memory (Virtual DOM). When data changes:

  1. React creates a new Virtual DOM
  2. Compares it with the old one ("diffing" algorithm)
  3. Calculates the minimal changes
  4. Applies only these changes to the real DOM
// You just describe the desired result
function UserCard({ user }) {
    return (
        <div>
            <span id="name">{user.name}</span>
            <span id="email">{user.email}</span>
            <span id="role">{user.role}</span>
        </div>
    );
}
// React takes care of optimizing updates

Unidirectional Data Flow

The Problem with Two-Way Binding

In some frameworks, data flows in both directions: the view can modify the model and vice versa. This can create loops and make debugging difficult.

The React Solution

In React, data always flows down from parent to child via props:

       App
        |
        ▼ props (users)
    UserList
        |
        ▼ props (user)
    UserCard

If a child wants to modify data, it calls a function passed by the parent:

function App() {
    const [users, setUsers] = useState([]);

    const deleteUser = (id) => {
        setUsers(users.filter(u => u.id !== id));
    };

    return <UserList users={users} onDelete={deleteUser} />;
}

function UserList({ users, onDelete }) {
    return (
        <ul>
            {users.map(user => (
                <UserCard
                    key={user.id}
                    user={user}
                    onDelete={onDelete}
                />
            ))}
        </ul>
    );
}

function UserCard({ user, onDelete }) {
    return (
        <div>
            {user.name}
            <button onClick={() => onDelete(user.id)}>Delete</button>
        </div>
    );
}

Data flows down (props), actions flow up (callbacks).

Declarative vs Imperative

Imperative Approach (jQuery)

You describe how to do things, step by step:

// "When the button is clicked, find the element, modify its content..."
$('#btn').click(function() {
    const count = parseInt($('#count').text()) + 1;
    $('#count').text(count);
    if (count > 10) {
        $('#count').addClass('warning');
    }
});

Declarative Approach (React)

You describe what you want based on state:

function Counter() {
    const [count, setCount] = useState(0);

    return (
        <div>
            <span className={count > 10 ? 'warning' : ''}>
                {count}
            </span>
            <button onClick={() => setCount(count + 1)}>
                +1
            </button>
        </div>
    );
}

You don't say "add the warning class". You say "if count > 10, the class is warning". React handles the rest.

Comparison with Other Approaches

Concept PHP/jQuery React
Where is the logic? Separate (MVC) In the component
How to modify UI? Manipulate the DOM Change the state
Data flow Bidirectional possible Unidirectional
Paradigm Imperative Declarative

Key Points to Remember

  1. Components: reusable blocks that encapsulate logic and rendering
  2. Virtual DOM: React automatically optimizes updates
  3. Unidirectional flow: data down, actions up
  4. Declarative: describe the result, not the steps

<- Back to Module | Next Chapter: JSX ->