cd ../writing
// career · onboarding

Learning a new codebase fast — the first 30 days.

New job. New team. 200,000 lines of code you've never seen, written by 50 people you don't know, evolving for 8 years before you arrived. The strong engineer becomes productive in this environment in 30 days. The weak one is still asking the same questions 3 months later. The difference isn't intelligence — it's approach. This is the working playbook for getting your bearings fast.

30-day plan 7 practices real traps to avoid © use freely

01What "productive" actually means

You're not productive when you've read all the code. You'd never finish. Productive means:

  • You can pick up a routine bug and fix it without help.
  • You can review a teammate's PR and add real value.
  • You can answer simple questions about how the system works without looking everything up.
  • You can predict where in the codebase a feature would live, without grepping.

30 days is plenty of time to reach that bar — if you optimize for the right things.

02Week 1 — get it running, end to end

Before reading any code, get the application running locally. Database migrations applied. Services up. Frontend talking to backend. Real auth working. Run the test suite. Watch it pass.

This single step teaches you more than reading code for a week:

  • You learn what services exist and how they connect.
  • You discover the dev tools, build system, and conventions.
  • You find the gaps in onboarding docs — and you can fix them while they're still fresh.
  • You unlock the ability to make real changes and see what happens.

Most onboarding docs are out of date. Document every divergence as you go. Your fixes become the next new hire's headstart.

03Build a mental map, top-down

Don't read code linearly. Build a map from the outside in:

  1. What does the product do? Use it as a user. Sign up. Click through. Understand it as a customer first.
  2. What are the major services? List them. Two-sentence description each.
  3. What's the data model? Look at the database schema. Identify the 5-10 most important tables. The rest are details.
  4. What are the entry points? Routes, queue consumers, scheduled jobs. Where does work come into the system?
  5. What's the deploy and observability story? How do changes get to prod? Where are the dashboards?

After this, you don't know the code, but you know the territory. That's enough to navigate.

04Trace a feature end-to-end

Pick one common user action — search, login, checkout, whatever's central. Trace its full path:

  • What URL or event triggers it?
  • Which controller/handler picks it up?
  • What services does it call?
  • What database queries run?
  • What gets returned to the client?
  • What state changes happen as a side effect?

Use the debugger. Use logs. Use observability tools to trace a real request through the system. Don't try to read every file — follow the one path you chose.

After tracing one feature, you've seen the patterns used everywhere. Authentication, validation, error handling, logging, dispatch — all the conventions are visible in one slice.

05Use git history as documentation

When you find a piece of code you don't understand, run git log -p on it. The commits tell a story: when was this added, what bug did it fix, what PR introduced it. Often the commit message explains the "why" that the code itself doesn't.

✓ git archaeology commands
# History of a specific file
$ git log -p path/to/file

# Who wrote each line and when
$ git blame path/to/file

# History of a specific function or block
$ git log -L :functionName:path/to/file

# Find when something appeared or was changed
$ git log -S "some unique string"
$ git log -G "regex pattern"

Linked PRs add even more context: discussion, related issues, the reviewer who pushed back. The codebase you're inheriting is the visible result of thousands of conversations. The artifacts of those conversations are still there.

06Ship something small in week 1

Don't wait until you "understand everything." Ship a small change in the first week:

  • A typo fix in user-facing copy
  • A missing test for a function with no coverage
  • A documentation update from your own onboarding experience
  • A small refactor someone has wanted for months

Why: shipping forces you to learn the whole pipeline. PR template, CI, code review, deployment. Every step you'll need later, but now you've practiced it under low-stakes conditions.

Also: psychologically, shipping breaks the "I don't know anything yet" spiral. You DO know something — you just shipped it.

07Ask questions in batches

Two failure modes:

  • Asking every question immediately. Interrupts your senior teammates 20 times a day. They start avoiding you.
  • Asking no questions. Spending hours stuck on things that have a 30-second answer. Slows you to a crawl.

The sweet spot: keep a running doc of questions. Try to answer them yourself first (read code, search Slack, check docs). If you can't, batch them into your 1-on-1 or a scheduled "questions hour" with your buddy.

Add to the questions list: "things I figured out on my own." You'll review later, and the patterns of what was confusing become your onboarding doc improvements.

08Look for conventions, not exceptions

Codebases have conventions. The 80% of the code that follows them is uninteresting — once you've seen the pattern, you can predict it. The 20% that diverges from convention is where the bugs and the history live.

Spend your reading time on:

  • The conventions themselves. One example each of routing, models, controllers, tests. Internalize the patterns.
  • The shared utilities and abstractions. What's in the lib/ folder? The helpers everyone uses?
  • The exceptions. Anywhere the code diverges from convention is a signal — either it's old code that wasn't migrated, or there's a reason for the exception. Both are worth understanding.

09Traps to avoid

Trying to read every file. You'll burn out and learn nothing. Read in service of a task.

"I should understand this perfectly before changing it." No, you should understand it enough to make the change correctly. Perfect understanding is unreachable; sufficient understanding is.

Defending the previous codebase. "At my old job, we did X." Every team has heard this from every new hire. Internalize the new patterns before evaluating them.

Refactoring before you understand. The code you think is bad usually has reasons you don't yet see. Wait 3 months before proposing major refactors. The opinions you'd have today are different from the ones you'll have then.

Being afraid to break things. You will break things. So has every engineer on the team. The recovery is what matters — own it, fix it, learn. Companies that punish honest mistakes are companies you want to leave.

Skipping the human side. The codebase isn't the only system. Learn who works on what, who knows what, who to go to with which question. The social graph matters as much as the file graph.

10AI tools — useful, with caveats

LLM-based tools (Cursor, GitHub Copilot, Claude Code) are genuinely useful for onboarding to a new codebase. They can:

  • Explain what a function does in plain English
  • Find usages of patterns you've identified
  • Suggest where similar features might live
  • Generate test cases to verify your understanding

But: don't let the AI substitute for understanding. If the AI tells you "this function handles authentication" and you ship a change based on that, you've ceded the understanding. Use AI to accelerate exploration; verify the conclusions by reading the actual code.

The compound

The first 30 days set the trajectory. Engineers who establish good habits early — running locally, tracing features, asking questions in batches, shipping small changes — accelerate continuously. Engineers who fall into the "I'll just keep reading" trap stall for months.

Treat onboarding as an engineering problem. Optimize for time-to-productive. Document the gaps you find. Ship early. The next codebase you join will go even faster, because the pattern transfers.