A rewrite is a migration problem wearing a coding problem's clothes.
The questions people ask first (new stack, timeline, test coverage, feature freeze) all assume the work sits in producing the new system. The work sits somewhere else: proving the new system behaves like the old one on inputs that were left undocumented.
So I put this one ahead of those: can both systems process the same request, and can you diff the results?
If yes, the rewrite gets incremental and boring. Route a slice of real traffic to the new path, keep the old one authoritative, compare outputs until each difference is either explained or fixed. Each discrepancy is a free bug report from production.
If no, you are committing to a flag day. And flag days fail on the undocumented parts of the legacy. In Python 2 to 3 migrations and monolith-to-services rewrites, the surprises were rarely syntax or service boundaries. They were implicit behaviors encoded in data: rows that violate the constraint the model claims to enforce, encodings that only show up in records written years earlier, branches kept alive by a single caller.
Three follow-ups matter more than the stack choice. What is the rollback unit: one request, one user, or the whole service? Who owns writes during the overlap, and can anything double-write? What reconciliation tells you the two systems agreed, rather than that neither crashed?
I wrote up how I sequence this kind of migration here: https://polycratia.com/c/f086e021
If you have run a parallel-run migration, I want to hear what the diff caught that your test suite never did...