Escaping output does not always work when, e.g. you have thousand of integrated systems and don't control any of them nor their upgrades.
If you don't filter malicious inputs, they will forever live in your database and it takes one bad release of some reporting tool somewhere for your users to become vulnerable.
If you rely on sanitizing before storing, you can end up with data in your database that somehow missed being sanitized, or is maliciously entered in your database.
You must escape the outputs, no matter how hard you try to sanitize the inputs. Losing "control" of any integrated systems means your system is vulnerable, even if only to someone at a terminal typing things into the DB manually.
Of course you must escape your outputs, get in-depth layers you don't even need now, track how data flows in your application, patch every known vulnerability, sandbox every single thing, implement capability - based security, and many more. I didn't mean otherwise.
Filtering input is not sufficient. But it is not optional.
Yes, it does. The only exception is if there is no way to represent a given value in the language that you speak to another component, but then you either need to reject the request or sanitize on output (if you can be reasonably sure that doing so won't break the semantics of the information that you are passing on).
I've worked on systems so shitty that some input was triple-escaped so that it would trickle down three unescape layers in old buggy clients deployed to the field.
The thing is, there's no wisdom to take away from this monstrosity. It's just old shitty legacy ad-hoc code. The grandparent post thinks there is.
That you might need to break every rule in the book to integrate shit-tier software doesn't need to be said when talking about software best practices.
Escaping input is of course path to nowhere, because you never know what kind of context your data will be displayed in. So, you cannot guess proper escaping rules.
Escaping data on input is novice mistake. Not having unfiltered data, reject data not conforming to some rules, so you know exactly what to expect getting you somewhere.
You can bake checks and constraints into your database model too if it is needed.
If you don't filter malicious inputs, they will forever live in your database and it takes one bad release of some reporting tool somewhere for your users to become vulnerable.