DEV Community

Alex Spinov
Alex Spinov

Posted on

OpenFGA Has a Free API — Heres How to Build Google Drive-Style Permissions

OpenFGA is an open-source authorization engine inspired by Google Zanzibar — the system that powers permissions in Google Drive, YouTube, and Google Cloud. Build relationship-based access control for any app.

Why OpenFGA?

  • Google Zanzibar: Same model used by Google, Airbnb, GitHub
  • Relationship-based: 'Alice is editor of document:1'
  • Sub-millisecond: Check permissions in <1ms
  • Any scale: Handles billions of relationships
  • Open source: CNCF project from Auth0/Okta
  • Language SDKs: JS, Go, Python, Java, .NET

Docker Setup

docker run -p 8080:8080 -p 3000:3000 openfga/openfga run
Enter fullscreen mode Exit fullscreen mode

Define Authorization Model

{
  "schema_version": "1.1",
  "type_definitions": [
    {
      "type": "document",
      "relations": {
        "owner": {"this": {}},
        "editor": {"union": {"child": [{"this": {}}, {"computedUserset": {"relation": "owner"}}]}},
        "viewer": {"union": {"child": [{"this": {}}, {"computedUserset": {"relation": "editor"}}]}}
      }
    },
    {
      "type": "folder",
      "relations": {
        "owner": {"this": {}},
        "viewer": {"union": {"child": [{"this": {}}, {"computedUserset": {"relation": "owner"}}]}}
      }
    }
  ]
}
Enter fullscreen mode Exit fullscreen mode

This means: owners are editors, editors are viewers (inheritance).

Write Relationships

curl -X POST http://localhost:8080/stores/STORE_ID/write \
  -H 'Content-Type: application/json' \
  -d '{
    "writes": {
      "tuple_keys": [
        {"user": "user:alice", "relation": "owner", "object": "document:budget-2026"},
        {"user": "user:bob", "relation": "editor", "object": "document:budget-2026"},
        {"user": "user:charlie", "relation": "viewer", "object": "document:budget-2026"}
      ]
    }
  }'
Enter fullscreen mode Exit fullscreen mode

Check Permission

curl -X POST http://localhost:8080/stores/STORE_ID/check \
  -H 'Content-Type: application/json' \
  -d '{
    "tuple_key": {
      "user": "user:alice",
      "relation": "editor",
      "object": "document:budget-2026"
    }
  }'
# {"allowed": true} — Alice is owner, owners inherit editor
Enter fullscreen mode Exit fullscreen mode

JavaScript SDK

import { OpenFgaClient } from '@openfga/sdk';

const fga = new OpenFgaClient({
  apiUrl: 'http://localhost:8080',
  storeId: 'STORE_ID',
});

// Write relationship
await fga.write({
  writes: [{ user: 'user:alice', relation: 'editor', object: 'document:report' }],
});

// Check permission
const { allowed } = await fga.check({
  user: 'user:alice',
  relation: 'viewer',
  object: 'document:report',
});
console.log(allowed); // true (editors inherit viewer)

// List objects user can access
const { objects } = await fga.listObjects({
  user: 'user:alice',
  relation: 'viewer',
  type: 'document',
});
console.log(objects); // ['document:report', 'document:budget-2026']
Enter fullscreen mode Exit fullscreen mode

Express Middleware

function authorize(relation: string, getObject: (req) => string) {
  return async (req, res, next) => {
    const { allowed } = await fga.check({
      user: `user:${req.user.id}`,
      relation,
      object: getObject(req),
    });
    if (!allowed) return res.status(403).json({ error: 'Forbidden' });
    next();
  };
}

app.get('/documents/:id',
  authorize('viewer', (req) => `document:${req.params.id}`),
  getDocument
);

app.put('/documents/:id',
  authorize('editor', (req) => `document:${req.params.id}`),
  updateDocument
);
Enter fullscreen mode Exit fullscreen mode

Real-World Use Case

A document collaboration app used RBAC (admin/user roles). Users wanted to share individual docs with specific people — impossible with RBAC. After switching to OpenFGA, they built Google Drive-style sharing in 1 day: per-document owner/editor/viewer with inheritance.


Need to automate data collection? Check out my Apify actors for ready-made scrapers, or email spinov001@gmail.com for custom solutions.

Top comments (0)