Each week I write a blog post which describes what I learned that week. I write these blog posts for two reasons.
First, I want to keep track of my personal development and writing regular blog posts is a great way to do it.
Second, I want to share my findings with you. I hope that you can use some of them in your daily work.
Let’s get started and find out what I learned in week 35.
What I Learned in Week 35
First, Sometimes (most of the time) reading reference documents IS NOT a waste of time. This week I was working on my Spring Social example application which demonstrates how we can integrate Spring Social 1.1.0 with Spring Security 3.2.
My progress was really slow because I didn’t pay any attention to the reference manual of Spring Social 1.1.0. Because I learn by doing, I could not control my urge to start experimenting right away. It was fun but it caused a lot of frustration as well.
At some point I decided to read the reference manual and noticed that it answered to the questions I had in my mind. I know that real men don’t read manuals but if you want to get the job done as fast as possible, reading the manual is the only way to do it.
Second, Logging matters. This week I was adding an interesting new feature to an existing application when all hell broke lose. I got a call from a customer who told me that our application is not sending email notifications.
I dropped everything I was doing and started reading the logs. I was pretty confident that I could figure out what the problem was because I knew that this application writes a lot of stuff to the log.
Well guess what? I found out that sometimes writing a lot of stuff to a log file is not enough. You have to also think about what you write to the log file.
The biggest problem was that I had no way to track the execution of the process which triggered an email notification. That is why I could not find the root cause of the problem.
When I was investigating the issue, the email notifications started to work again but I knew that my work was not over. I need to make improvements to the logging of that application. I will start by reading the 10 Tips for Proper Application Logging.
You should do the same.
Third, One product. One master. Each product should have only one person who has the final say on every non-technical decision made during the project. This person should listen to the opinions of other people but he must not ask other people make decisions for him.
He should remember that
- Shared responsibility is nobody’s responsibility.
- Each person has a hidden agenda. This agenda might not be the same than the best interest of the product.
If you are a product manager, project manager, or a product owner you must OWN your product. You must have a VISION about the product and the GUTS to make decisions.
In the end, if the product fails, your neck is on the line. Are you sure that you remember this?
Fourth, Don’t build objects without adding meaning to the process. I am a big fan of the builder pattern because it helps me to create objects without using the telescoping constructor (anti)pattern. When I started using the builder pattern, I followed these two rules:
- The property values of required properties were passed as a constructor argument to the builder.
- Optional property values were passed by using the methods of the builder class.
However, I soon realized that many classes (especially domain model class) have too many mandatory properties. If I would have followed the rules described above, the constructor of my builder class would have followed the telescoping constructor (anti)pattern.
I solved this problem by modifying those rules. My new rules were following:
- The "essential" property values were passed as a constructor argument.
- All other property values were passed by using the methods of the builder class.
Then I ran into this these two questions:
- What is essential?
- If something is so essential, shouldn't I describe what it means?
The problem of my second set of rules was that the essential property values can be sometimes tricky to find. Also, the second question really bothered me. Although the constructor of my builder class had typically only a few parameters, it could be confusing.
Then I read this blog post by Blake Caldwell.
I realized that the I could set all property values by using methods of the builder class. This way I could create a DSL which describes the construction of an object and improve the readability of my code.
Remember that object creation is not a meaningless process. There is a reason why we create all these objects. Shouldn't we make this reason clear to anyone who reads our code?
Fifth, do you know which method threw the exception? If you are writing unit tests with JUnit, you can use the expected attribute of the @Test annotation to specify the exception which is expected to be thrown during the test. This approach has two problems:
- You can only check the type of the of the thrown exception. Sometimes it is helpful to analyze the thrown exception a bit further.
- If the tested method uses more than one external dependency, you cannot verify which method threw the exception because the execution of your test method is stopped when the exception is thrown.
The catch-exception library solves both of these problems. I started using it right away and I recommend that you do the same. It is an useful addition to the toolbox of any developer.
What Did you Learn This Week?
Share your learning experiences or other comments on the comment section.