DEV Community

Fagner Brack
Fagner Brack

Posted on • Originally published at fagnerbrack.com on

The US$4000 JavaScript Interview Question Nobody Could Answer

Imagine being presented with a challenge that could seriously make you earn 0.1 Bitcoin (roughly US$4000 at current rates) for simply answering a JavaScript interview question. A wave of enthusiasm rushes through you until you read the question:

“From ES5 to ES6, was there any one website that would break due to the language update? If yes, which code?”

It wasn't a joke, and I actually had the money ready to transfer.

Fagner Brack on Twitter: "I've been giving hints in multiple places I posted this so people are starting to get closer to the actual answer so the 0.1BTC offer is over as that was only for those who could come up with the answer without hints, now it's easier knowing the wrong answers. / Twitter"

I've been giving hints in multiple places I posted this so people are starting to get closer to the actual answer so the 0.1BTC offer is over as that was only for those who could come up with the answer without hints, now it's easier knowing the wrong answers.

But here’s the catch: the question was never about a binary yes or no response. As an interview question, it was designed to be seen through the lens of tech interviews for business application development, their underlying purpose and their value to the organization.

And so, to much surprise, the correct answer is:

It doesn’t matter

The second question is moot.

Here’s why:

Interviews are supposed to hire new devs who can add more value to the organization. Better yet if they know more than the person interviewing them, that's what allows the organization to grow instead of becoming more of the same. Tech interviews, therefore, should focus on identifying developers who can proficiently code and design software, irrespective of the language, with perspectives that can add more value so the team grows. Instead, most interviews out there favour those who invest their time in learning programming niche specifics that play against real-world scenarios.

Imagine being a carpenter; you should be proficient in the techniques of building a house, not fixated on the brand of the hammer.

Using obscure JavaScript features in a way they could break when transitioning from older to newer language versions is an indication that the domain is too coupled to the language and there's a skill gap in software engineering expertise. The whole premise of the question, in the context of an interview, is misguided.

Unless you’re hiring for a cook, don't set up your questions to embrace those who can make more spaghetti.

What We Learn from The Answers

A series of insightful "great wrong answers" came up during this challenge, and they serve a valuable point. Typically, programming language designers would make breaking changes affecting code rarely used, usually when your domain models are coupled to the programming language.

In the context of an interview, the knowledge that breaking changes exist is fundamental, the specifics are not as it's easy for anyone to spend 5 minutes googling them or looking at the language spec. However, the correct answer is to design systems at the correct level of abstraction, ensuring that such a problem wouldn’t arise. The correct answer is to ensure that a programming language update wouldn’t affect your code by writing simple, long-lasting code designed around Domain Models.

"Probably this company is not for me"

— One the answers that came the closest

For example, take the code below. It's coupled to the programing language Literals and would fail while trying to group based on a prop called 'toString', so it requires crazy hops to fix like the use of Object.prototype.call internally or TypeScript interfaces to limit the prop lookup:

const groupBy = <T extends AnyDomainInterfaceInThisCaseCartItem>(
  cartItems: T[],
  prop: keyof T
): Record<string, T[]> => {
  ...
};
const cart = groupBy(cartItems, prop);
storage.save(cart);
Enter fullscreen mode Exit fullscreen mode

Instead, a decoupled design would be more domain-specific like this (in an object-based paradigm):

const cart = ShoppingCart(config);
cart.addItem(cartItem);
storage.save(cart);
Enter fullscreen mode Exit fullscreen mode

Or this (in an immutable functional-based paradigm), using the principles of state = fn(command, state):

cart = execute(addToCart, cart);
storage.save(cart);
Enter fullscreen mode Exit fullscreen mode

NOTE: The examples above are NOT extensive, there are many ways to decouple Domain Models from the language, but those are just two out of many possible ways of doing this for the domain of e-commerce; there are tradeoffs on each approach. Regardless, the Domain Models will evolve over time and the final result tends to be much more specific than my examples, depending on which "kind" of e-commerce subdomain you're operating on. That's why many frameworks don't work together with Domain Models, they lock your code to the framework's domain, not your application's domain.

In the examples above, can you see how the "groupBy" function has absolutely NO domain information other than variable names? The encapsulated function is too generic, designed for general reusability (excessive DRY), and relies upon primitives (Primitive Obsession) as the function is coupled to an ArrayLiteral of ObjectLiteral, (Array[] for short). None of that has any meaning whatsoever in the context of e-commerce, only for those who contribute to an Open Source library like Lodash. In the context of application development, the model is too generic; it has no value.

Ironically, those who provide complex interview answers or delve into very cryptic, underground knowledge about the language are often those who perform poorly in overall software engineering; yet, they're easier to get hired because the market is optimized for {TrendyStuff} roles. They focus excessively on language, frameworks, or technology, failing to comprehend that these elements constantly evolve and code that is coupled to them is a liability.

As an interviewer, when you interview based on such grounds, you end up hiring people who think the same way, fostering groupthink, hindering innovation, and preventing the dissemination of knowledge of software design. Ultimately leading to a higher-than-necessary cost of development.

Hiring based on technology skills foster groupthink, hinder innovation, and prevent dissemination of software design knowledge.

This is the reason why most companies struggle to hire someone better than their existing workforce: they will test candidates against what they believe to be valuable, even if one can just google or write a test to check how the code works; not against an actual domain scenario.

It eventually leads to layoffs, which is a reaction of organizations to the constant production of low-value software and infinite rewrite cycles. The irony is palpable when software engineers who have experience with Domain Modeling and software design fail an interview crafted by programmers who don't understand any of that. That happens even when those interviewers bear the title of Senior or Principal/Staff Engineers, which happens more often than not.

What can we learn from all this?

So, as we look back at this exciting challenge, it’s clear that the real lesson lies not in knowing the intricacies of JavaScript’s evolution. It is in understanding what truly matters when it comes to hiring staff for the purpose to build competent, successful, adaptable and innovative software engineering teams. Those are things most people don't know how to do, as proven by the many attempts to answer this question in the context of the JavaScript language.

Just like some devs lost the opportunity to win US$4000 here, organizations are missing the opportunity to turn millions due to their outdated tech interviewing practices.

So here's one variation for a great answer to the original question:

It doesn't matter.

If the code breaks after an ES update it will probably break after a framework or library update and it will be hard to fix; depending on how coupled things are, we may have to rewrite the whole application. That also means the code is too smart and doesn't provide real-life value to the organization.

I would design the code in such a way the domain is not coupled to the programming language, frameworks, libraries, etc. Therefore, updates or specific language/framework/libraries idiosyncrasies are NOT likely to break my code. In the rare cases where it does, the domain is encapsulated so third party code is easy to fix.

Also, you might be able to easily hire programmers from other programming language communities who can perform with minimal quality impact, as long as they understand the fundamentals, patterns and paradigms of software engineering and domain modeling.

THAT is the answer.

Domain Modeling skills for application development (such as Domain-Driven Design), obliterate the need for engineers to learn 90% of the features of any programming language or framework. In that context, interviews about the language make absolutely no sense. If the intention is to assess whether the engineer will perform in the organization technically, the question is wrong. They should assess basic patterns of the core paradigms, not cryptic underground language syntax puzzles.

That's why tools like HackerRank are the worst thing to ever happen in modern times to the software engineering industry.

The right answer, in the context of qualifying a developer against application development experience, is to change the question…

… because after all, The Problem You Solve Is More Important Than The Code You Write.

Unfortunately, we all know other fellow programmers interviewing that person will lack the skills to understand the whole premise of the answer, which is to create software that has BUSINESS VALUE. The interviewer will fail the interviewee probably for being scared of the unexpected answer, even if they have the ability to adapt to a less-than-ideal scenario.

If an organization knows how to engineer good software, the only outcome for the interviewee should be: Congratulations, you passed!

Unfortunately, those organizations (including teams within big ones) are very rare. I have been fortunate enough to work with a few of them in my career.

And you, what was your experience in tech interviews?

If you know an organization that would be friendly to valuable software development without forcing good engineers into a management role, I'm open to work. Get in touch with me via LinkedIn!

In the meantime, happy tech interviewing!

Thanks to Igor J. Santos for their insightful input on this post.

Thanks for reading. If you have feedback, contact me on Twitter, LinkedIn or Github.

Top comments (0)