The project had good test coverage. The main issue I had working in that codebase was never reliability, it was documentation. It's simply harder to read code that doesn't have types annotated. It takes longer to figure out what the shape of some certain data is, or is supposed to be.
Separately from that job, I've also worked with 1M+ LOC codebases in Ruby as well as Python. The Ruby codebase was statically typechecked with Sorbet and the Python with mypy. Big improvement to developer experience IMO.
It's common to ask, "why even use Ruby/Python and then typecheck it anyway?" But that question misses the point. The power of dynamic languages, in my opinion, isn't really that the types are dynamic. Rather, it is that the environment is dynamic. One thing this unlocks is that types and functions are just values and can be freely inspected, and created, at runtime. Another is that you can attach a REPL to a running system and inspect and debug it, live. Both of these allowed us to develop features and solve problems at a greater velocity than if we'd been working with a more static language.