In preparation for the general availability of SpiceDB Caveats, planned for the next 1.17.0 release, we thought it would be cool to share some of the recurrent use cases we’ve seen for caveats out in the wild. Caveats allow augmenting your SpiceDB schema with dynamic logic written in Google's CEL.
Here are top-3 most used caveat patterns:
🥉 IP Allowlists
One common use case is to implement conditional access based on the originating IP of an inbound request. Organizations that want to tighten employee access to their systems make sure they can only perform requests from a range of allowed IPs, e.g. as a CIDR block. GitHub’s IP Allowlists functionality provides a good real-world example.
SpiceDB offers first-class support for IP Allowlists via two built-in pieces of functionality: the ipaddress type and the in_cidr method. Let’s see this in action by modeling GitHub’s IP Allowlists! (Playground Link)
definition user {}
caveat expected_ip_range(user_ip ipaddress, cidr string) {
user_ip.in_cidr(cidr)
}
definition organization {
relation resources: repository
relation members: user
/*
ip_allowlist_policy is a caveated relationship to members of the organization based on IP Allowlists, and can
be disabled by setting the relationship to user:*
*/
relation ip_allowlist_policy: organization#members with expected_ip_range| user:*
permission policy = ip_allowlist_policy
}
definition repository {
relation owner: organization | user
relation reader: user
relation writer: user
relation adminer: user
permission read = (reader + write) & owner->policy
permission write = (writer + admin) & owner->policy
permission admin = adminer & owner->policy
}
🥈 Session-bound permissions
Another recurrent use of caveats is implementing access conditioned to the existence of a user session or properties of their session: Enforce a policy to allow access to resources only when users have 2FA set up Authorized based on attributes of SAML Session tags or JWT token claims
In the case of JWTs, after the client application verifies an incoming token, it could forward a subset of the claims as part of the SpiceDB request context to enrich the authorization operation.
One example could be access attenuation based on the audience claim (aud). A user has been granted admin permissions on a highly sensitive resource (e.g. administrative UI), but in order to be authorized we also need to make sure the web session was actually intended for the expected domain.
In this example the client application would write relationships with a stored value for the expected_aud
caveat context key, which would take precedence over anything coming from the client-side. Here is the (Playground Link):
definition user {}
definition organization {}
caveat valid_session_audience(aud string, expected_aud string) {
aud == expected_aud
}
definition control_plane {
relation granted: user with valid_session_audience
permission admin = granted
}
🥇 Time-Bound Permissions
And number one goes to limiting access based on time criteria! Organizations use this approach to further reduce the attack surface, in line with the principle of least privilege. This can be the likes of: only allowing employee access during working hours providing temporal access to support staff for a few hours to troubleshoot a customer problem Improving security posture by making all employee entitlements self-expiring
Since we’ve started with the well-understood GitHub model as an example, let’s see how a hypothetical temporal repository access grant could be implemented (Playground Link):
definition user {}
definition organization {}
caveat temporal_grant(grant_duration duration, current_timestamp string, grant_timestamp string) {
timestamp(current_timestamp) - timestamp(grant_timestamp) < grant_duration
}
definition repository {
relation owner: organization | user
relation reader: user | user with temporal_grant
relation writer: user | user with temporal_grant
relation adminer: user | user with temporal_grant
permission read = reader + write
permission write = writer + admin
permission admin = adminer
}
Wrap-up
So there you go, the top-3 most used caveat patterns for SpiceDB! 🏆 If you haven’t yet, feel free to check out the documentation 📖 and tinker with it in our recently released playground support! Have a question? Check out the Discord, where we and the community are discussing all things SpiceDB
Additional Reading
If you’re interested in learning more about Authorization and Google Zanzibar, we recommend reading the following posts: