It has been a decade since my first post on the lessons learned. There have been significant changes in the way we work, and tools and techs we use but I can see the lessons I wrote up 10 years ago are still valid. Although it would be better to rephrase them and elaborate more, I’d like to focus more on the additional ones but some will be already overlapping.
Photo by janisfilmt on Unsplash
1. Communication is Key
We, as human beings, understand things based on their image on our mind, and those images are formed based on our knowledge, experience and understanding of the other things before. Even when one says a word like “apple”, it is not the exact same apple in everyone’s mind although there are very common patterns. So, in communication, it is important to be clear and also set a basis on the things to have a shared understanding. Here are some tips I find very useful in this subject:
- Be specific to unprofessional people
- Design the things simple so that they can speak out themselves
- Write code readable even for the future yourself
- Write up points discussed in a meeting and shared with an email/message to be on the same page
- Make your (or your team’s) progress visible
- Make sure everyone has the same understanding of the design or the architecture of the system
2. Deliver Frequently and Fast
It is important to deliver value to the customer as early as possible and get customer feedback to build the right solution and to create business value earlier. Unsurprisingly, these are two of the 12 principles of the Agile Manifesto: “deliver working software frequently, from a couple of weeks to a couple of months, with a preference to the shorter timescale” and “our highest priority is to satisfy the customer through early and continuous delivery of valuable software.”
3. Deliver Minimum
This principle can be achieved by having the ability to deliver frequently and fast but it is important from the point of what to deliver. There are several well-known approaches to this
Minimum Viable Product(MVP) is about creating a version of products with just enough features usable by early customers so that they can then provide feedback for future product development. It also helps to make better and faster business decisions.
Minimum Loveable Product(MLP) is about more focusing on how to delight the customers rather than the bare minimum features to solve their problem. MLP requires more thought on the design of the product so it can take more time but it can be more useful in creating products with delighted customers.
Also, no matter what approach is used, it is very important to prioritize the requirements so that the team can focus on the right thing while helping to reduce wasting time on less important features. The MoSCoW method can be used to prioritize the requirements. Also, it really helps to ask the question: “What happens if we don’t include this feature?” to find out the importance of a feature.
4. Focus on Business Value
Software is useful if it produces a value. If developers are not well aware of the business goals to be achieved by the software and business value they produce, they will not make right decisions in the design, they will not focus on the right problems. They can easily spend a lot of time on something which doesn’t add value such as a feature never to used or a performance improvement not needed at all or refactorings on the area which is not important.
5. Focus on Working Software
Although it is one of the core principles in agile approach and most software people already know about it, I have seen many times that it has been still missed and it can be easily missed when it comes to defining a process. The software that delivers business value is “working software”. Of course, design, documentation, and process are necessary but they are for working software. So, the working software needs to be in the centre of the process, and the process should be revised if it is blocking or slowing down the principle. You might have seen projects, being called “doing in agile way” but it is hard to get a line of code fix into the production, or pull requests piling up and waiting days and days just for review while causing developers chaining the branches.
6. Change is The Only Constant
This simple rule changes a lot in the approach and design. You design systems and build your processes to welcome change: You allow your customer to change their mind or requirements, you create just enough docs also keeping in mind that they will be outdated sooner or later, and your design allows you to analyze the impact of a change, your software can give you feedback of the side effects when a change is applied (via tests), your process can handle delivering changes to the production (continuous delivery ) etc.
7. Avoid The Trap of Fancy And Trending
Don’t use the tools, techs and languages just as they are fancy and trending. It is a trap. Always evaluate their pros and cons in the context of your requirements, and make decisions favouring simplicity.
8. Be Aware of Human Nature
Although we try to be professional and do our job better, we are all human being and come with the nature of human being. This fact cannot be simply ignored. In the contrary, being aware of it and choosing approaches and taking actions in accordance with the fact can help a lot.
- I have seen how reflections such as retrospectives can help the team to motivate and feel more involved.
- Social chat with a demotivated team member can help a lot.
- Showing your understanding of their situation (like busy teammate) and being nice when approaching to the people always helps.
- You cannot measure the performance of the team members using the existing approaches without impacting it.
- Team events can help increasing collaboration, motivation and productivity.
9. Always Hands-on
As developers, team leads and architects always stay hands-on. I cannot imagine a successful software architect making the right ( and good enough) decisions for the system without having hands on the tools and techs. I cannot imagine software architects, sitting in their ivory towers and making decisions on a system without having seen the consequences of their decisions and impact on the system and team. They should be aware of the consequences to use as feedback and also to take responsibility for their decisions/actions?
10. Pay Technical Debt
Usually, the tech debt is ignored since it is not seen as impacting the business directly. But, it has always impact on the quality and the time of the value. Mostly, it has an impact on the long-term. So, handling of the technical debt should be planned and act based on the priority defined by the impact on the business value.
11. Context Matters
Everyone knows “it depends” answer, right?. It is about the context. Each tool and tech has its own pros and cons. For example, one framework can be a good option for a system while not for another one. Because it depends on the requirements and constraints of the system. So, the context defines the boundaries and constraints. Software design is based on a set of decisions made within a context. A decision is about choosing one option while giving up on other ones to maximize the business value while reducing the cost. The context matters in making the right decision. Therefore, it is important for an architect to learn the patterns, best practices and principles, and understand the pros and cons of each relevant tech and tools within their effective context
12. Strive For Technical excellence
Technical excellence means doing things right and well. It reduces redoing things, helps teams to learn repeatable lessons. It also builds confidence in the people you work with and the people deliver, which creates trust.
13. Continous Learning
Software development is an area with rapidly changing. In every a few years, our toolset changes a lot. So, we have to keep learning to do our job.
- Curiosity is the engine in learning so you have to find the things the drives your curiosity.
- There is no excuse for not learning. Find your best way to learn: Read (books, blogs, articles, code) Watch (videos, conferences,) Do (practice!)
- Learn a new language or tools, for example, not only to use it but more to have different aspects in solving problems.
14. Everything is interconnected
In software development, as in the universe, everything is interconnected and it has an impact on the output produced.
- Your understanding of the problem impacts the solution you come up with.
- Your background and experience impact your decisions and design.
- The way you organize your teams impacts the output they produce (Conway’s Law)
- The motivation of your team impacts the quality of the output.
- The culture you build within the team/company shapes the product you deliver, so on.
The list can be extended more and there are still a dozen worth to mention but I wanted not to keep long. I didn’t want to write it at the beginning since most of them are already known and some can be subjective but the first one kinda made me feel that I had to write it. Hope you like it and find it useful.