Imported from jeremylongshore/tons-of-skills-marketplace (
skills/.curated/flexport-enterprise-rbac/SKILL.md). Install upstream withnpx skills add jeremylongshore/tons-of-skills-marketplace --skill flexport-enterprise-rbac. Copyright stays with the author (MIT).
Flexport Enterprise RBAC
Overview
Implement role-based access control for Flexport integrations. Since Flexport API keys are scoped at the account level, RBAC is implemented in your application layer with per-role API key allocation and request filtering.
Prerequisites
- A role owner, current access matrix, least-privilege credential allocation, and periodic access-review schedule.
- Approved endpoint/data classifications and synthetic fixtures that can test authorization without a real shipment.
Output
Maintain an RBAC receipt with role, allowed operation class, policy version, access-review date, approver, and revocation outcome. Never include credentials, customer identifiers, commercial records, or documents.
Error Handling
- Deny unknown roles, paths, methods, and cross-tenant requests by default.
- Alert the policy owner on repeated authorization failures and suspend a credential if misuse is suspected.
- Preserve redacted evidence only and require review before expanding a role or endpoint policy.
Examples
Give a temporary test role access to a fictional shipment status only, attempt an invoice read, and verify it is denied. Remove the role and confirm the status access is revoked, recording only opaque test IDs and decisions.
Instructions
Step 1: Define Roles
| Role | API Key Scope | Allowed Endpoints | Use Case |
|---|---|---|---|
| Viewer | Read-only | GET /shipments, GET /products |
Dashboard users |
| Operator | Read-write | GET/POST /bookings, GET/PATCH /purchase_orders |
Ops team |
| Finance | Read invoices | GET /freight_invoices, GET /commercial_invoices |
Finance team |
| Admin | Full access | All endpoints | System administrators |
Step 2: Application-Layer RBAC
type Role = 'viewer' | 'operator' | 'finance' | 'admin';
const ROLE_PERMISSIONS: Record<Role, { methods: string[]; paths: RegExp[] }> = {
viewer: {
methods: ['GET'],
paths: [/^\/shipments/, /^\/products/, /^\/purchase_orders/],
},
operator: {
methods: ['GET', 'POST', 'PATCH'],
paths: [/^\/shipments/, /^\/bookings/, /^\/purchase_orders/, /^\/products/],
},
finance: {
methods: ['GET'],
paths: [/^\/freight_invoices/, /^\/commercial_invoices/, /^\/shipments/],
},
admin: {
methods: ['GET', 'POST', 'PATCH', 'DELETE'],
paths: [/.*/],
},
};
function checkPermission(role: Role, method: string, path: string): boolean {
const perms = ROLE_PERMISSIONS[role];
return perms.methods.includes(method) && perms.paths.some(p => p.test(path));
}
// Middleware
function rbacMiddleware(role: Role) {
return (req: Request, res: Response, next: NextFunction) => {
const flexportPath = req.params.flexportPath;
if (!checkPermission(role, req.method, `/${flexportPath}`)) {
return res.status(403).json({ error: 'Insufficient permissions' });
}
next();
};
}
Step 3: Multi-Tenant API Key Management
// Each tenant/team gets their own Flexport API key
interface TenantConfig {
tenantId: string;
flexportApiKey: string;
role: Role;
allowedShipmentPrefixes?: string[]; // Filter visible data
}
class MultiTenantFlexport {
private configs: Map<string, TenantConfig>;
async request(tenantId: string, path: string, options: RequestInit = {}) {
const config = this.configs.get(tenantId);
if (!config) throw new Error('Unknown tenant');
if (!checkPermission(config.role, options.method || 'GET', path)) {
throw new Error('Permission denied');
}
return fetch(`https://api.flexport.com${path}`, {
...options,
headers: {
'Authorization': `Bearer ${config.flexportApiKey}`,
'Flexport-Version': '2',
'Content-Type': 'application/json',
},
}).then(r => r.json());
}
}
Step 4: Audit Logging
async function auditLog(entry: {
userId: string;
role: Role;
action: string;
resource: string;
result: 'allowed' | 'denied';
}) {
await db.auditLogs.create({
data: { ...entry, timestamp: new Date(), ip: req.ip },
});
logger.info(entry, 'RBAC audit');
}
Resources
Next Steps
For migration strategies, see flexport-migration-deep-dive.