Licet

Hex.pm Docs CI

Licet evaluates SpiceDB permission schemas (.zed files) inside your Elixir application, with relationships stored in your own Postgres database. There is no SpiceDB server to run.

Licet is Latin for "it is permitted".

Licet answers questions like "can Ada edit this document?" from relationships you store: Ada owns the folder, the folder contains the document, owners of a folder can edit what's in it. This is relationship-based access control (ReBAC), as described in Google's Zanzibar paper. Because the schema is plain SpiceDB, you can start embedded and move to a SpiceDB cluster later without rewriting it.

Why Licet

Installation

Add Licet to your dependencies in mix.exs:

def deps do
  [
    {:licet, "~> 0.1"}
  ]
end

Licet needs Elixir 1.17 or newer and Postgres 15 or newer.

A two-minute example

Describe your permissions in priv/licet/schema.zed:

definition user {}

definition team {
  relation member: user
}

definition document {
  relation owner: user
  relation viewer: user | team#member
  permission edit = owner
  permission view = owner + viewer
}

Generate the migration that creates Licet's tables, then run it:

mix licet.gen.migration
mix ecto.migrate

Start Licet in your supervision tree, after your repo:

children = [
  MyApp.Repo,
  {Licet,
   name: MyApp.Licet,
   repo: MyApp.Repo,
   schema: {:file, Application.app_dir(:my_app, "priv/licet/schema.zed")}}
]

Write relationships and check permissions:

{:ok, token} =
  Licet.write(MyApp.Licet, [
    {:create, "document:roadmap#owner@user:ada"},
    {:create, "team:eng#member@user:bob"},
    {:create, "document:roadmap#viewer@team:eng#member"}
  ])

opts = [consistency: {:at_least, token}]

Licet.check(MyApp.Licet, "document:roadmap", "view", "user:bob", opts)
#=> {:ok, :allowed}

Licet.check(MyApp.Licet, "document:roadmap", "edit", "user:bob", opts)
#=> {:ok, :denied}

Licet.lookup_resources(MyApp.Licet, "document", "view", "user:bob", opts)
#=> {:ok, ["roadmap"], nil}

By default a check reads a snapshot that is refreshed every few seconds and shared through a cache. Passing the token from a write guarantees the check sees that write. Consistency explains the trade-off.

Getting started walks through the same steps in more detail.

Features

Coming from SpiceDB?

Your .zed schema and your validation files run unchanged, unless they use caveats or self. Migrating to or from SpiceDB covers moving relationships in either direction, and Limitations lists what Licet leaves out, such as caveats and the Watch API.

When to use something else

Examples

Documentation

Contributing

See CONTRIBUTING.md for how to run the test suite, including the comparison against a live SpiceDB.

License

Licet is released under the Apache License 2.0. Copyright Netoum.

SpiceDB is a trademark of AuthZed. Licet is an independent project and is not affiliated with AuthZed.