Martin Carlsson
04/18/2025, 9:23 AMexport const runtime = 'nodejs';
import { NextRequest, NextResponse } from 'next/server';
import { can } from '@/lib/cerbos';
export async function GET(_req: NextRequest, { params }: { params: Promise<{ id: string }> }): Promise<NextResponse> {
const { id: docId } = await params;
const principal = { id: 'user123', roles: ['reader'] };
try {
const allowed = await can(principal, 'view', {
kind: 'document',
id: docId,
});
if (!allowed) {
return NextResponse.json({ error: 'Forbidden' }, { status: 403 });
}
return NextResponse.json({ id: docId, content: 'This is secret.' });
} catch (err) {
console.error('Cerbos unreachable:', err);
return NextResponse.json({ error: 'Authorization service unavailable' }, { status: 503 });
}
}
apiVersion: api.cerbos.dev/v1
resourcePolicy:
version: default
resource: document
rules:
- actions: ['view']
roles: ['reader']
effect: EFFECT_ALLOW
Martin Carlsson
04/18/2025, 9:25 AMMartin Carlsson
04/18/2025, 9:27 AM// lib/cerbos.ts
import { GRPC } from '@cerbos/grpc';
const host = process.env.CERBOS_HOST ?? 'cerbos';
const port = process.env.CERBOS_GRPC_PORT ?? '3593';
export const cerbos = new GRPC(`${host}:${port}`, { tls: false });
export async function can(principal: { id: string; roles: string[] }, action: string, resource: { kind: string; id: string }): Promise<boolean> {
return cerbos.isAllowed({
principal: { id: principal.id, roles: principal.roles },
resource: { kind: resource.kind, id: resource.id },
action,
});
}
oguzhan
(principal, resource, action)
. The policy seems to be fine and it is working as expected. (pg)
Could you send a request via cURL to Cerbos instance running in docker?
curl -X POST '127.0.0.1:3592/api/check/resources' \
--header 'Content-Type: application/json' \
--data-raw '{
"requestId": "123123",
"principal": {
"id": "user123",
"roles": [
"reader"
],
"attr": {}
},
"resources": [
{
"resource": {
"kind": "document",
"id": "docId",
"attr": {}
},
"actions": [
"view"
]
}
]
}'
Martin Carlsson
04/19/2025, 5:44 AMoguzhan
docker-compose
file?
Also when cerbos PDP launches, it states where it read the cerbos configuration file as:
{
"log.level": "info",
"@timestamp": "2025-04-19T12:31:32.141Z",
"log.logger": "cerbos.server",
"message": "Loading configuration from __default__"
}
If it is __default__
like it is reported above, it means it uses the default configuration file embedded with the cerbos image.
Could you check if this is the case?Martin Carlsson
04/20/2025, 4:27 AMMartin Carlsson
04/20/2025, 4:56 AM.devcontainer/devcontainer.json
{
"name": "PowerBI",
"dockerComposeFile": [
"docker-compose.yml"
],
"service": "app",
"runServices": [
"app",
"cerbos"
],
"shutdownAction": "stopCompose",
"workspaceFolder": "/workspace",
"postCreateCommand": "zsh .devcontainer/postCreateCommand.zsh",
"forwardPorts": [
3000,
3593
],
"features": {
"<http://ghcr.io/devcontainers/features/azure-cli:1|ghcr.io/devcontainers/features/azure-cli:1>": {
"version": "latest",
"bicepVersion": "latest"
},
"<http://ghcr.io/devcontainers/features/common-utils:2|ghcr.io/devcontainers/features/common-utils:2>": {
"installZsh": true,
"configureZshAsDefaultShell": true,
"installOhMyZsh": true,
"installOhMyZshConfig": true,
"upgradePackages": true
}
},
"customizations": {
"vscode": {
"extensions": [
"dbaeumer.vscode-eslint",
"esbenp.prettier-vscode",
"bradlc.vscode-tailwindcss",
"vincaslt.highlight-matching-tag",
"formulahendry.auto-rename-tag",
"ms-vscode.vscode-typescript-next",
"mtxr.sqltools-driver-pg"
]
}
},
"remoteUser": "root"
}
.devcontainer/docker-compose.yml
services:
app:
image: <http://mcr.microsoft.com/devcontainers/typescript-node:1-22-bookworm|mcr.microsoft.com/devcontainers/typescript-node:1-22-bookworm>
command: sleep infinity
volumes:
- ../:/workspace:cached
- /var/run/docker.sock:/var/run/docker.sock
working_dir: /workspace
depends_on:
- cerbos
environment:
- GRPC_DNS_RESOLVER=native
- CERBOS_HOST=cerbos
- CERBOS_GRPC_PORT=3593
cerbos:
container_name: cerbos
image: <http://ghcr.io/cerbos/cerbos:latest|ghcr.io/cerbos/cerbos:latest>
command:
- server
- --config
- /workspace/cerbos/cerbos.yaml
volumes:
- ../cerbos:/workspace/cerbos:ro
ports:
- '3593:3593'
- '3592:3592'
cerbos/cerbos.yaml
server:
grpcListenAddr: ':3593'
storage:
driver: disk
disk:
directory: /workspace/cerbos/policies