Good enough, is Good enough!

WhiteFish Creative Ltd
8 min readJul 5, 2023
Good enough, is Good enough, perfection is just the first stop to failure

In the fast-paced world of software development, time-to-market and efficiency are crucial factors that determine success. While many developers strive for perfection, the reality is that perfectionism can hinder progress and impede timely delivery.

In this article, we explore the notion that prioritisation, practicality, and timely delivery should take precedence over perfectionism. We’ll delve into the importance of test coverage, delivering working features, handling system replacements, and maintaining a focus on delivery rather than being overly concerned with the latest technologies or code intricacies.

Test Coverage on Complex Code:

In certain scenarios, such as when rushing to release a Proof of Concept (PoC) or striving to be the first to market, prioritising unit testing, end-to-end testing, and integration testing may take a back seat to manual testing. While comprehensive testing is crucial for software quality, it’s important to acknowledge that time constraints and market demands can sometimes necessitate a different approach.

Instead of aiming for 100% code coverage across the entire application, a more pragmatic strategy involves identifying the complex and critical code segments that are most susceptible to errors. By focusing testing efforts on these areas, you can achieve robust test coverage without excessive time investment.

This selective testing approach mitigates risks and ensures the stability of the application’s core functionality. By prioritising thorough testing in the key areas, you can address potential vulnerabilities and verify the correctness of critical operations.

It’s worth noting that while this approach may be appropriate in certain situations, it’s essential to revisit and enhance test coverage as the product evolves and stabilises. As the PoC transitions into a full-fledged product, dedicating more time and resources to expanding the testing scope becomes imperative to maintain a high level of quality and reliability.

While comprehensive testing is a fundamental aspect of software development, there are instances where prioritising specific code segments for testing can be more efficient and aligned with project goals. Balancing time constraints, market demands, and criticality of code segments allows for a pragmatic testing approach that ensures the stability and reliability of the application’s core functionality.

Delivering Functional Features:

When striving for efficient software delivery, it’s crucial to prioritise the development of features that align with the client’s needs. Rather than aiming for every feature to be fully complete and feature-rich, the focus should be on delivering the core functionality that is essential to the client.

This pragmatic approach offers several advantages. First, it enables quicker iterations, allowing for faster feedback loops and the ability to address any issues or enhancements promptly. By focusing on the core functionality, developers can deliver a functional product sooner, reducing time to market and enabling the client to start realising value from the software without unnecessary delays.

Additionally, this approach promotes a more efficient use of resources. By prioritising essential features, development efforts are concentrated on what truly matters to the client, avoiding the investment of time and effort in less critical or non-essential functionalities. This streamlines the development process and optimises resource allocation.

By delivering the core functionality early on, clients can begin utilising and benefiting from the software sooner. This allows them to gather user feedback, validate assumptions, and make informed decisions about future enhancements or iterations. It fosters a collaborative relationship between the development team and the client, as they work together to shape the product based on real-world usage and needs.

Prioritising the development of essential features over complete feature richness is a pragmatic approach to efficient software delivery. By focusing on the core functionality, development cycles are shortened, resources are utilised effectively, and clients can start reaping the benefits of the software sooner. This approach sets the foundation for iterative improvements and client-centric development, driving value and satisfaction for all stakeholders involved.

Phased System Replacements:

When replacing an existing system, the aim should be to retain all essential features without any loss, the key being essential features. This can be accomplished by conducting a thorough assessment of the feature set of the current system and devising a strategy for either providing replacements for all features or implementing a phased replacement approach.

By breaking down the system replacement into manageable chunks, the transition becomes smoother, minimising disruption for the end-users. This approach allows for a systematic migration from the old system to the new one, ensuring that all essential functionalities are accounted for and effectively transferred.

Careful planning and coordination are key in this process. The assessment phase involves identifying the critical features of the existing system and determining how they will be addressed in the replacement. It may involve developing equivalent functionality in the new system or finding suitable alternatives that meet the same objectives.

For a seamless transition, a phased replacement approach can be adopted. This involves prioritising features or modules based on their importance and replacing them incrementally. By taking this approach, the risks associated with a complete system overhaul are mitigated, and end-users can adapt to the changes gradually.

Throughout the replacement process, effective communication with stakeholders, including end-users, is vital. By involving them in the planning and providing clear expectations, their concerns can be addressed, and any potential disruption can be minimised. User feedback and testing play a crucial role in ensuring that the replacement system meets the needs of the users and delivers the expected functionality.

When you look to take on a project of replacing an existing system, it is essential to retain all essential features. This can be achieved through careful assessment, planning, and a phased replacement approach if necessary. By breaking down the transition into manageable chunks and involving stakeholders in the process, the replacement can be executed smoothly with minimal disruption to the end-users.

Prioritising Delivery:

The ultimate goal of software development is to deliver a functional product to the client. While technological advancements and elegant code are admirable, they should not take precedence over timely delivery. The client values a product that meets their needs and delivers value to their business. Therefore, developers must prioritise delivering working features within reasonable timelines rather than getting caught up in perfecting every aspect of the codebase.

It is important to strike a balance between code quality and meeting client expectations. While clean and well-structured code is desirable, it should not come at the expense of timely delivery. Developers should focus on implementing the necessary features and ensuring they work as intended, rather than aiming for perfection in every line of code.

By adopting an agile development approach, developers can deliver incremental releases that provide tangible value to the client. This iterative process allows for regular feedback and course correction, ensuring that the end product aligns with the client’s evolving needs.

Effective communication and collaboration with the client are crucial. Regular updates, demos, and transparent discussions help manage expectations and ensure that the development process remains aligned with the client’s priorities. By keeping the client informed and involved throughout the development cycle, developers can deliver a product that meets their needs and delivers value.

The primary focus of software development should be on delivering a functional product that meets the client’s needs and delivers value to their business. While code quality and technological advancements are important, they should not overshadow the importance of timely delivery. By prioritising working features and maintaining effective communication with the client, developers can achieve the ultimate goal of software development.

“Good Enough, is Good Enough” Mentality:

I have a mantra “good enough, is good enough”, embracing the mantra is vital for achieving efficient software delivery. When a feature meets the agreed-upon requirements and delivers the necessary functionality, it is considered sufficient to be released. Adopting this mindset enables developers to avoid the pitfalls of perfectionism, which can cause unnecessary delays and impede progress. By prioritising reaching an acceptable level of quality, developers can swiftly transition to the next task, ensuring a continuous flow of deliverables.

This approach to software development promotes a balance between quality and speed. Rather than endlessly striving for perfection in every aspect of the codebase, developers focus on delivering functional solutions that meet the immediate needs of the client. It allows for quicker iterations and ensures that valuable features are delivered in a timely manner.

By adopting the “good enough, is good enough” mentality, developers can avoid getting stuck in an endless pursuit of perfection. Instead, they can channel their efforts into delivering tangible results and meeting project milestones. This mindset encourages efficiency, enabling developers to deliver more, faster.

Ultimately, the key is to find the right balance between quality and timely delivery. By recognising when a feature meets the necessary requirements and functional criteria, developers can maintain a steady pace and ensure a continuous flow of value to the client. Embracing the mantra of “good enough, is good enough” paves the way for efficient software delivery and drives progress in the development process.

Remember, in the fast-paced world of software development, always good enough is truly good enough, unless you’re working on software that could kill someone, then perfectionism is definitely the route for you there.

Efficient software delivery requires a shift in mindset, emphasising prioritisation, practicality, and timely delivery over perfectionism. It’s like finding the perfect balance between speed and quality — kind of like riding a unicycle while juggling code!

Ensuring test coverage on complex code, delivering functional features, and handling system replacements are all part of the software development dance. It’s about gracefully pirouetting through the development process, making sure to keep your eyes on the prize: delivering valuable software on time.

Maintaining a focus on delivery means strapping on your developer boots and getting things done. No time for twiddling thumbs and waiting for the muse to strike! It’s about embracing the “good enough, is good enough” mentality and knowing that sometimes “perfect” can be the enemy of progress.

Navigating system replacements requires the finesse of a tightrope walker. By carefully assessing existing features and devising a plan to provide replacements or phasing them out, you can ensure a smooth transition that won’t leave your end-users hanging.

In the end, it’s all about meeting client needs and delivering tangible value. Remember, software development isn’t a one-man magic show — it’s a team effort. So grab your coding wand, strike a pose, and let’s deliver some awe-inspiring software that makes clients say, “Wow, this is exactly what we needed!

In this ever-evolving world, embracing these principles will help you keep pace with the market’s dynamic demands. So, let’s put on our development hats, turn on the “get things done” playlist, and deliver software that truly matters.

If you’re ready to bring some efficiency and a dash of humour to your software development projects, reach out to WhiteFish Creative or James Studdart. We’re here to juggle your development challenges and deliver results that will leave you standing ovation-worthy!



WhiteFish Creative Ltd

James Studdart: Bespoke software solutions, in .Net, Flutter, Python, C#, JS, and designs. A popular podcast host.