fnids are evil, they just need to drop them and respond properly to posts without them. What more state needs to be recorded which is not already encoded in a POST reply request {user:n,post:7651593,text:'xxx'}?
The solution should be pretty straightforward:
Reply forms -> Remove fnid, authenticate on post, add CSRF
Flag links -> Remove fnid, authenticate on post, add CSRF
They already check authentication on these actions anyway as you'll see if you try upvote links from another user without login, all that would be required would be to use CSRF instead of these closures to handle posts like this - the closures are not a workable solution on a large site, and I'd contend are dangerous on a small site - they throw away a lot of the advantages of HTTP for no appreciable gains.
Things like the more link are particularly pointless, they could just use something like:
https://news.ycombinator.com/x?fnid=xxx -> https://news.ycombinator.com/news/2
This would change over time like the existing home page, but there's no reason for a simple GET request like this to
expire.