Permission Sets
Grant application, object, field, and system permissions.
Permission sets are the primary way to grant capabilities. They can be
assigned directly to users or indirectly through
positions. Assignments may
carry valid_from / valid_until windows — expired grants stop
resolving immediately.
What permission sets control
| Permission type | Examples |
|---|---|
| Application access | User can open CRM or Console |
| Object permissions | Create, read, update, delete records |
| Field permissions | Read or update selected fields |
| System permissions | Access Console, run reports, export data |
| Integration permissions | Use API keys, webhooks, or admin actions |
Object permissions
Object permissions answer:
Can this user perform this operation on this object at all?Permission set grants use these flag names (as enforced by the security plugin's permission evaluator):
| Flag | Meaning |
|---|---|
allowRead | Read records allowed by record access rules |
allowCreate | Create records |
allowEdit | Update records allowed by record access rules |
allowDelete | Delete records allowed by record access rules |
viewAllRecords | Read every record for the object, bypassing record access |
modifyAllRecords | Update or delete every record for the object, bypassing record access; implies viewAllRecords for reads |
Record access still matters
unless viewAllRecords or modifyAllRecords bypasses the normal
row-level boundary. Reserve those flags for
administrative permission sets — they are effectively a tenant-wide
super-user grant for that object.
System permissions
System permissions are for platform actions such as:
- Console access;
- manage users;
- manage positions and permission sets;
- run reports;
- export reports;
- manage integrations;
- view audit logs.
Keep system permissions separate from business object permissions so administrators can audit them easily.
Recommended sets
Start with a few named permission sets:
| Permission set | Purpose |
|---|---|
| Basic User | Login and access the main application |
| Setup Administrator | Manage users, roles, settings, and diagnostics |
| Report Viewer | View reports and dashboards |
| Integration Operator | Manage webhooks/API keys |
| Support User | Read/update support objects |
Then add domain-specific sets for the customer's application.
Marking a set isDefault suggests it for assignment when the owning
package is installed (this replaces the pre-13 isProfile flag).
Delegated administration
A permission set can carry an adminScope that turns its holders into
scoped administrators. The scope declares:
- where delegates may act — a business-unit subtree;
- what they may do —
manageAssignments,manageBindings,authorEnvironmentSets; - which permission sets they may distribute
(
assignablePermissionSets).
Delegates write single rows against allowlisted sets only, and every
grant is stamped with granted_by for audit. Granting or authoring a
set that itself has an adminScope requires the grantor to hold a
strictly containing scope. Tenant-level admins bypass the gate
entirely.
Field security (appendix)
Permission sets also carry field-level grants. Even when a user can read a record, individual fields can be hidden or made read-only.
Two modes
| Mode | Effect |
|---|---|
| Hidden | Field is stripped from API responses and Console views entirely |
| Read-only | Field is returned but writes are rejected |
Where it's enforced
The same evaluator that checks object permissions applies field rules on every path — REST, ObjectQL, generated Console forms, exports. There is no "back door" through a lower-level API.
Typical patterns
| Use case | Recommendation |
|---|---|
HR data on sys_user (salary, SSN) | Hide for everyone except an HR permission set |
| External system identifiers | Read-only for support, writable for integration operators |
Internal cost vs. customer price on product | Hide cost from sales, surface to finance |
| Notes field with PHI | Hide unless permission set includes the relevant clinical role |
Authoring guidance
- Default to hide rather than read-only when the field carries sensitive data — read-only still leaks the value into responses and logs.
- Always write field-permission keys object-qualified
(
crm_lead.budget, notbudget) — since ObjectStack 14.4 thesecurity-fls-unqualified-keylint rejects bare keys at compile time, because they silently matched nothing. - Bundle field rules into permission sets that match a real job
function (
HR Manager,Finance Read-only) instead of inventing one set per field — easier to audit. - For compliance use cases, pair field security with audit log retention so you can answer "who saw this row?" after the fact.