Collections & API Rules
Collections are PocketBase’s tables. Each collection defines a schema (typed fields) and a set of API rules that control who can list, view, create, update, and delete its records. Getting the rules right is the single most important step in securing your app.
Creating a collection
Using the portal
- Open the admin panel at
https://<instance-name>.pocketbasecloud.com/_/ - Click New collection
- Choose the type:
- Base — regular data (posts, products, comments, …)
- Auth — user accounts with login capability
- View — read-only collection backed by a SQL
SELECT
- Add fields and click Create
Using the CLI
Point pbc at the instance once, log in as its superuser, and the collection
commands work against it:
pbc use https://<instance-name>.pocketbasecloud.com
pbc login
Create an empty collection, or pass a full definition to create it with its fields in one step:
pbc collections create tasks --type base
pbc collections create '{"name":"posts","type":"base","fields":[
{"name":"title","type":"text","required":true},
{"name":"body","type":"editor"},
{"name":"published","type":"bool"}]}'
Inspect and change them:
pbc collections ls
pbc collections get posts
pbc collections update posts '{"fields":[…]}'
pbc collections rm posts
pbc use --name <profile> keeps several instances side by side (staging and
production, say), and --profile <name> picks one per command. The same
commands work against a local instance — pbc use http://127.0.0.1:8090.
Field types
PocketBase supports the field types you’d expect:
| Type | Use for |
|---|---|
text, editor, number, bool |
Basic values, rich text |
email, url, date |
Validated formats |
select |
One or more values from a fixed list |
relation |
References to records in another collection |
file |
File uploads |
json |
Arbitrary structured data |
Relations are expanded on demand with the expand query parameter:
const post = await pb.collection("posts").getOne("RECORD_ID", {
expand: "author,comments_via_post",
});
API rules
Each collection has five rules — List, View, Create, Update, and Delete. A rule is a filter expression; the operation is allowed only when the expression matches.
Using the portal
Edit them from the lock icon on the collection page in the admin panel.
Using the CLI
pbc rules get posts
pbc rules set posts \
--list-rule '@request.auth.id != ""' \
--view-rule '@request.auth.id != ""' \
--create-rule '@request.auth.id != ""' \
--update-rule 'author = @request.auth.id' \
--delete-rule 'author = @request.auth.id'
Pass null as a value to lock a rule back to superusers only:
pbc rules set posts --delete-rule null
Three states matter, whichever way you set them:
- Locked (superusers only) — the rule is
null; only superusers via the admin panel or admin token can perform the operation - Empty string — anyone can perform the operation
- Filter expression — allowed only when the expression evaluates to true
Common rule recipes
Only signed-in users can read:
@request.auth.id != ""
Users can only see and edit their own records (with an owner relation
field pointing to users):
owner = @request.auth.id
Anyone can read published posts, authors see their drafts too:
status = "published" || author = @request.auth.id
Validate incoming data on create — e.g., force the owner field to the
current user:
@request.auth.id != "" && @request.body.owner = @request.auth.id
Rules can reference the current record’s fields, @request.auth (the
authenticated user), @request.body, @request.query, and even fields across
relations (author.verified = true).
Working with records
Using the portal
Open a collection in the admin panel to browse, filter, edit, and create records.
Using the CLI
The same operations, handy for seeding data and for checking what a rule actually returns:
pbc records ls posts --filter 'published = true' --sort '-created' --per-page 50
pbc records get posts RECORD_ID
pbc records create posts '{"title":"first","published":true}'
pbc records update posts RECORD_ID '{"published":false}'
pbc records rm posts RECORD_ID
Testing your rules
The admin panel’s API preview on each collection shows the exact REST
endpoints and lets you copy example requests. A quick way to verify rules is
to call the API without a token and confirm you get a 403 or filtered
results, then repeat with a logged-in user.
From the terminal, pbc records ls runs as the superuser (rules don’t apply to
it), so test the rules themselves with an unauthenticated request:
curl https://<instance-name>.pocketbasecloud.com/api/collections/posts/records
Important: never leave Create/Update/Delete rules empty on a production collection unless you truly want them public. Locked-by-default is the safe starting point.
Moving a schema between instances
Once a schema is right on one instance, copy it to another — staging to production, or a local instance to the cloud.
Using the portal
The project’s Collections page has Export and Import dialogs, and the admin panel has its own under Settings → Import collections.
Using the CLI
pbc use https://staging.pocketbasecloud.com && pbc login
pbc collections export --out collections.json
pbc use https://production.pocketbasecloud.com && pbc login
pbc collections import collections.json
--delete-missing makes the import an exact mirror by dropping collections not
present in the file — it asks for confirmation first, and it drops their data
with them.