Skip to content
ExponaBLOG
ENGINEERING CRAFT · DAY 056 / 100

From senior engineer to tech lead: a step-by-step guide

What changed when I stepped into leadership.

Expona Admin8 min read

The jump from senior engineer to tech lead isn't about writing better code—it's about making everyone else's code better. Six months into my first leadership role, I realized my personal commit count had dropped by 60%, yet I was somehow working harder. This shift from individual contributor to force multiplier is where the real craft begins.

Your output is the team's output — Unblocking others matters more than your own commits

As a senior engineer, I measured success by the features I shipped, the bugs I fixed, the architecture I designed. The moment I became tech lead, that metric inverted. My job was no longer to be the best individual contributor on the team—it was to make my team collectively unstoppable.

I remember our first sprint where a mid-level engineer got stuck on a database query optimization. Three years ago, I would have owned it immediately: "Let me take this, you work on something else." Now I asked different questions. Where's the bottleneck exactly? What have you tried? What's blocking you from researching this yourself? Sometimes the answer was a 10-minute pairing session. Other times it was pointing them to a PostgreSQL article or introducing them to a team member who'd solved something similar.

That engineer ended up writing a more elegant solution than I would have. They learned something real. And I unblocked the entire team without context-switching away from planning the next quarter's roadmap.

Unblocking manifests in different ways:

  • Removing technical debt before it blocks stories. Spotting patterns early—"I see three PRs this month fighting the same service mesh issue"—and making space to fix it once, properly.
  • Clarifying requirements. A vague ticket kills momentum faster than a missing library. Spending 30 minutes with product to write a crisp acceptance criteria saves the team hours of rework.
  • Protecting focus time. Pushing back on constant ad-hoc requests so people can actually finish work.
  • Building onboarding infrastructure. A new engineer joining should not need three days of questions to get their first PR merged. Docs, runbooks, and clear patterns reduce friction exponentially.

The most counterintuitive part: I shipped fewer lines of code, but my team's velocity increased. That's the compounding effect of leadership.

Context switching increases — Protect some time for deep technical work

Week two as tech lead, I had seventeen things on my plate: a design review, two one-on-ones, an incident post-mortem, a vendor evaluation call, code review feedback for four PRs, and a deployment decision. By Friday, I hadn't written a single line of code. I also had no idea if the decisions I'd made were technically sound—I was operating on day-old context.

This is the hidden trap. Leadership creates permission to stop coding, but it doesn't remove the need to stay sharp. You lose credibility fast if you're making architecture decisions about systems you don't actually build in anymore.

I implemented a simple rule: Tuesday and Thursday mornings, before 11 AM, are mine. No meetings. I pair on something that matters—a tricky service refactor, mentoring someone through a complex PR, or working on a shared library that the team uses daily. It's not about shipping features; it's about staying tethered to reality.

This time also compounds. A junior engineer is writing a WebSocket handler and gets stuck on Redis pub/sub backpressure. Because I spent my deep-work block last week building exactly that pattern, I can explain it in context. Because I'm still touching the codebase, I spot architectural drift early. Because I'm still debugging real problems, I understand what our observability tools are actually missing.

Protecting this time also sends a signal to the team: technical work is still valued. It's not something you outgrow into meetings.

Communication becomes core — Translate between product, engineering and stakeholders daily

Senior engineers communicate within their team. Tech leads communicate across functions. I now spend more time in Slack and meetings than in code, translating constantly.

A product manager asks, "Can we add real-time notifications to the dashboard?" A reasonable request. But I need to translate: for whom, with what latency, at what scale, with what reliability? Is this a nice-to-have or a blocker? What problem does it solve? What's the deadline? Then I translate back to engineering: "Here's the requirement. Here's why it matters. Here are three ways we could build this. What are the tradeoffs?" Then back to product: "This is what we can ship in two weeks if we skip some edge cases, or four weeks if we do it right."

The same with stakeholders. A C-level asks about "AI-powered features." That's a signal about direction, but it's vague. My job is to parse what problem they're actually solving for customers, translate that into technical requirements, assess what's actually possible with our data and infrastructure, and come back with a realistic plan.

Bad translation kills projects. I've seen teams build features no one needed because the requirement got lost in handoffs. I've seen stakeholders get frustrated because they expected miracles and engineering was silent about constraints.

Good translation looks like:

  • Asking clarifying questions without being dismissive. "When you say 'scale to millions of users,' what does that actually look like? Peak concurrent load? Sustained? Geographic distribution?"
  • Surfacing tradeoffs explicitly. "We can have it faster, cheaper, or better—pick two. Here's why."
  • Writing down decisions and their reasoning. Slack conversations disappear. A two-minute document saves three months of "I thought we agreed..."
  • Admitting unknowns. "I don't know if that's possible yet. Let me spike it and come back Friday" is infinitely better than committing to something you're not sure about.

I started a weekly "translation check"—15 minutes with product to confirm we're aligned on what we're building and why. Prevents misalignment before it becomes waste.

Decisions outlive you — Architecture choices shape the team for years

As a senior engineer, I made architectural decisions that mattered. But the radius was usually one system, maybe two. When we chose to standardize on a message queue, or decided on a caching strategy, it affected what I built.

As a tech lead, those decisions ripple differently. If I green-light a monolithic service because it's faster to ship, the team will inherit that complexity for three years. If I push for too much abstraction, I'm adding cognitive load to everyone who touches that code. If I decide we're "all in" on a framework or language, I'm constraining future hiring and team composition.

I learned this the hard way. Early in my tenure, we had a performance crisis with our trading platform. Orders were backing up. The obvious fix was to optimize the existing code. But I convinced the team to rewrite the critical path in a lower-level language for speed. It worked—we got 10x throughput. It also meant we needed specialists to maintain it, and that code became a bottleneck for hiring for two years.

Now I think differently. Architecture is a bet about the future. I ask:

  • Who will maintain this in two years when I'm thinking about other things?
  • What skills will the team need?
  • How does this constraint or enable future work?
  • Can we reversible this decision, or are we locked in?

I also document decisions. Not as death-by-PowerPoint design documents, but as a simple ADR (Architecture Decision Record):

typescript
/*
  ADR: Use Redis for session caching, not in-memory
  
  Decision: Implement session storage in Redis instead of Node process memory.
  
  Context: Our current setup loses sessions on deploy. We need statefulness 
  across horizontal replicas. Options: sticky sessions, shared memory, Redis.
  
  Chosen: Redis
  
  Rationale:
  - Survives deployments (sticky sessions don't)
  - Works across multiple servers (in-memory doesn't)
  - We already run Redis for pub/sub
  - Single source of truth for auth state
  
  Consequences:
  - Adds Redis dependency (acceptable, we have it)
  - Network I/O instead of memory access (negligible for session checks)
  - One more service to monitor
  
  Future: If session performance becomes critical at massive scale, 
  we could layer in local caching with TTL syncing.
*/

I post it in Slack, tag the team, invite questions. Three months later, a junior engineer is wondering why we did something. One link back to that decision and they understand the reasoning, the context, the tradeoffs. No mystery, no "because senior people said so."

Common mistakes

Trying to remain an individual contributor while leading. You can't. The team needs your leadership more than your code. Trying to do both usually means you do neither well. Pick which job is actually yours.

Making decisions without building consensus. Especially on big architectural choices. You have authority to decide, but authority without buy-in is brittle. Spend time explaining the reasoning. Let people poke holes. A decision the team disagrees with will be sabotaged, consciously or not.

Not protecting deep work time. Block it. Treat it like a meeting with yourself. Your team will learn quickly that you're not available for ad-hoc meetings at 3 PM because you've been consistent about it for three weeks.

Over-communicating or under-communicating. There's a balance. Over-sharing every decision exhausts everyone. Under-sharing creates rumors and misalignment. Read the room. One weekly team sync + one monthly all-hands is usually enough for a team of 8–12. Adjust by size.

Forgetting that you're still judged on technical quality. A team lead who can't spot a shaky design, who rubber-stamps obvious technical debt, or who makes decisions they can't defend technically loses respect fast. Your code review voice still matters. Your ability to ask "does this scale?" still matters.

Key takeaways

  • Your metric changed from personal output to team output. Measure success by velocity, stability, and growth of people around you.
  • Block deep technical work time and protect it fiercely. You can't lead well if you're disconnected from reality.
  • Most of your job is translation: between product and engineering, engineering and ops, technical and non-technical stakeholders. Get good at explaining tradeoffs clearly.
  • Architecture decisions are leadership decisions. They shape what the team can build and who they can hire for years. Document your reasoning so future maintainers understand the why.
  • Unblocking others compounds. A 30-minute pairing session or a clarified requirement saves the team hours of wasted motion.
  • You're still judged on technical judgment. Stay sharp. Touch the code. The moment you lose credibility as a builder, your leadership becomes hollow.
ShareXLinkedInReddit

Found this useful? Support the writing.

Buy me a coffee
Written by
Expona Admin
Site administrator

Comments

Loading comments…

Leave a comment

Comments are reviewed before they appear. Be kind and stay on topic.

Related articles