> Once you need specific changes going into a release, you need branches.
I don't have this need. Then I don't need to deal with the sheer insanity of loosely spreading all those different git refs you mention over everything including the future.
Changes get integrated fast into main, because nothing is blocked, frozen, or left for someone else in the future. This also makes commits/PRs/changes small. Feature flags are used to ease this even more.
In the face of absolute disaster it is possible to simply revert/rollback a release/deploy. However in practice I don't really need to do this, almost never. Some hotfix here and there maybe, but it's still all much faster than the sheer insanity of git-flow overcomplications. Often a hotfix is the only solution, a revert/rollback fixes nothing when the problem is outside of git (DBs, client storage...).
In the end, you have to evaluate all the time you sink into this model, and how much risk you actually mitigate. Wherever I've seen git-flow, the overhead was huge and ever-growing, and it never really helped with any risk mitigation. I would go as far as saying that overall it increased the risk, due to its complexity.