Ask HN: How would you refactor a big project in 2023?
The current code base is PHP with Symfony 3/4, an Admin based on an open source project that is not really going anywhere and Doctrine as the ORM.
During a refactor that started in 2018 it was over-engineered with 10-20 micro services, Kubernetes etc.
Besides the problem that it takes us very long to put simple things to production as we need to touch 3-8 micro services it is also hard to find good developers for our current stack.
Also, we want to be more independent of developers to add a simple field to the database and have it shown up on the frontend. The research of CMS feels like Bachelor theses.
What would your favorite stack be to start a new project in 2023 where you know that you will have hundreds of thousands of visitors guaranteed per day?
24 comments
[ 2.8 ms ] story [ 64.5 ms ] threadI don't mind spending time and money to refactor everything into a completely new setup that makes us move faster in the next 5-7 years but also enables us to find talent more easily.
Why?
This pretty much sums up our current situation:
https://www.youtube.com/watch?v=y8OnoxKotPQ
Since you're talking about refactoring, which is a stepwise procedure, an early step can be identifying things like these repetitions and consolidating them into a single (or single set) of modules which are referenced by the multiple services. This doesn't fix the deployment problem (needing to redeploy multiple services for a single change), but it can address the code change problem.
This also sets you on the path to a monolith if that's what makes sense for your system or organization in the future since your code will become more consolidated with this process over time. But you can avoid committing to a monolith earlier than necessary, you may find multiple services (micro or mega) are appropriate as you start cleaning up the system.
"We know, for example, that iterating on existing solutions is more likely to improve software than a full rewrite. The dangers of full rewrites have been documented. Joel Spolsky and Stack Overflow described them as “the single worst strategic mistake that any software company can make.” - Kill It with Fire - Manage Aging Computer Systems (and Future Proof Modern Ones) by Marianne Bellotti
you have multiple reference implementations. learn from them.
have better engineers make the attempt.
do it in parallel and only switch over if it’s not worse.
bonus points for multiple competing rebuilds.
2. Update dependencies.
3. Fix bugs.
4. Delete extra code. Remove not needed dependencies. Look are there better smaller dependencies.
Also, just start the refactor because it will help to break analysis paralysis. Just edit the damn code. After some time maybe you will need to throw everything away and maybe start again, but with better understanding of the code.
For the database, I would recommend using a flexible, scalable NoSQL database such as MongoDB or Cassandra.
For the CMS, I would recommend using a headless CMS such as Strapi, which allows for more independence in terms of adding fields to the database and displaying them on the frontend
OTP (i.e. Erlang, Elixir, etc.) would be my default for that sort of load.
Try using "branch by abstraction" [2] to slowly replace this part of the code by a new component (a microservice, perhaps?). Then release that (via a canary if you need to).
See how it goes in prod, and then rinse and repeat.
Trying to make a massive 8 microservice change in one hit is a recipe for disaster.
[1] https://martinfowler.com/bliki/StranglerFigApplication.html
[2] https://trunkbaseddevelopment.com/branch-by-abstraction/ and https://www.branchbyabstraction.com/
Forget the overhead of k8s, forget servers and patching, and ansible and managing VPCs and networks and all that.
Just do the following: Cloudfront, S3-hosted front-end codebase (react, vue, angular, whatever), API Gateway backed by a lambda infra which provides your API, DynamoDB for your databases, and, where needed SQS/SNS between lambdas to fan out workloads. For inter-account messaging, try EventBridge. And then, for auth, go for Cognito*
* Cognito is, in my view, the worst piece of all this -- so, maybe try something else here if you need to (Auth0, or keycloak if you must).
Write the lambdas in Node or Python.
Use SSM Parameter Store as a config management key-value store to configure environments, lambdas etc.
Deploy the lambdas with serverless framework (or terraform).
Build all the rest of the infra with terraform.
Stick it all in a monorepo.