ApiKeyPermission
Junction table that links API keys to specific permissions, implementing fine-grained access control for programmatic access. While API key scopes define broad categories of access (like 'users:read'), permissions represent specific, granular rights within the system (like 'can_view_user_emails' or 'can_export_data'). This many-to-many relationship allows flexible permission assignment where the same permission can be granted to multiple API keys, and each key can have multiple permissions. This entity tracks not just what permissions are granted, but also who granted them, when they become effective, and when they expire. Temporary permissions are useful for time-limited access, like giving a contractor's API key elevated permissions only during their project. The system evaluates these permissions on every API request, combining them with scopes to determine if an action is allowed. This dual-layer approach (scopes + permissions) provides both simplicity for common cases and flexibility for complex authorization requirements. It's particularly useful when different API keys need slightly different access to the same resources.
Properties
| Property | Type | Mode | Description | Required |
|---|---|---|---|---|
| apiKeyId | uuid | stored | The API key receiving this permission | Required |
| permissionId | uuid | stored | The specific permission being granted | Required |
| grantedAt | DateTime | stored | When this permission was assigned | Required |
| grantedBy | User | stored | Administrator who granted this permission | Optional |
| reason | string | stored | Explanation for why this permission was granted Example: | Optional |
| validFrom | DateTime | stored | When this permission becomes active | Optional |
| validUntil | DateTime | stored | When this permission expires | Optional |
| conditions | string | stored | JSON conditions that must be met for permission to apply Example: | Optional |
| isActive | boolean | stored | Whether this permission grant is currently active | Optional |
| revokedAt | DateTime | stored | When this permission was revoked | Optional |
| revokedBy | User | stored | Who revoked this permission | Optional |
| revokedReason | string | stored | Why the permission was revoked | Optional |
| lastUsedAt | DateTime | stored | Last time this permission was checked | Optional |
| usageCount | integer | stored | Number of times this permission was used | Optional |
Examples
Example 1
{
"@type": "ApiKeyPermission",
"apiKeyId": "key_550e8400",
"permissionId": "perm_export_users",
"grantedAt": "2024-03-01T10:00:00Z",
"grantedBy": "admin_123",
"reason": "Monthly user data export for analytics team",
"validFrom": "2024-03-01T00:00:00Z",
"validUntil": "2024-03-31T23:59:59Z",
"conditions": "{\"rate_limit\": \"1_per_day\", \"max_records\": 10000}",
"isActive": true,
"lastUsedAt": "2024-03-15T02:00:00Z",
"usageCount": 15
}Example 2
{
"@type": "ApiKeyPermission",
"apiKeyId": "key_contractor_789",
"permissionId": "perm_delete_records",
"grantedAt": "2024-02-15T14:00:00Z",
"grantedBy": "manager_456",
"reason": "Temporary access for data cleanup project",
"validFrom": "2024-02-15T14:00:00Z",
"validUntil": "2024-02-20T18:00:00Z",
"isActive": false,
"revokedAt": "2024-02-19T16:30:00Z",
"revokedBy": "manager_456",
"revokedReason": "Project completed ahead of schedule",
"lastUsedAt": "2024-02-19T15:45:00Z",
"usageCount": 47
}