Match Resource Attribute
The Match Resource Attribute (matchResourceAttribute) access rule restricts operations and filters data based on the attributes of the target record itself (such as status == 'published', is_active == true, stock > 0, or category in ['books', 'electronics']).
While Match User Property inspects attributes on the caller (e.g. department or subscription tier), Match Resource Attribute inspects the state of the data record being accessed.
1. How It Works
Section titled “1. How It Works”- Dual-Phase Execution:
- Collection Queries (
list,search) inFETCHPhase: Automatically injects SQLWHEREclauses into the database query, ensuring users only retrieve matching records without performance overhead. - Single-Record Detail Actions (
read,update,delete) inPOST_FETCHPhase: Evaluates the loaded record in memory before returning or mutating it.
- Collection Queries (
- Fail-Fast Projection Safety: If an API endpoint uses field projections, the engine ensures the filtered attribute is always selected from the database so security checks cannot be bypassed.
| Property | Specification |
|---|---|
| Rule Type | matchResourceAttribute |
| Identity Constraining | false (Must be paired with an identity rule in the same scenario) |
| Supported Strategies | All strategies (RBAC, OrganizationRBAC, EnterpriseRBAC) |
| Allowed Placement Levels | Exposed Entity Level (exposure), Action Level (action) (Not allowed at global API Model Level) |
| Execution Phases | FETCH (list, search), POST_FETCH (read, update, delete, link, unlink) |
Must Be Paired with an Identity Rule
Because Match Resource Attribute inspects data attributes rather than user identity, it cannot exist as the only rule in an Access Scenario. Every scenario containing Match Resource Attribute must also include at least one identity-constraining rule (such as Allow Public, Allow Authenticated, Match User Role, or Match Resource Owner).
2. Supported Comparison Operators
Section titled “2. Supported Comparison Operators”When configuring Match Resource Attribute, you select the target entity property, a comparison operator, and an expected value:
1. Equality & Inequality
Section titled “1. Equality & Inequality”equal(==): Record attribute must match the value (e.g.status equal 'published',is_active equal true).notEqual(!=): Record attribute must not match the value (e.g.status notEqual 'archived').
2. Set Membership (in & notIn)
Section titled “2. Set Membership (in & notIn)”in: Record attribute must be one of the specified list values (e.g.status in ['draft', 'published']).notIn: Record attribute must not be in the specified list (e.g.status notIn ['archived', 'banned']).
3. String Matching (with Automatic Wildcard Escaping)
Section titled “3. String Matching (with Automatic Wildcard Escaping)”startsWith: String begins with prefix (e.g.sku startsWith 'PRO-').endsWith: String ends with suffix (e.g.file_format endsWith '.pdf').contains: String contains substring (e.g.tags contains 'featured').
4. Numeric Comparisons
Section titled “4. Numeric Comparisons”greaterThan(>) &greaterThanOrEqual(>=): Numeric value meets or exceeds threshold (e.g.stock_count > 0,rating >= 4.0).lessThan(<) &lessThanOrEqual(<=): Numeric value is at or below threshold (e.g.price_cents <= 0for free tier items).
3. Recommended Modeling Patterns
Section titled “3. Recommended Modeling Patterns”Pattern 1: Public Read of Published Content (Staff Full View)
Section titled “Pattern 1: Public Read of Published Content (Staff Full View)”Allow public visitors to see only published articles, while editorial staff see drafts and archived items:
Article.list Scenarios:├── Scenario 1 (Editorial Staff):│ └── Match User Role: ['editor', 'admin'] <- Staff see all articles (no status filter)└── Scenario 2 (Public Visitors): ├── Allow Public <- Identity rule (open to public) └── Match Resource Attribute (status == 'published') <- FETCH injects WHERE status = 'published'Pattern 2: Ownership + State Gating (Drafts-Only Deletion)
Section titled “Pattern 2: Ownership + State Gating (Drafts-Only Deletion)”Allow authors to delete their own articles, but only while in draft status. Once published or archived, only an administrator can delete them:
graph TD
subgraph "Article.delete Endpoint"
S1["Scenario 1: Match User Role (admin)"] --> Adm["Admins delete any article"]
S2["Scenario 2: Match Resource Owner + status == 'draft'"] --> Auth["Author deletes own draft"]
Blocked["Author tries to delete published article"] --> Denied["403 Forbidden"]
end
Pattern 3: Composite Multi-Attribute Gating (AND Logic)
Section titled “Pattern 3: Composite Multi-Attribute Gating (AND Logic)”Include multiple attribute rules inside the same scenario to enforce compound conditions:
Product.read Scenario (Public Active & In-Stock):├── Allow Public├── Match Resource Attribute: is_active == true└── Match Resource Attribute: stock_count > 0Both attribute rules must pass. On list actions, the engine combines them into WHERE is_active = true AND stock_count > 0.
4. HTTP Status Codes Summary
Section titled “4. HTTP Status Codes Summary”| Caller State | Resource State | Resulting HTTP Status |
|---|---|---|
| Anonymous (Public Scenario) | Resource matches attribute criteria (e.g. status == 'published') | 200 OK |
| Anonymous (Public Scenario) | Resource does not match attribute criteria (e.g. status == 'draft') | 403 Forbidden |
| Authenticated (Staff Scenario) | Resource is in any state (draft/archived) | 200 OK / 204 No Content |
| Author (Draft Scenario) | Author tries to modify/delete an archived article (status != 'archived' fails) | 403 Forbidden |
| Resource Not Found | Record ID does not exist in the database | 404 Not Found |
Next Steps
Section titled “Next Steps”- Match User Property: Attribute-based checks on the calling user session.
- Match Resource Owner: Direct ownership checks for creator-owned records.
- Match Lifecycle Status: Specialized lifecycle status matching.