Skip to content

Lab 2.4: Incremental Improvement ​

Module: 2.4 - Safe Refactoring | ← SlidesDuration: 1 hour Sample Project: node-express-mongoose-demo

Learning Objectives ​

By the end of this lab, you will be able to:

  • Refactor code safely with test verification
  • Make incremental changes (small steps)
  • Improve readability without changing behavior
  • Use tests as a safety net

Prerequisites ​

  • Completed Labs 2.2 and 2.3
  • Tests in place for the code you'll refactor
  • Confidence in running the test suite

The Safe Refactoring Workflow ​

1. Verify tests pass (baseline)
2. Make one small change
3. Run tests
4. If green: commit and continue
5. If red: revert and try again

Setup ​

bash
# Navigate to the sample project
cd sample-projects/node-express-mongoose-demo

# Verify tests pass BEFORE starting
npm test

# Start Claude Code
claude

Task 1: Identify Code Smells ​

Time: 10 minutes

Find code that needs improvement.

Prompts to try:

What code smells exist in app/controllers/articles.js?
Are there any functions with too many responsibilities?
Find examples of duplicated code in this project.

Common code smells:

  • Long methods (>20 lines)
  • Duplicated code
  • Poor naming
  • Deep nesting
  • Magic numbers/strings

Success criteria:

  • [ ] Identified 2-3 code smells
  • [ ] Selected one to fix

Task 2: Refactor for Readability ​

Time: 15 minutes

Improve variable and function names.

Step 1: Run tests (baseline)

bash
npm test

Step 2: Improve naming

Rename the variables in this function to be more descriptive. Don't change any behavior.
The function name 'proc' is unclear. Suggest a better name and rename it throughout the codebase.

Step 3: Verify tests pass

bash
npm test

Success criteria:

  • [ ] Names are clearer
  • [ ] Tests still pass
  • [ ] Behavior unchanged

Task 3: Extract Helper Functions ​

Time: 20 minutes

Break down complex functions.

Step 1: Identify extraction opportunities

This function is too long. What parts could be extracted into separate functions?

Step 2: Extract one piece

Extract the [specific logic] into a separate helper function.

Step 3: Run tests

bash
npm test

Step 4: Repeat for other pieces

Success criteria:

  • [ ] At least one function extracted
  • [ ] Tests pass after each extraction
  • [ ] Main function is now shorter

Task 4: Remove Duplication ​

Time: 15 minutes

DRY up the codebase.

Step 1: Find duplication

Find duplicated code between the create and update functions.

Step 2: Extract shared logic

Extract the common validation logic into a shared function used by both create and update.

Step 3: Verify

bash
npm test

Success criteria:

  • [ ] Duplication removed
  • [ ] Shared function created
  • [ ] Tests pass

Refactoring Techniques ​

TechniqueWhen to UseExample
RenameUnclear namesx → userId
Extract FunctionLong methodsPull out 10 lines into helper
InlineOver-abstractionRemove unnecessary wrapper
MoveWrong locationMove util from controller to utils/
Replace MagicHard-coded values86400 → SECONDS_PER_DAY

The Golden Rule ​

Remember

"Refactoring is changing code without changing behavior."

After every change:

  1. Run tests
  2. If they pass, you're safe
  3. If they fail, you changed behavior (revert!)

Commit Strategy ​

Commit after each successful refactoring:

bash
# After each green test run
git add .
git commit -m "Refactor: Extract validation helper from article controller"

Small commits = easy rollback if something goes wrong.


Tips for Success ​

  1. One change at a time - Don't combine refactorings
  2. Run tests constantly - After every single change
  3. Commit frequently - Save your progress
  4. Keep behavior identical - If tests fail, you went too far

Common Refactoring Prompts ​

Rename this variable to something more descriptive.
Extract the loop body into a separate function.
Replace this magic number with a named constant.
Simplify this nested if-else into an early return pattern.

Red Flags (Stop Refactoring) ​

  • Tests start failing unexpectedly
  • You're adding new features (that's not refactoring)
  • Changes are getting too large to track
  • You've been refactoring for >30 min without committing

Stretch Goals ​

If you finish early:

  1. Refactor deeply nested conditionals into guard clauses
  2. Extract a configuration object from scattered magic values
  3. Improve error handling consistency

Deliverables ​

At the end of this lab, you should have:

  1. Cleaner, more readable code
  2. Smaller, focused functions
  3. Reduced duplication
  4. All tests still passing
  5. Clean commit history showing incremental changes

Next Steps ​

After completing this lab, move on to Lab 2.7: Modernization Mini-Project - the Day 2 capstone.

Claude for Coders Training Course