Blog

Posts on software development, careers, and craft.

A weird misuse of React’s context I just found: 1

A weird misuse of React’s context I just found: 1. The user clicks a record on a list page. 2. The record’s detail is fetched, then stored in conte...

Problem: Meetings are often needless, slow, expensive, and hard to schedule

Problem: Meetings are often needless, slow, expensive, and hard to schedule. My solution: Create a video instead. I make a clear proposal in a vide...

Problem: In React Query, a mutation often needs access to the query's key so...

Problem: In React Query, a mutation often needs access to the query's key so it can clear cache. Solution: Put associated queries and mutations in...

Reviewing code is one of the most rewarding things I do

Reviewing code is one of the most rewarding things I do. Why? Because I get to see developers grow. At first, junior developers have a lot of issue...

Poll: Which code do you prefer for returning totals

Poll: Which code do you prefer for returning totals? 1. let and forEach 2. reduce Poll in next tweet...

Just refactored a React component

Just refactored a React component. I removed 50% of the code.🔥 What I did: 1. Unify 10 related useState into 1 useState object 2. Unify 10 onChang...

Problem: Sometimes I make unrelated changes when working on a feature

Problem: Sometimes I make unrelated changes when working on a feature. (I notice nearby, related code that needs work, so I fix it). This can lead...

If useEffect is the answer, I'm probably asking the wrong question

If useEffect is the answer, I'm probably asking the wrong question. Examples: "How do I sync state?" Don't. Derive it. "How do I fetch with plain R...

A well-designed REST API doesn't merely expose each DB table

A well-designed REST API doesn't merely expose each DB table. Doing so leads to: 🚫 Many HTTP calls 🚫 Returning data the UI doesn't need 🚫 A lot...

How I define a unit test: An automated test that tests 1 function or...

How I define a unit test: An automated test that tests 1 function or component, alone. I write unit tests for 2 cases: 1. Reusable, pure util funct...

I joined a struggling team in January

I joined a struggling team in January. Then: 🚫 No tests 🚫 Few lint rules 🚫 No CI config 🚫 Over 1,300 “any” in TypeScript 🚫 1,000’s of lines of...

Problem: TypeScript optional fields reduce type safety

Problem: TypeScript optional fields reduce type safety. Why? Because an optional field can't specify when the field is optional vs required. Soluti...

A single monorepo for an entire company rarely makes sense

A single monorepo for an entire company rarely makes sense. A separate repo for every team also rarely makes sense. The happy middle-ground? Put *r...

Comprehensive test coverage is great

Comprehensive test coverage is great. But, focusing on code coverage metrics isn’t. Avoid “we require x percent code coverage”. Prefer “we write au...

Some developers love consistency too much

Some developers love consistency too much. Examples: “Always use let.” “Always use an arrow function instead and of a function declaration.” “Alway...

The less experience a developer has, the harder their job is (because they...

The less experience a developer has, the harder their job is (because they accidentally make it hard). The more experience a developer has, the eas...

As, a consultant, I’ve learned PRs are the most effective way to create...

As, a consultant, I’ve learned PRs are the most effective way to create actual change. If I ask for meetings, or suggest a change, the change won’t...

When I audit a project, I clean up first

When I audit a project, I clean up first. 1. Run cspell to fix spelling issues 2. Remove unused vars and imports 3. Remove "dead" code (commented o...

A new reason I’m a fan of Tailwind: It’s AI friendly

A new reason I’m a fan of Tailwind: It’s AI friendly. I can ask an AI to create components with styles written in Tailwind. This idea doesn’t work...

Web app testing tip: 1

Web app testing tip: 1. Store all your links and headers in an array 2. Use the array to generate your nav bar 3. Use the array to generate a test...

6 signs a dev team is out of control: 1

6 signs a dev team is out of control: 1. Few/no automated tests 2. Many lint warnings/errors 3. No Continuous Integration server 4. Frequent misspe...

One of the hard parts of leaving a software development project: I can't see...

One of the hard parts of leaving a software development project: I can't see what I built anymore. If I built a building, I could drive by and smil...

TypeScript is the biggest improvement to my web dev experience in the last 5...

TypeScript is the biggest improvement to my web dev experience in the last 5 years. ✅ I feel less stressed. ✅ Reading code is easier. It's more exp...

Situation: Multiple teams are collaborating to create a single, big React app

Situation: Multiple teams are collaborating to create a single, big React app. How would you handle it? 1. Cross-team monolith - All teams collabor...

When you’re building a dialog, ask this: “Should users be able to share a...

When you’re building a dialog, ask this: “Should users be able to share a link to this dialog?” If so, store the open state for the dialog in the U...

React: The Most Common Mistakes in 2023 I'm presenting this talk at @kc_dc...

React: The Most Common Mistakes in 2023 I'm presenting this talk at @kc_dc in July! The list: State: Needless state Global state overuse Syncing st...

Problem: A page has multiple dialogs, but only one dialog should be...

Problem: A page has multiple dialogs, but only one dialog should be displayed at any given time. Solution: Handle dialog state via one piece of sta...

Had a lot of fun this week teaching React with TypeScript, React Query, Mock...

Had a lot of fun this week teaching React with TypeScript, React Query, Mock Service Worker, Tailwind, and Playwright here in my hometown of KC!

I prefer: ✅ Static types over dynamic types ✅ Functional programming over...

I prefer: ✅ Static types over dynamic types ✅ Functional programming over object oriented programming ✅ Automated tests over manual tests ✅ Integra...

In JavaScript, I export on the same line as the declaration

In JavaScript, I export on the same line as the declaration. This avoids having to repeat the function's name in two spots. And I can see the funct...