Jaff Parker
10 May 2021
•
4 min read
This is the first installment in a series of articles of indefinite length.
Throughout the years of working in various teams and building one, I have grown to appreciate code quality more than the actual tooling that the team uses. It doesn't matter what language you write in or what framework you use, anyone can get on board, if your code matches certain quality standards.
I want to share my experience to help startups out there expand their hiring pool by making their codebase easy to read and comprehend.
What on Earth am I talking about? Is it a sufficient amount of // comments
? Maybe it's an abundance of s p a c e s
? Indentation? Documentation?..
All of those are important, if done right. If you have ambiguous code, add clear comments to it. You do need to make sure your indentation and spaces are consistent. And you sure should write docs from the beginning (that might just be an article in this series).
In this post though I will talk about English. That is, the language. Spanish or Chinese can work too, but they'll highly limit your hiring pool, so English it is.
In most languages humans use nouns to identify objects and verbs to express actions on those objects. That's how we read English.
If we start substituting verbs and nouns, it becomes literally impossible to understand the meaning of words. Here's this sentence with verbs and nouns swapped:
If we beginning substitution verbs and nouns, it start literally impossible to understanding the mean of speak.
The hell is this, right? I wanted to carve my eyes out writing that.
So why would we write code like this:
function user() {
return {
id: '1',
name: 'Mr. Poopy Butthole'
}
}
if (user()) {
const gottenUser = user()
}
This doesn't make sense in human language. This is not how we read sentences. While this is a small example, if you have an entire project written with such disregard for human language grammar, it will quickly become confusing. It will take you much more brain power to keep in mind what's what.
How I would fix that code:
function hasUser() {
return true
}
function getUser() {
return {
id: '1',
name: 'Mr. Poopy Butthole'
}
}
if (hasUser()) {
const user = getUser()
}
What did I change?
First, I introduced a new function for the if
statement. It returns a boolean, which makes it clearer in itself, but also the name indicates that it returns a boolean. How? Try and make it a question: Has User? The answer is yes or no - boolean!
Second, I renamed the user()
function to getUser()
. Since functions are actions, it is only appropriate to use verbs for function names.
Third, I could use the now-available noun for the variable. That again makes more sense, since variables are objects, thus should generally be nouns.
Try to read that code like English now. Can you quickly understand what's happening? I don't doubt you do.
One Rule To Rule Them All:
You must be able to read your code like English the day after.
If you can't, you screwed up, redo it.
Now, I'm not saying that you have to keep writing and reading and re-writing and reading and re-writing ... until it feels right. There's a pretty clear set of rules that'll help you get it right. In fact, these rules will also help you have clear separation of concerns, which is just a win-win! Here we go:
Avoid function names such as user()
or post()
, especially avoid the temptation to make them handle the entire CRUD. Instead, introduce actions on objects: getUser()
, addUser()
, modifyPost()
, deletePost()
. Right away you see what each function does.
This is a tricky one. Always include everything your function does in the name. If your function creates a user and sends a welcome email, name it createUserAndSendWelcomeEmail()
. You might see even with 2 verbs this is getting long. This is a sign for you to split it into 2 functions: createUser()
and sendWelcomeEmail()
. Then you can emit an event from createUser
that sends a welcome email.
This achieves 2 goals. First, it makes obvious what your functions do. Second, it forces you to split your functions by concerns and keep them short!
Your variables contain data, or objects, which in English are described by nouns. Thus, to make your functions that act on your variables (objects) clear, your variable names have to be nouns. users
or posts
are acceptable.
With that in mind, always include relevant adjectives in your variable names, especially if you have more than 1 with the same data type in one context. For example, you fetched all posts and then filtered the ones written by Mr. Poopy Butthole. Instead of having posts
and posts2
, you should have allPosts
and postsByPoopy
. It makes a huge difference!
These rules are foolproof. Follow them and you will inevitably produce readable code.
How about a bad and good example of these rules?
// ❌ BAD
function users(id) {
if (id) {
return userByIdFromDatabase(id)
} else {
return allUsersFromDatabase()
}
}
function posts(post, userId) {
if (!post) {
return allPostsFromDatabase(userId)
} else {
return updatePostInDb(post)
}
}
const user = users('1')
const postsFromDb = (null, user.id)
const posts2 = posts.filter(post => post.author === 'Mr. Poopy Butthole')
posts2[0].title = 'I write bad code'
posts(posts2[0])
// ✔️ GOOD
function getUserById(id) {
return getUserByIdFromDatabase(id)
}
function getAllPosts() {
return getPostsFromDatabase()
}
function updatePost(id, post) {
return updatePostInDatabase(id, post)
}
const user = getUserById('1')
const allPosts = getAllPosts()
const firstPostByPoopy = posts.filter(post => post.author === 'Mr. Poopy Butthole')[0]
updatePost(
firstPostByPoopy.id,
{
...firstPostByPoopy,
title: 'I write good code!'
}
)
What a difference! The first example is impossible to read in English, function names are ambiguous and do not reflect what they do. The second example is totally different though! The functions and their purposes are clear, each variable is understandable and I'm sure it takes you no time to read.
As I mentioned in the beginning, I have been a part of different teams and have built one. Having readable code helped us each time to hire good developers that don't have experience with our specific tools (which is especially important in JS with its variety of standards and frameworks). Approaching code like human language will allow your new developers to spend time being productive instead of trying to understand what you wrote.
Do you have any other good readable code practices? Let's discuss it in the comments!
Jaff Parker
See other articles by Jaff
Ground Floor, Verse Building, 18 Brunswick Place, London, N1 6DZ
108 E 16th Street, New York, NY 10003
Join over 111,000 others and get access to exclusive content, job opportunities and more!