The Constraints We Code Against
Every web developer eventually hits the same wall: the realization that our medium is bound by forces that don't exist for developers on other platforms. The "C" word that deserves more attention in our industry isn't CSS or "continuous integration"—it's constraints. How well we understand and respect those constraints determines whether the software we build actually works for the people who use it.
The lesson is easiest to see in retro gaming. Super Nintendo developers shipped remarkable, enduring titles inside a box of hard limits: 16-bit color, 8-channel audio, and cartridges measured in megabits rather than megabytes. Select titles even embedded a special 3D coprocessor chip in the cartridge itself. But those constraints were static—one console, one set of capabilities. Master that single configuration and anyone with the hardware could enjoy your work.

PC games of the same era told a different story. The system requirements printed on the box read like a sliding scale of compromise: a 386 processor was the floor, but a Pentium was preferred; Ad Lib or PC speaker audio would do, but a Sound Blaster was better; 4 MB of RAM was the minimum, but more was always welcome. The result was a gradient of experiences. Players with modest machines could still play, just with reduced fidelity, while those with top-tier hardware got the full effect.

Three Variables, One Performance Target
Web developers face a harder version of that PC problem. Unlike console developers, we can't nail down a single target configuration. And unlike PC game developers, we don't even get to ship a binary tuned for a handful of known sound cards and CPUs. We are forced to reconcile three independent variables at once:
- The network.
- The device.
- The browser.
Each of those variables changes between users, and each changes over time for the same user. That makes the job of building fast websites genuinely difficult, and it's a difficulty that repeats itself on every project and with every new technology evaluated against it.
Where's the line between shipping too much JavaScript and starving the developer experience? There's a tension there. We need some level of tooling and abstraction to keep our day-to-day work productive, but we can't let that convenience degrade what end users experience. On that question, the foundational documents are unambiguous: users come first.
Relearning the Same Lesson
Every year brings the same fundamental insight, delivered in a slightly different disguise: technology choices carry costs and trade-offs. One persistent lesson, driven home in clear and present fashion this year, is that choices can lock us into architectures that hurt the user experience when we don't tread carefully—and those architectures become increasingly difficult to escape the longer they persist.
A second lesson is that working directly with the platform is hard but essential. Raw platform APIs aren't always the most scalable way to ship software, and abstractions exist for a reason. But using the platform regularly—rather than grabbing whatever package scratches today's itch—builds a deeper understanding of how the web works. And that knowledge is exactly what makes building good abstractions possible in the first place.
Room for a Range of Experiences
The final, recurring lesson is that our constraints are variable. It's acceptable when some things don't work perfectly everywhere—but we must be deliberate about which things those are. For critical functions, our responsibility to the public demands the utmost care. The past year of rising unemployment and remote learning made plain that the internet supports more than commerce.
The best hope for the web is not uniformity but adaptability. We should expect experiences to vary in fidelity to accommodate slower systems, just as PC games of an earlier era scaled back gracefully on modest hardware. Rather than forcing every visitor to endure the exact same experience regardless of their device, the web could aim for what console and PC developers long ago figured out: a well-built experience accommodates the range of hardware it may run on, rather than pretending that range doesn't exist.



