The Pragmatic Programmer — Your Journey to Mastery (20th Anniversary Edition)

Authors: David Thomas & Andrew Hunt
Edition: 20th Anniversary (2nd Edition, 2019)
Topics: 53 | Tips: 100 | Pages: 497


Book in One Paragraph

A pragmatic programmer is defined by attitude — taking ownership of their work, thinking deliberately, and applying universal principles (not fashionable tools) to produce software that is correct, maintainable, and flexible. The book covers 53 topics across individual philosophy, design principles, basic tools, code practices, concurrency, project management, and ethics, unified by a single root idea: write code that is easy to change.


Structure Overview

ChapterTopicsCore Theme
1: A Pragmatic Philosophy1–7Ownership, attitude, knowledge investment, communication
2: A Pragmatic Approach8–15ETC, DRY, orthogonality, reversibility, tracer bullets, prototypes, domain languages, estimation
3: The Basic Tools16–22Plain text, shell, editor fluency, VCS, debugging, text manipulation, daybooks
4: Pragmatic Paranoia23–27DBC, crash early, assertions, resource balancing, small steps
5: Bend, or Break28–32Decoupling, event strategies, transformations, inheritance tax, configuration
6: Concurrency33–36Temporal coupling, shared state, actor model, blackboards
7: While You Are Coding37–44Lizard brain, coincidence, Big-O, refactoring, testing, property tests, security, naming
8: Before the Project45–48Requirements, impossible puzzles, working together, agility
9: Pragmatic Projects49–53Teams, methodology, starter kit, delighting users, pride
10: PostfaceEthical responsibility

The 100 Tips (Quick Reference)

#Tip
1Care About Your Craft
2Think! About Your Work
3You Have Agency
4Provide Options, Don’t Make Lame Excuses
5Don’t Live with Broken Windows
6Be a Catalyst for Change
7Remember the Big Picture
8Make Quality a Requirements Issue
9Invest Regularly in Your Knowledge Portfolio
10Critically Analyze What You Read and Hear
11English is Just Another Programming Language
12It’s Both What You Say and the Way You Say It
13Build Documentation In, Don’t Bolt It On
14Good Design Is Easier to Change Than Bad Design
15DRY — Don’t Repeat Yourself
16Make It Easy to Reuse
17Eliminate Effects Between Unrelated Things
18There Are No Final Decisions
19Forgo Following Fads
20Use Tracer Bullets to Find the Target
21Prototype to Learn
22Program Close to the Problem Domain
23Estimate to Avoid Surprises
24Iterate the Schedule with the Code
25Keep Knowledge in Plain Text
26Use the Power of Command Shells
27Achieve Editor Fluency
28Always Use Version Control
29Fix the Problem, Not the Blame
30Don’t Panic
31Failing Test Before Fixing Code
32Read the Damn Error Message
33”select” Isn’t Broken
34Don’t Assume It — Prove It
35Learn a Text Manipulation Language
36You Can’t Write Perfect Software
37Design with Contracts
38Crash Early
39Use Assertions to Prevent the Impossible
40Finish What You Start
41Act Locally
42Take Small Steps — Always
43Avoid Fortune-Telling
44Decoupled Code Is Easier to Change
45Tell, Don’t Ask
46Don’t Chain Method Calls
47Avoid Global Data
48If It’s Important Enough to Be Global, Wrap It in an API
49Programming Is About Code, But Programs Are About Data
50Don’t Hoard State; Pass It Around
51Don’t Pay Inheritance Tax
52Prefer Interfaces to Express Polymorphism
53Delegate to Services: Has-A Trumps Is-A
54Use Mixins to Share Functionality
55Parameterize Your App Using External Configuration
56Analyze Workflow to Improve Concurrency
57Shared State Is Incorrect State
58Random Failures Are Often Concurrency Issues
59Use Actors For Concurrency Without Shared State
60Use Blackboards to Coordinate Workflow
61Listen to Your Inner Lizard
62Don’t Program by Coincidence
63Estimate the Order of Your Algorithms
64Test Your Estimates
65Refactor Early, Refactor Often
66Testing Is Not About Finding Bugs
67A Test Is the First User of Your Code
68Build End-to-End, Not Top-Down or Bottom Up
69Design to Test
70Test Your Software, or Your Users Will
71Use Property-Based Tests to Validate Your Assumptions
72Keep It Simple and Minimize Attack Surfaces
73Apply Security Patches Quickly
74Name Well; Rename When Needed
75No One Knows Exactly What They Want
76Programmers Help People Understand What They Want
77Requirements Are Learned in a Feedback Loop
78Work with a User to Think Like a User
79Policy Is Metadata
80Use a Project Glossary
81Don’t Think Outside the Box — Find the Box
82Don’t Go into the Code Alone
83Agile Is Not a Noun; Agile Is How You Do Things
84Maintain Small, Stable Teams
85Schedule It to Make It Happen
86Organize Fully Functional Teams
87Do What Works, Not What’s Fashionable
88Deliver When Users Need It
89Use Version Control to Drive Builds, Tests, and Releases
90Test Early, Test Often, Test Automatically
91Coding Ain’t Done ‘Til All the Tests Run
92Use Saboteurs to Test Your Testing
93Test State Coverage, Not Code Coverage
94Find Bugs Once
95Don’t Use Manual Procedures
96Delight Users, Don’t Just Deliver Code
97Sign Your Work
98First, Do No Harm
99Don’t Enable Scumbags
100It’s Your Life. Share it. Celebrate it. Build it. AND HAVE FUN!

The Unifying Idea

Everything in the book flows from ETC — Easier to Change:

  • DRY → one representation = one place to change
  • Orthogonality → independent components = local changes
  • Decoupling → loose coupling = isolated changes
  • Reversibility → no final decisions = freedom to change
  • Refactoring → gardening, not construction = continuous change
  • Agility → feedback loop = capability to change
  • Good naming → clarity = easier to understand before changing
  • Testing → safety net = confidence to change

Chapter Notes Index