Clean, Reusable Code

6.Code Written for the Next Person

A

In this chapter

We'll learn what makes code easy for the next person: comments, formatting and naming — and the bigger ideas of reusable code, abstraction and modularity.

12–14 min

The Problem in Real Life

Anna opens her first pull request: "Fix BUG-142 and move pricing into one function." The code works. All her tests pass. She expects a quick approval.

John leaves six comments instead: "What does t mean?" · "What is 0.8?" · "This comment says what the line does — tell me why instead." · "Indentation is mixed here." · "This function also sends the email. Should it?" · "Move this into its own file."

J

Code is read far more often than it's written. Write it for the next person — that might be you in six months.

John

Code That Works vs. Code Others Can Work With

Working isn't enough

Code that only its author understands becomes a problem the day someone else has to change it.

Small habits, big difference

Good names, consistent formatting and the right comments make code readable at a glance.

Big programs need structure

Thousands of lines stay manageable only when they're split into small, focused pieces.

Writing Clean, Reusable Code

Software lives for years, and many people change it. So professional code has two jobs: work correctly, and be easy for a person to read and change. John's six comments cover the six habits that make that happen:

  • Naming: names should say what something is or does. t means nothing; ticket is clear. calc() is vague; calculateTotal() is clear. Booleans read best as questions: isStudent, hasPaid. JavaScript usually uses camelCase (totalCents), and fixed values often use CAPITALS (GROUP_SIZE). A good name removes the need for many comments.
  • No magic numbers: a bare 0.8 in the middle of code makes the reader guess. A named constant — STUDENT_DISCOUNT = 0.8 — explains itself and can be changed in one place.
  • Comments: notes in the code for people, ignored by the computer (// like this in JavaScript). The best comments explain why, not what — the code already shows what it does. // add 1 to count is useless. // students get the best price, so check them first is valuable.
  • Formatting: consistent indentation, spacing and line breaks, so the structure is visible at a glance. Teams don't argue about this — they use an automatic formatter (like Prettier) that formats every file the same way on save.
  • Reusable code: don't repeat yourself. If the same logic appears in two places, put it in one function and call it from both — exactly what Anna did with calculateTotal. This idea is often called DRY: Don't Repeat Yourself.
  • Abstraction: hiding the details of how something works behind a simple name. The checkout page calls calculateTotal(cart, isStudent) and doesn't need to know how discounts work inside. Abstraction lets you use something without understanding all of it — like driving a car without knowing how the engine works.
  • Modularity: splitting a program into separate, focused pieces — modules, usually separate files — that each do one thing. Pricing lives in pricing.js, email in email.js. One function should do one job, so calculateTotal shouldn't also send emails. Modules share code with export and import.
Table — Before and after the code review
BeforeAfterHabit
for (const t of c)for (const ticket of cart)Naming
total * 0.8total * STUDENT_DISCOUNTNo magic numbers
// check student// students get the best price, so check them firstComments explain why
Mixed 2- and 4-space indentsFormatted automaticallyFormatting
Pricing copied in 3 pagesOne calculateTotal functionReusable (DRY)
Pricing also sends emailsPricing only prices; email is separateOne job per function
Everything in checkout.jspricing.js module, imported where neededModularity
pricing.js — the final, reviewed module
// pricing.js — every BlueTicket price is calculated here, and only here.
export const GROUP_SIZE = 5;
export const GROUP_DISCOUNT = 0.9; // 10% off
export const STUDENT_DISCOUNT = 0.8; // 20% off
export function calculateTotal(cart, isStudent) {
const subtotalCents = sumTicketPrices(cart);
// Students always get the best price, so check them first.
if (isStudent) {
return Math.round(subtotalCents * STUDENT_DISCOUNT);
}
if (cart.length >= GROUP_SIZE) {
return Math.round(subtotalCents * GROUP_DISCOUNT);
}
return subtotalCents;
}
function sumTicketPrices(cart) {
let totalCents = 0;
for (const ticket of cart) {
totalCents += ticket.priceCents;
}
return totalCents;
}
// checkout.js
// import { calculateTotal } from "./pricing.js";

sumTicketPrices isn't exported: it's a detail of how pricing works, hidden behind calculateTotal. That's abstraction.

Anna works through the comments. She renames t to ticket, replaces 0.8 and 0.9 with named constants, rewrites one comment to explain why students are checked first, runs the formatter, removes the email-sending from the pricing function, and moves pricing into its own module, pricing.js, which the checkout, mobile and refund code all import.

John approves the pull request. It's merged. BUG-142 is closed, the college gets its refund, and Anna takes a screenshot of her first merged fix. The sticky note on her desk now has a second line: First merged fix!

Key Takeaway

Clean code is written for people: clear names, no magic numbers, comments that explain why, and consistent formatting. Reusable code follows DRY; abstraction hides details behind a simple name; modularity splits a program into small focused pieces, each doing one job.

Why This Matters

In a real team, code review is how quality is protected, and these habits are what reviewers look for first. They decide how fast the team can change BlueTicket safely — and in Act 24, Anna will get a much tougher review with 31 comments. Clean, modular code is also what makes the testing in Act 17 and the large codebase in Act 25 manageable.

BUG-142 is closed, and Anna has written, fixed, tested, cleaned up and shipped real code. Before moving on, John asks her to write the full pricing rules from scratch — with one new discount added.

Next