
PocketBase API Rules
FreeStreamline PocketBase access control with precise rules.
Free · Opens the source repo
What PocketBase API Rules does
PocketBase API Rules provides a comprehensive guide for defining and managing access control rules within PocketBase applications. This skill is essential for developers and designers who need to configure permissions, write filter expressions, and debug access issues such as 403 and 404 responses. With detailed explanations of the five rule types—List, View, Create, Update, and Delete—users can understand how to control access to their collections effectively.
The skill covers the syntax for filter expressions, including various operators and logical constructs, enabling users to create complex rules that suit their application needs. For instance, it explains how to use operators like =, !=, and ~ for filtering records based on specific conditions. Additionally, it introduces macros that allow access to request context and collection data, which can be pivotal in crafting dynamic and responsive access rules.
Moreover, the skill includes practical examples and common patterns that illustrate how to implement rules for owner-only access, verified users, and role-based permissions. This makes it easier for users to adopt best practices in their access control strategies. The inclusion of datetime macros and the geoDistance() function further enhances the capability of the rules, allowing for time-based and location-based filtering, respectively.
Overall, PocketBase API Rules is a valuable resource for anyone working with PocketBase, ensuring that they can define precise and effective access control mechanisms for their applications.
When to use it
Use this skill when you need to configure access permissions for your PocketBase collections or troubleshoot access-related issues.
When not to use it
This skill is not suitable for users unfamiliar with API concepts or those who do not require detailed access control in their applications.
What you can build with it
Configuring User Permissions
Set up detailed permissions for different user roles in your PocketBase application to ensure secure access to sensitive data.
Debugging Access Issues
Use the skill to troubleshoot and resolve 403/404 errors by verifying your access control rules and filter expressions.
Implementing Location-Based Filtering
Utilize geoDistance() in your rules to restrict access based on user location, enhancing the relevance of data access.
How to install PocketBase API Rules
View source1. Install with the skills CLI
npx skills add davila7/claude-code-templates/pb-api-rules --agent claude-code2. Or install it manually
Download the skill folder and drop it into ~/.claude/skills/ for all projects, or .claude/skills/ to scope it to one repo. Restart Claude Code so it picks up the new skill.
Anthropic's agentic coding CLI, and the reference implementation of Agent Skills. Drop a skill folder into ~/.claude/skills and Claude Code loads it automatically whenever a task matches the skill's description. Claude Code docs
Inside SKILL.md
Written by davila7PocketBase API Rules & Filter Expressions
Rule Types
Each collection has 5 rule types. Each rule is a filter expression that must evaluate to true for the request to proceed.
| Rule | Controls | Locked = | Empty string = |
|---|---|---|---|
| List | GET /api/collections/{name}/records | superusers only | everyone can list |
| View | GET /api/collections/{name}/records/{id} | superusers only | everyone can view |
| Create | POST /api/collections/{name}/records | superusers only | everyone can create |
| Update | PATCH /api/collections/{name}/records/{id} | superusers only | everyone can update |
| Delete | DELETE /api/collections/{name}/records/{id} | superusers only | everyone can delete |
Critical: null/locked means only superusers can perform the action (regular users and guests are denied). Empty string "" means EVERYONE including guests. Superusers always bypass API rules entirely — see below.
Superuser Bypass
Superusers (formerly admins) always bypass API rules. Rules only apply to regular auth records and guests.
Filter Syntax
Operators
| Operator | Meaning | Example |
|---|---|---|
= | Equal | status = "active" |
!= | Not equal | status != "draft" |
> | Greater than | count > 5 |
>= | Greater or equal | count >= 5 |
< | Less than | count < 10 |
<= | Less or equal | count <= 10 |
~ | LIKE (contains) | title ~ "hello" |
!~ | NOT LIKE | title !~ "spam" |
?= | Any/has (array contains) | tags ?= "TAG_ID" |
?!= | None (array not contains) | tags ?!= "TAG_ID" |
?> | Any greater than | scores ?> 90 |
?>= | Any greater or equal | scores ?>= 90 |
?< | Any less than | scores ?< 10 |
?<= | Any less or equal | scores ?<= 10 |
?~ | Any LIKE | emails ?~ "@gmail.com" |
?!~ | Any NOT LIKE | emails ?!~ "@test.com" |
Critical: use ?= (not =) for multi-valued fields (multi-select, multi-relation, multi-file). = checks the raw JSON string, ?= checks individual values.
Logical Operators
status = "active" && author = @request.auth.id
status = "active" || status = "featured"
Parentheses for grouping: (a = 1 || b = 2) && c = 3
Values
- Strings:
"value"or'value' - Numbers:
123,45.67 - Booleans:
true,false null— empty/missing value- Identifiers: field names, macros
Request Macros (@request.*)
Access the current request context in rules:
| Macro | Type | Description |
|---|---|---|
@request.auth.id | string | Current auth record ID (empty if guest) |
@request.auth.email | string | Current auth record email |
@request.auth.verified | bool | Whether email is verified |
@request.auth.collectionId | string | Auth collection ID |
@request.auth.collectionName | string | Auth collection name |
@request.auth.* | any | Any field from the auth record |
@request.body.fieldName | any | Field value from request body |
@request.query.paramName | string | URL query parameter |
@request.headers.name | string | Request header (lowercase key) |
@request.method | string | HTTP method (GET/POST/PATCH/DELETE) |
Auth record relations
You can traverse relations on the auth record:
@request.auth.team.owner = @request.auth.id
Collection Macros (@collection.*)
Cross-collection lookups without explicit joins:
@collection.memberships.user ?= @request.auth.id &&
@collection.memberships.team ?= team
This checks if a record exists in the memberships collection where the user matches the current auth user and the team matches the current record's team field.
Note: @collection.* performs an implicit EXISTS subquery. It's powerful but can be slow on large datasets — add indexes.
Field Modifiers
Use in create/update rules to validate specific field behaviors:
| Modifier | Works on | Description |
|---|---|---|
:isset | @request.body.* | True if the field was sent in the request (even if empty) |
:changed | record field | True if the field value differs from current stored value (update only) |
:length | string/array | Returns the length |
:each | array | Applies the condition to each element |
:lower | string | Lowercased value |
Examples
// Only allow changing status if user is owner
status:changed = false || author = @request.auth.id
// Prevent setting role on create
@request.body.role:isset = false
// Require at least 2 tags
@request.body.tags:length >= 2
// Check each tag is from allowed list
@request.body.tags:each ?= @collection.allowed_tags.id
Datetime Macros
| Macro | Example output |
|---|---|
@now | 2024-01-15 10:30:00.000Z |
@second | 2024-01-15 10:30:00.000Z |
@minute | 2024-01-15 10:30:00.000Z |
@hour | 2024-01-15 10:00:00.000Z |
@day | 2024-01-15 00:00:00.000Z |
@month | 2024-01-01 00:00:00.000Z |
@year | 2024-01-01 00:00:00.000Z |
@todayStart | 2024-01-15 00:00:00.000Z |
@todayEnd | 2024-01-15 23:59:59.999Z |
@monthStart | 2024-01-01 00:00:00.000Z |
@monthEnd | 2024-01-31 23:59:59.999Z |
@yearStart | 2024-01-01 00:00:00.000Z |
@yearEnd | 2024-12-31 23:59:59.999Z |
Arithmetic: @now - 7d, @now + 1h, @now - 30m
geoDistance()
For location-based filtering:
geoDistance(lat, lon, 40.7128, -74.0060) <= 10000
Arguments: geoDistance(latField, lonField, targetLat, targetLon) — returns meters.
Common Patterns
Owner-only access
// View/Update/Delete rule:
author = @request.auth.id
Authenticated users only
@request.auth.id != ""
Verified users only
@request.auth.verified = true
Role-based access
@request.auth.role = "admin" || author = @request.auth.id
Team membership
@collection.team_members.user ?= @request.auth.id &&
@collection.team_members.team ?= team
Public read, owner write
// List/View: "" (empty = everyone)
// Create: @request.auth.id != ""
// Update/Delete: author = @request.auth.id
Prevent field modification
// Update rule: prevent changing `owner` after creation
owner:changed = false
Time-limited access
expires > @now
Frequently asked questions about PocketBase API Rules
Similar skills
WinMD API Search
Easily find and explore Windows desktop APIs.
WebMCPify
Transform any web app into an agent-ready platform.
Phoenix Tracing
Instrument LLM applications with OpenInference tracing.
Foundry Hosted Agent CopilotKit
Guidance for developing agentic web apps on Azure.
Power Automate Foundation
Connect AI agents to Power Automate seamlessly.
Power Automate Flow Builder
Efficiently build and deploy Power Automate flows programmatically.
