There are at least a few development rules we are always aware of at Functionite while working on the JavaScript applications. We have picked 5 of them to show what we have learned over the last couple of years that makes our code way more maintainable.
Always stay conservative
We believe that removing code is better than adding it. Being adventurous in writing new functionality is often looking for troubles by introducing another level of complexity. Instead, we should measure our code quality by how many lines we removed or how little code we’ve added. Never the other way around.
We strongly recommend reading this nice write-up on Programming Is Terrible blog– http://programmingisterrible.com/post/139222674273/write-code-that-is-easy-to-delete-not-easy-to — on how to create code that is easy to delete.
Avoid fat views
Another thing everyone should avoid is implementing a business logic in the views. It always puts our application off the track so it becomes unmaintainable in the long run. In MVC design pattern it’s a model who keeps the business logic and never a view. Let’s take a look at the following example in which a view removes a single model, which in turn is linked with the other items that also should be removed:
View that contains such part is often called a fat view. It means it is implementing a lot of unnecessary business logic whereas it should have a single responsibility. In the above snippet, the view is responsible not only for calling remove function on the model, but also for removing otherThings from that model. It makes the code harder to test and maintain.
In order to write some unit tests, we’d need to test both the view and the model, instead of just the model. This is a sign that something is wrong. Code that removes otherThings should be put into remove method in a model.
Make your errors informative
For a programmer who works in a dynamic environment (like startups are) it’s always tempting to skip checking your functions’ input or the conditions required to make an algorithm work. In fact, we should go a little overeager and throw errors wherever it may occur important to quickly debug an app:
As you can see, it’s worth including information about which function (and/or module) failed and what a given input was. It makes debugging faster and environment-independent.
Return early
We believe also that it is a more effective strategy to return a value early instead of wrapping it in long if else statements. Having the code below:
we should have failed early and remove the else part making the code more readable:
Now, this is a way more readable, allowing us to keep the edge cases at the beginning of the file, so we don’t have to switch between if/else branches.
Avoid logic in if statements
If we do program using OOP style, we need to be aware of reducing a logic put into switch or if statements. It’s a very similar case to what the fat views case is, showing that our object structure may have been better thought. What is it about really? Let’s consider the following code:
What happens here is that in a single makeWords function we do certain actions like setWord or sayIt depending on the model’s type. Now, what if we add more types in a future? Will we have to keep adding more corresponding else if statements in makeWords function, which can be placed in a different package or module? It would make our code verbose and hard to maintain as we would need to always synchronize that function with the current state of models’ code.
Instead, we should encapsulate makeWords logic for each model type so they can decide individually what to do when makeWords is called:
This is just a tip of the iceberg of examples showing when you can make your code easier to maintain. Hungry for more? Follow us on Twitter where we often tease our work and visit our website to get in touch.