App Studio
Export/Import API
The App Studio REST API provides programmatic export and import — enabling CI/CD pipeline integration, automated environment promotion, and scripted tenant provisioning. All API calls require a valid Passport JWT with admin-level scope for the target tenant.
Export API
GET /api/tenants/{tenantId}/apps/{appId}/export
// Response: 200 OK
// Content-Type: application/json
// Body: the full export bundle JSON
// Example:
curl -X GET \
-H "Authorization: Bearer {jwt_token}" \
https://api.bizfirstai.com/api/tenants/acme/apps/crm/export \
-o crm-app-export.json
// With version label and changelog (query params):
GET /api/tenants/{tenantId}/apps/{appId}/export?version=1.4.2&changelog=Release+notes+here
Import API
POST /api/tenants/{tenantId}/apps/import
Content-Type: application/json
Authorization: Bearer {jwt_token}
Request body:
{
"bundle": { ...full bundle JSON... },
"conflictStrategy": "replace", // "replace" | "merge"
"dryRun": false // true = validate only, do not apply
}
// Response: 200 OK
{
"success": true,
"appId": "crm",
"version": "1.4.2",
"created": 3, // Elements created
"updated": 12, // Elements updated
"deleted": 0, // Elements deleted (replace only)
"skipped": 0 // Validation skipped
}
// Response: 400 Bad Request (validation failure)
{
"success": false,
"errors": [
"Page 'lead-detail': breadcrumbParent 'missing-page' not found in bundle",
"Widget 'leads-grid': duplicate widgetId in pane 'main-pane'"
]
}
Dry Run — Validate Without Applying
// Use dryRun: true to validate the bundle and preview changes
// without writing anything to the database
POST /api/tenants/{tenantId}/apps/import
{
"bundle": { ... },
"conflictStrategy": "replace",
"dryRun": true
}
// Response shows what would happen:
{
"success": true,
"dryRun": true,
"appId": "crm",
"preview": {
"pagesCreated": 0,
"pagesUpdated": 8,
"widgetsCreated": 2,
"widgetsUpdated": 43,
"widgetsDeleted": 1
}
}
Required Permissions
| API | Required role |
|---|---|
| GET export | app-studio-admin or platform-admin on the tenant |
| POST import | app-studio-admin or platform-admin on the tenant |
CI/CD Pipeline Integration
# GitHub Actions — promote app to staging on tag push
name: Promote CRM App to Staging
on:
push:
tags:
- 'app-crm-v*'
jobs:
promote:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Export from Dev
run: |
curl -s -X GET \
-H "Authorization: Bearer $DEV_TOKEN" \
$DEV_API/api/tenants/acme-dev/apps/crm/export \
-o crm-bundle.json
env:
DEV_TOKEN: ${{ secrets.DEV_API_TOKEN }}
DEV_API: ${{ vars.DEV_API_URL }}
- name: Import to Staging
run: |
BUNDLE=$(cat crm-bundle.json)
curl -s -X POST \
-H "Authorization: Bearer $STAGING_TOKEN" \
-H "Content-Type: application/json" \
-d "{\"bundle\": $BUNDLE, \"conflictStrategy\": \"replace\"}" \
$STAGING_API/api/tenants/acme-staging/apps/import
env:
STAGING_TOKEN: ${{ secrets.STAGING_API_TOKEN }}
STAGING_API: ${{ vars.STAGING_API_URL }}