Each function or method should operate at a single level of abstraction. This means that a function should only do one thing at a specific level of detail, making the code easier to understand and maintain.
Instead of leaving an empty state, like when there are no contacts or messages, consider adding a call-to-action button to engage the user. This small addition can capture their attention and encourage them to interact more with your app.
High-level modules should not depend on low-level modules, but should depend on abstractions. This encourages the decoupling of components in a system, making it more flexible and easier to maintain.
Classes should be open for extension, but closed for modification. You should be able to add new features or behaviors without changing existing code. This keeps things flexible and prevents breaking existing functionality when adding new stuff.
A class should have just one reason to change, meaning it should focus on a single responsibility. This keeps the code clean and maintainable, making it easier to understand, test, and extend.