This is a nice example of why one should parse, not validate. If every function that requires some kind of permission takes that permission as an argument, say (pseudocode)
void doFoo(PermissionToDoFoo permission, ...){...}
and then, the only way to call it is through something like from request import getAuth, respond
\\ Maybe<AuthenticationData> getAuth(Request request)
\\ void respond(String response)
from permissions import askForPermissionToDoFoo
\\ Maybe<PermissionToDoFoo> askForPermissionToDoFoo(AuthenticationData auth)
response =
try
auth <- getAuth(request)
permission <- askForPermissionToDoFoo(auth)
doFoo(permission)
"Success!"
fail
"Oopsie!"
respond(response)
It becomes impossible to represent the invalid state of doing Foo without permission.