Software Engineering Technical Competence Roadmap

Originally posted on my medium page:

Building your technical competence in the world where new technological tools and programming languages emerge daily can be challenging, especially for fresh engineers trying to find their feet in the tech space and build a career for themselves in tech.

I have also struggled with this challenge at a point in my life which prompted me to come with this career path plan.

This article has been divided into four sections:

  • The Fundamentals
  • Software Engineering
  • Selecting a Domain (Web, Mobile, Devops, Quality)
  • Mastering Domain Tools (Programming Languages, OS etc)

I would go through each section to explain its requirements.

The Fundamentals

This cannot be overemphasized, you have to understand the fundamentals if you want to go very far in your career for a couple of reasons:

  • To understand the inner workings of computer systems.
  • Makes it easier to switch from a domain to another if you wish at any time in future.

We have more self-taught engineers than people that did computer science related courses in the university. Many of those who did CS-related courses in the university did not put their minds into these fundamentals back in school. If you fall into any of these two categories, then this section is a must for you.

I followed this resource online and these are the topics and things I learnt from the resources stated on the page:

  • Computer Architecture: How everything in your computer works, you would get to understand boolean logic gates (the fundamentals for information processing) etc.
    Recommendations: The Elements of Computing Systems
  • Programming: This basically helps you understand how abstractions have been built upon the basic arithmetic operations in a computer. Recommendations: Structure and Interpretation of Computer Programs
  • Algorithms and Data Structures: You would learn how the computer executes instructions, how to write fast programs putting memory consumption in mind as well.
    Recommendations: Introduction to AlgorithmsAlgorithms
  • Mathematics for CS: Learn mathematical notations and writing proofs for your algorithms, learn combinatorics etc.
    Recommendations: Mathematics for Computer Science
  • Operating Systems: You would learn how your CPU manages tasks (concurrency etc), and how having multiple CPUs can yield better overall performance (threads etc) but introduce some complications (locking etc). Recommendations: Operating Systems: Three Easy Pieces
  • Computer Networking: Understand how communication is done between computers, networking protocols TCP/IP, UDP.
    Recommendations: Computer Networking: a top-down approach
  • Databases: Learn how data is structured when persisted to disk in popular database engines. Learn about data normalizing in Relational Database Management Systems.
    Recommendations: Readings in Database Systems

Software Engineering

Now you know the essential fundamentals, the next step is to understand the layers in a Software development life cycle and the necessary knowledge you need to have.

The Software Development Life Cycle Includes the following stages:

  • Requirement Analysis
  • System Specification
  • System Design & Construction
  • Testing
  • Shipping
  • Maintenance

These stages are every present irrespective of the development methodology you choose to go with, be it Agile, Waterfall etc.

Here, we would only focus on the stages that involves software engineering: System Design & Construction, Testing, Shipping and Maintaining Your CodeBase.

  1. System Design & Construction:

This depends on the requirements of the system, both functional and non-functional.

Functional requirements describes the users in the system. These include the functions they are allowed to perform and how each user function interacts with other functions.

Non-Functional requirements deal more with the quality of the overall system. Non-functional requirements cover system setup and also areas such as availability, reliability, maintainability, latency etc.

Recommendations: Designing data intensive applicationsPatterns of Enterprise Application Architecture.

2. Testing

This section is all about reducing the number of bugs in your application before shipping to your clients. Testers have to manually test the features/functions before giving the feature a go-ahead. These days, testers now do automated testing instead, they have a test suite they run against new features just to ensure the feature doesn’t break existing features before writing tests for the new feature and adding it to the test suite.

More recently, a new way of developing application evolved called Test Driven Development (TDD). TDD incorporates testing into the design and the construction layer to further improve the quality of the application going to clients. The idea here is to write tests for functions/features first that basically tells what the functions should do. You start with failed tests and work towards making them pass.

Recommendations: Test-Driven-DevelopmentArticle: Unit Testing in JavaArticle: Unit Testing in PHP

3. Shipping

Here is usually handled by the system operators. They write scripts that do the deployments and also ensure there is no down time doing this. There are a couple of tools out there that have been built to help execute this processes seamlessly.

4. Maintenance

Most times, work doesn’t stop after shipping the application to clients, one of the essential qualities of an application in modern terms is its ability to incorporate users feedback to further improve upon it. Having said this, you should design your systems in a way that it is very easy for you and others to improve it. There are lots of the resources out there that can help you design your system to make them highly maintainable.
Recommendations: Learn SOLID principles, Learn Design Patterns (Gang Of Four) and TDD like I mentioned earlier helps in cases where you need to refactor to add new features.

Selecting a Domain.

There are various domains out there, AI, Web, Mobile, DevOps, QA etc.. these domains further have sub-domains. The idea is to try and pick a domain of specialization. This doesn’t mean you are only limited to this domain, after gaining a level of mastery in a domain, it is actually advisable you try other domains so you get a sense of how things work in other domains and how you can incorporate some of your learnings into your main domain.

Devops Resources: Building apps on HerokuGetting Started on Microsoft AzureGetting Started on AWSHosting Static Files on Netlify

Mastering Domain Tools.

After selecting a domain and a subdomain, you need to pick a set of tools that would help in developing applications/systems in that domain. For example in the web domain, there are backend engineering and frontend engineering subdomains. You can decide to focus on the backend engineering subdomain then pick a backend language, there are a couple of backend languages out there: Java, PHP, Go, Scala etc. After picking this, you can further go ahead and add a framework to your stack that would help hasten development. If you choose PHP, there are lots of PHP frameworks out there you can choose from: Laravel, Phalcon, Yii are just some I know among many others.

Having said this, technology is always changing, and some of the skills you have now might become irrelevant in future, the advice here is to have a solid grasp of the fundamentals and be ready to switch domains easily when required.