This article is not aimed at criticizing anybody.
The sole intention is to open up and share the thought process of someone like me as a mean to possibly help others out there to be more understanding of what might be going on within their respective teams.
Within a team environment, striving to push things forward can lead to exhaustion and a feeling of alienation.
Design Constraints and Creativity
Let’s talk a bit about food and imagine for an instant that we, a bunch of die-hard fast-food eaters, were to decide to:
- exclusively cook unprocessed food to gain control over what we eat.
- not use any refined sugar to avoid all sort of health issues over time.
- become vegans because we’d want to help animals.
That’d be quite a drastic change in our habits all of a sudden, wouldn’t it? Quite the challenge even—with these three constraints in place, we’d have to:
- change how we think about food.
- invest more time and energy instead of picking the easy way out.
- become creative to replace the ingredients that we grew used to.
- accept failure.
- be perseverant.
But look at the upside! Beyond that initial hurdle, some rewarding, healthy, and mindful food awaits!
Such well-justified constraints can have a similar beneficial impact when designing new tools, workflows, pipelines, APIs, and just about any product, really.
For example, I know for one that if I get to design such a product then I won’t be satisfied until the result is:
- comprehensive and frictionless for the end users.
- simple in its concept so that it should be easy enough to explain and extend.
- implemented with seemingly little to no technical debt so that it can be maintained without much hassle.
And that’s where constraints can help.
To achieve these ideals listed above, I always start my designing process with imposing upon myself a bunch of guidelines that I need to stick to no matter what.
Here are some examples of such constraints:
- developing in C to go back to a more fundamental style of coding, where I am not tempted with a myriad of abstractions that do nothing but obfuscating the code (trivia: you’ve got C++, the rule of five, and you’re reading a line of code that initializes an object—guess which constructor gets called).
- keeping the dependencies to a minimum so that projects are easier to deploy, are less likely to break due to non-backward compatible changes upstream, and have shorter code paths since they don’t go through layers and layers of abstractions where each add a potential point of failure.
- avoiding to use the
#includestatement in header files to speed up compile times.
- clearly separating any UI code from the API logic so that there’s no coupling between them and it’s easier to reason about.
- reducing dynamic memory allocations because it’s slow and fragments data in memory.
- making front-end operations work intuitively, without much learning curve required from the end users.
- avoiding the need to handle special cases differently.
- enforcing a single way of doing things to streamline front-end operations without being limiting.
- ... and so on!
I would like to point out that none of these constraints are about over-engineering—they all focus on improving either the user experience, the performance, or the maintenance aspects.
This doesn’t sound like too bad of an idea to approach things this way, right? So what’s wrong?
Path of Least Resistance
Like with our previous food example, the cost for these improvements now needs to be paid upfront by the creators. It requires to change how we think, to invest more time, to be creative, and to often walk an uncertain path where we’re not too sure whether we’ll successfully manage to make things work or not.
In other words, making things simple ain’t easy.
But challenges are fun and I’m personally looking forward to making my own work more difficult if this translates into a better product and happier end users over the long term.
And that’s what I assumed everyone would also opt for, at least in an ideal world.
However, over the years, I came to realize that the vast majority of people somehow prefer to pick the ‘easy’ path. Even when given the chance to rebuild a product from scratch, most would choose to reapply the same old recipes that they’re familiar with, while attempting to patch some bits here and there. Not many seem interested in questioning the status quo, in exploring a problem from a truly novel angle, in striving for something even greater.
And that’s fine. With the reality of today’s productions and deadlines, it’s not as if one approach is necessarily superior to the other. It’s more alike to a compromise between getting things out quickly and then paying the cost later through increasingly more challenging maintenance tasks, or releasing at a later date to spend more time on the designing phase in the hope that the product will age better.
Despite both approaches being valid, there are times where we can be really, really, confident about a certain direction needed to be taken because the benefits are too great to be let go. The choice is obvious. We know everyone would surely agree that it’ll be worthwhile putting in a bit more efforts to avoid a given pitfall. And yet, here we stand, powerlessly witnessing a different proposal being supported despite our best efforts at recommending against it. Almost like a sabotage to our best intentions.
Not sharing an ideal or a vision with someone, is one thing. Not sharing these with a whole group and being the one who thinks differently, it’s tough.
It’s as if we didn’t belong there...
I believe that it is crucial for us, humans, the social species that we are, to be able to create relationships with like-minded people, to have at least one person in our surrounding who is genuinely aligning with our ideals, someone who just gets it.
In itself, this desire is also a manifestation of the path of least resistance. Instead of expanding energy to try to articulate and justify each idea in front of an opposing group, and be left exhausted and saddened because it was all in vain, a synergy with like-minded people can be invigorating and inspiring. It can push each individual to bounce ideas back and forth, to strive together towards a same objective, to grow.
Like everything in life, there needs to be a balance. There is definitely a place for opposing forces to helps us reassess our ideas, but we also need positive ones that lift us up.
As a result, being a perfectionist who’s deeply driven by the will of helping to improve things while at the same time being exclusively surrounded by people who do not share the same fundamental ideals is, unfortunately, a cocktail that turns out to be fairly unhealthy.
When I face such a situation and that all my attempts at persuasion have failed, I find myself losing motivation and assuming that it’s after all my fault for caring too much.
At this point, my usual course of action is to:
- distance myself as much as possible from work.
- stop sharing my inputs to avoid any disagreement.
- remind myself that I’m still fortunate to have a cool job in a cool team.
- tell myself that probably not many people in our fast-paced society get the satisfaction of following their vision at work neither.
- find solace by focusing on my own projects where I just get to do some work the best I can, without anyone interfering with my ideals.
- let some time pass until I heal and am ready again to give it another shot.
This sensation of alienation and how I unprofessionally handle it makes me doubt real hard about me being a good fit for any given team. And for someone who has more often than not been giving his all to push things forward, and to share his knowledge, that sucks big time.