🧭 Introduction
In the previous lesson, you learned how to think about testing.
Now it’s time to actually test React components the right way.
Component testing focuses on one core idea:
Test how the component behaves from a user’s point of view.
Not:
- Internal state
- Private functions
- Implementation details
This lesson shows how professional React developers write reliable, maintainable component tests.
🎯 What You’ll Learn in This Lesson
By the end of this lesson, you will understand:
- What component testing really means
- How component tests differ from unit tests
- How to test rendering, interactions, and state changes
- How to handle props, conditional UI, and errors
- Common mistakes and best practices
🧠 What Is Component Testing?
Component testing verifies:
- The component renders correctly
- The component responds to user actions
- The UI updates as expected
It treats the component as a black box:
Input → Interaction → Output
🧩 Component Test vs Unit Test
| Aspect | Unit Test | Component Test |
|---|---|---|
| Scope | Logic only | UI + behavior |
| Focus | Functions | User interaction |
| React involved | ❌ Optional | ✅ Yes |
🧠 Golden Rule of Component Testing
If a user can’t see it or do it, you shouldn’t test it.
🧪 Basic Component to Test
function Counter() {
const [count, setCount] = React.useState(0);
return (
<div>
<p>Count: {count}</p>
<button onClick={() => setCount(count + 1)}>Increment</button>
</div>
);
}
🧪 What Should We Test Here?
✔ Initial render
✔ Button click behavior
✔ UI update
❌ State variable
❌ setState calls
🧠 Testing the Initial Render
expect(screen.getByText("Count: 0")).toBeInTheDocument();
This checks what the user sees, not how state works.
🧠 Testing User Interaction
fireEvent.click(screen.getByText("Increment"));
🧠 Testing UI Update
expect(screen.getByText("Count: 1")).toBeInTheDocument();
✔ Simple
✔ Clear
✔ Reliable
🧠 Testing with Props
function Greeting({ name }) {
return <h2>Hello, {name}</h2>;
}
Test Thinking
- Does the text render correctly based on props?
expect(screen.getByText("Hello, Avni")).toBeInTheDocument();
🧠 Testing Conditional Rendering
function Status({ isLoggedIn }) {
return (
<div>
{isLoggedIn ? <p>Welcome back</p> : <p>Please login</p>}
</div>
);
}
Tests
expect(screen.getByText("Welcome back")).toBeInTheDocument();
and
expect(screen.getByText("Please login")).toBeInTheDocument();
Each test represents a user scenario.
🧠 Testing Forms (High-Level)
function Login() {
return (
<form>
<input placeholder="Email" />
<button>Login</button>
</form>
);
}
Test Focus
✔ Input is present
✔ Button is clickable
Not:
❌ Form library internals
🧠 Testing Error UI
function ErrorMessage({ error }) {
if (!error) return null;
return <p>{error}</p>;
}
Test
expect(screen.getByText("Invalid credentials")).toBeInTheDocument();
🧠 Avoid Testing Implementation Details
❌ Bad Test
expect(setCount).toHaveBeenCalled();
✅ Good Test
expect(screen.getByText("Count: 1")).toBeInTheDocument();
Test outcome, not mechanics.
🧠 Testing Accessibility (Bonus)
Good tests improve accessibility:
screen.getByRole("button", { name: /increment/i });
Encourages semantic HTML.
🚨 Common Component Testing Mistakes
❌ Snapshot-Only Testing
Snapshots don’t test behavior.
❌ Over-Mocking Components
Mock external APIs, not your UI logic.
❌ Testing CSS
Style tests are brittle and low-value.
❌ Ignoring Edge Cases
Test empty states and error states too.
🎯 Best Practices (Senior-Level)
✅ Test user behavior
✅ Use semantic queries
✅ Keep tests readable
✅ Avoid fragile selectors
✅ Test one behavior per test
✅ Maintain tests with code
❓ FAQs — Component Testing
🔹 Should every component have tests?
No — test important ones.
🔹 Can I test state directly?
No — test UI effects.
🔹 Is component testing slow?
No — when done correctly.
🔹 Is this interview-relevant?
Yes — very common.
🧠 Quick Recap
✔ Component tests focus on behavior
✔ Treat components as black boxes
✔ Test rendering and interactions
✔ Avoid implementation details
✔ User-first mindset
🎉 Conclusion
Component testing ensures your UI:
- Works as expected
- Responds to users
- Survives refactoring
When done right, tests become:
A safety net, not a burden
This lesson prepares you for real-world React testing workflows 🧪⚛️
👉 Next Lesson
Lesson 31 — Testing Forms & API Calls