At some point an old PHP version, an old database or an old API of your own becomes a weight. Deciding when to drop it is a judgement, but there are better and worse ways to make it.
Follow the platform, not your preference
When a language version stops receiving security updates, that is a defensible line. You are not dropping support for people, you are declining to support something unsafe, and that is a reason a buyer accepts.
Announce it one release early
A note in the changelog saying the next major version will require the newer version, with a date. Buyers can plan. Discovering it during an update is what generates anger.
Fail with an explanation, not an error
The update should check first and stop with a clear message naming what is needed and what was found. A fatal error halfway through is the same decision delivered badly.
Keep the old branch alive briefly
Security fixes only, for a few months, on the last version that supported the old platform. It costs little and it means nobody is stranded with something unsafe because they cannot upgrade their host this quarter.
Your own APIs deserve the same
If buyers built against a hook or a function you provide, renaming it is the same kind of break. Keep the old name working as a thin shim for a version, with a note in the changelog.
The rough rule
Announce one version ahead, support the old branch for a season, and never break somebody silently. Almost every complaint about a dropped version is really a complaint about not being told.