6 ms·
I was searching for a quick explainer of how revocation is implemented, but didn't find it (at least not quickly). Can anyone say how this works? Revocation is
by hn_throwaway_99 3y ago
I was searching for a quick explainer of how revocation is implemented, but didn't find it (at least not quickly). Can anyone say how this works?
Revocation is essentially the Achilles heel of JWTs - you want to have completely stateless bearer tokens, but if you need to check for revocations, it means you have to do some sort of lookup against a revocation table, and at that point you really lose the stateless nature that you wanted in the first place. There are some tricks to make this more tenable, but it's still a big reason why some folks say "don't use JWTs for end-user auth".
Would greatly appreciate details on how Biscuit implements this with their "revocation IDs".
Edit: Nevermind, I found it: https://www.biscuitsec.org/docs/why-biscuit/ https://www.biscuitsec.org/docs/why-biscuit/ - and it turns out revocation is a "non goal". And then in the linked page about how to implement revocations, they basically do exactly what I do for JWTs: have a revocation list, but then revocations can fall off that list once they're past the expiration date anyway.
So, not to be too harsh, but why would I use this over JWTs? There is no "magic" getting around the "well, they're kinda stateless" problem. To be honest I don't really care about some of the other tangential benefits (after all, you can stick whatever you want on a JWT and interpret it however you like) if it still has by far the same glaring pain point associated with any bearer token system.
- ivanb 3y ago> Revocation is essentially the Achilles heel of JWTs By the nature of the problem you have to store some kind of a list of tokens. Either a black list as with JWTs or a white list as with classic session tokens. There is no way around it. This makes both approaches practically the same. One can argue that the black list will in general be shorter than the white list, but in a case of a serious attack, would it really be so? I am afraid that the community will now abandon JWTs and move to biscuits, macaroons, buns and meringues as they did with classic session tokens, throwing away the tools and security practices.
- deleted 3y ago[deleted]
- antran22 3y agoIn the case of a serious attack, the blacklist should be every token. You can still handle this quite nicely with JWT by rotating the previous verification key. Depends on systems and configuration, this can be as easy as changing the HMAC private key or push a new RSA key to every verifier.
- physicsguy 3y agoI've already seen one company adopt Paseto tokens as though this is some sort of magic bullet.
- darkr 3y agoA simpler, but less targeted approach that works in case you're not tracking token issuance by ID is to maintain a list of maps of entity (e.g user) ID to minimum issue time. This way you can revoke all earlier tokens for a user ID with a single record, and not have to keep track of issued tokens.
- geal 3y ago(Biscuit author here) there is some support for revocation with the way revocation ids are implemented: there's one generated for each block of a token, so if you add the token's last block's revocation id to the revocation list, then all tokens derived from that one will be revoked as well. We outline the strategies to manage revocation in https://www.biscuitsec.org/docs/guides/revocation/ https://www.biscuitsec.org/docs/guides/revocation/ but as you said, there is no magic here, adding revocation reintroduces state in the system. As for why you would use this over JWTs: Biscuit avoids JWT's usual footguns, specifies an authorization language where checks can be carred by the token, it adds attenuation and third party blocks. You can build a lot more with those tokens
- GTP 3y ago> specifies an authorization language where checks can be carried by the token Why? Wouldn't a developer prefer to implement this inside its application logic anyway? Edit: I think I figured it out myself: you're likely targeting the case where someone with a certain authorization wants to give someone else a weaker form of that authorization (attenuation).
- bpicolo 3y agoIt could also let your clients do proactive validation without rewriting too much code, seems like?
- nulltxt 3y agoI believe from when I looked at it you have to store the revocation tokens in a list so it isn't an amazing solution but better than storing the whole token ig
- foota 3y agoIt's generally better because revocation lists are assumed to be smaller than valid lists.
- marcus_holmes 3y agoOff topic: I'm always confused by the passion to use JWTs where normal session uuid's would do just as well. A place I worked at recently insisted on JWTs despite being a monolith and calling the database on every API endpoint. I still don't get why.
- omeid2 3y agoIt is cheaper to look up at the handful of recovered tokens than however many active sessions you have, assuming you have a substantial number of them, otherwise, it is a moot point, similar to microservices for websites with 3-4 digits traffic per hour.
- angoragoats 3y agoWhile this is technically true, using an index for either lookup makes the lookup happen in O(log n)-ish time, so neither is slow, even if you have a large number of active sessions.
- omeid2 3y agoThe issue is not individual lookup time, it is the aggregate cost of millions database lookup requests that you can avoid.
- angoragoats 3y agoAh, sorry I misunderstood what you were saying. Still, any modern database system could handle these lookups for all but the largest sites, so this smells like premature optimization for the vast majority of projects out there.
- RcouF1uZ4gsC 3y agoDown below there is a link to an article by tptacek that says that these random session tokens are the simplest and most secure and you should use them if you are able to (which is true in a lot more cases than they are used) https://fly.io/blog/api-tokens-a-tedious-survey/ https://fly.io/blog/api-tokens-a-tedious-survey/
- Ecoste 3y agoMaybe a naive question: but is there any way at all (impractical or not) to implement stateless revocation? In my mind JWT is already non-stateless in the sense that the server at least needs to keep one piece of information which is the secret key. It's very memory efficient, but not stateless. If a decision is made to revoke a user, that state needs to be kept somewhere.
- ghayes 3y agoYou could make your expiration short enough that you are unlikely to need revocation, and allow token exchange (trade an expired token for a new one, and that would include a revocation check)
- conradludgate 3y agoNo. But a stateful revocation service can be extremely lightweight. The number of JWTs being revoked will be minimal and they are only revoked until they would otherwise expire, which keeps the dataset small. This could easily fit in an in memory cache to avoid a database hit.
- tptacek 3y agoIn Macaroonia, which is one of the most important Biscuit inspirations, you can address "stateless" revocation with a 3P caveat on a revocation check service, which can issue time-limited "not revoked" attestations; the services that rely on the tokens don't even have to understand what that revocation check service is, or have any revocation checking code at all; it's all hidden from the application, the service can get moved around, scaled out independently, etc. I'd be surprised if there wasn't a similar strategy available to Biscuits.
- geal 3y agothere's a siimilar concept in Biscuit, the 3rd party block: https://www.biscuitsec.org/blog/third-party-blocks-why-how-when-who/ https://www.biscuitsec.org/blog/third-party-blocks-why-how-w... It's not advertised a lot right now because it's not supported by all libraries yet