Programming can be called the art of making immensely big problems smaller and solving them one by one. Programmers divide and conquer entire systems that span across thousands of lines of code, making it all work like a giant clock day by day going full-on with an extremely low chance of an error happening, due to a sophisticated composition of its pieces and thorough testing achieved by experimenting and embracing chaos.
Sometimes, it is hard to pinpoint a small issue thatās going on. Tens of libraries, three frameworks and two synced-up databases your project employs to live up after a decade of development by several teams make it so hard to distinguish a small faulty click in an endless rattling of all the components of your program. There are a bunch of middlewares intercepting your request, then another bunch intercepting the response, some global configurations, sprinkled with a new library you never heard of and some additional services that need to be managed to start and work in the rhythm of the rest of your system.

To solve that, just like every open-source maintainer or a random fellow on StackOverflow will ask you, we can challenge our bugs to a duel we can use a little box where we extract only the thing we need to inspect. Those are called sandboxes, playgrounds, testbeds, reproductions. Just like Storybook allows us to enter the museum of our precious buttons and inspect each and one of them in every possible configuration, a small folder with just a beginner Vite+React template can help us identify why the library is not working as intended, or a composition of different docker-compose configurations can make it seamless to start the service from scratch, without all the overhead a dozen of tables incur when we are just trying to test out this simple stored procedure.
We can make sure that weāre allowed to do whatever the heck we want, be it sudo rm -rf / --no-preserve-root
or whatever else. Everything is contained in a box and will never get out, like package.json
ās dependencies. We will not just forget to undo this little change that we added to test our existing code, or remove the package that we donāt need, we have no chance of nuking our production database. Since we have this freedom, we are able to experiment beyond what is written in the docs, which promotes better learning with kinesthetic, practical experience we are allowing ourselves to have.
When we have extracted the problem, we erase all possibilities of external unknowns that live in our production system to affect what happens. Instead of relying on abstraction that tells us that some external is running and doing just what it must, instead of delving deep and finding out that it does not, and that it has another dependency that is probably just like itself, we can start anew, with full control over a certain package or a concept that weāre building.
Say, we want to test out the useContext
hook works in React. Do we need to use our other, existing projects for that? Surely not. If we learn how to use this hook on itself with a simple example from documentation, then we are ready to use this knowledge for our concrete case. So, we run:
1pnpm create vite@latest
choose React, TypeScript, and here we have a nice clean project:

We can remove all unnecessary things and have a clean white screen, where we would put whatever we need, install dependencies one by one, checking. if we need, whether they have an effect upon each other, trying out a new technology and so on. Being a curious programmer, we add a library, or write some unexpected code and see what happens. We can nuke it completely and start anew, and it makes our journey so much more fun.
For the sake of not setting it up from scratch every time we choose to try something, we can have a separate folder on our machine where all these kind of projects go and live, and then we can have them as either templates to just cp
them and add the things we need, or manage everything in one place, adding or removing the dependencies however we see fit.
For web development, we can have, for example, just a simple index.html
+ index.js
files to try out Vanilla JS things, plus to that we can add a simple Node
project with index.js
and package.json
to try out the JS quirks easily in our terminal. For other fields, we can add something we need day-to-day, to test out the new feature in Java
version 777, or to follow a quick tutorial on how to make pagination work with postgresql
.
To easily share our code and environment with others, there are projects dedicated to this, for example codesandbox. You can use their āimport project buttonā, but, say, we want to quickly share our GitHub repository with someone so they could tinker with the bug we found. We can go to our repoās page, and just add a box
at the end of domain name:

To share our HTML and CSS easily we can use codepen, although Python is not directly runnable in the browser, we can do it here. for all kinds of databaseās shenanigans, db-fiddle can help out. We are able to fill CREATE TABLE
queries alongside something we are stuck with, making the issue as small as possible, to later add the link to it in our dbastackexchange post. This way, people will be able to empirically figure out whatās wrong, instead of trying to interpret your situation the correct way. Oftentimes, when trying to reproduce issue in such an environment, you figure out not so long after starting where you have made a mistake and fix it on your own.
Trying to ensure our websiteās functionality, we can setup playwright
for it to run an emulated version of multiple browsers to check our project works well in them. If we donāt have a Mac, we can still use Safari through one of the many websites that run their instances and display previews, although slowly, for some cost, or even for free. If we donāt have a phone, we can either setup our Android Studio, running an emulated android, or use a website that emulates IOS
, since it is impossible to do on Linux, due to proprietary nature of MacOS
and XCode
.
To go a little bit deeper than that, we can use Docker
to emulate the environment completely to our behest: we can configure a clean Linux distribution with only the packages we want, starting from Alpine and to Arch Linux, or specific environments for our technology, like node:22
. We can also use a Dockerfile
with playwright
installed, if we canāt use it on our Arch Linux. Having setup a small compose.yml
(docker-compose.yml
), we can run the needed services with a simple docker compose up <servicename>
, having complete control unlike installing those on our machine, tainted by the bits of our own machine that we may not be able to control fully, or at least we donāt want to change all the time just for this one small thing.

Approaching problems like that, instead of banging our head against the wall with too much paint on it, helps us focus on whatās important, which is one of the most important aspect of our evolved brains. The world is filled with too much information, too much contradictions, but going one by one, and examining each piece of it slowly, allows us to arrive at a complex conclusion later. The systems that we build now are really complicated, and their complexity is exaggerated by outside factors like business decisions, systems that we do not control and people. When we start blank, we help ourselves and our brain run from chaos, and work out just a little bit of order that can help us stand firm on what we know and donāt know.
Thanks for reading!