Custom Apps
Manage App Builder apps end to end: create and clone apps, read and write their draft source files, publish versions and track builds, control code sharing and end-user hosting, and read the history of Vibecode AI coding sessions.
All paths on this page are relative to https://api.autessa.com/autessa_poweruser/custom-apps-v2. Every request is a POST with a JSON body, and every ID is an opaque string. See the Poweruser API overview for authentication and conventions.
The app object
- Name
appId- Type
- string
- Description
Unique app identifier.
- Name
companyId- Type
- string
- Description
The company that owns the app.
- Name
ownerId- Type
- string
- Description
User ID of the app's owner.
- Name
appName- Type
- string
- Description
Display name.
- Name
description- Type
- string
- Description
What the app does.
- Name
sharingLevel- Type
- string
- Description
Who can see and edit the source code:
PRIVATE,SPECIFIC_MEMBER, orCOMPANY.
- Name
companyPermissionLevel- Type
- string
- Description
Access level every company member gets when
sharingLevelisCOMPANY:READ,WRITE,PUBLISH, orADMIN.
- Name
createdAt- Type
- string
- Description
ISO-8601 creation timestamp.
- Name
updatedAt- Type
- string
- Description
ISO-8601 timestamp of the last update.
- Name
latestVersion- Type
- integer
- Description
Highest version number created by
/publish, or absent if never published.
- Name
publishedVersion- Type
- integer
- Description
The currently live published version, or absent if no build has succeeded yet.
- Name
userAccessLevel- Type
- string
- Description
The calling user's effective access level on the app:
READ,WRITE,PUBLISH, orADMIN.
- Name
hostingMode- Type
- string
- Description
How end users access the deployed app — orthogonal to
sharingLevel:DEFAULT(Autessa login required),PUBLIC(anyone with the URL),AUTH_CODE(shared access code),CUSTOM_AUTH(app-specific accounts backed by an AutessaDB table), orTOKEN(a private access link per person).
- Name
publicSlug- Type
- string
- Description
URL slug for non-default hosting modes.
- Name
publicUrl- Type
- string
- Description
Full end-user URL derived from the slug, when one is set.
- Name
hasAuthCode- Type
- boolean
- Description
Whether an
AUTH_CODEaccess code is stored. The code itself is hashed and never returned.
- Name
authTableId- Type
- string
- Description
The AutessaDB table backing
CUSTOM_AUTHsignups, when provisioned.
- Name
authPageConfig- Type
- string
- Description
JSON string with auth page theming for
CUSTOM_AUTHhosting.
- Name
requireEmailVerification- Type
- boolean
- Description
Whether
CUSTOM_AUTHsignups must confirm an emailed code before the account is created. Absent for apps not usingCUSTOM_AUTH.
- Name
enabledProviders- Type
- array<string>
- Description
The sign-in methods a
CUSTOM_AUTHapp offers: any ofPASSWORD,GOOGLE, andMICROSOFT. Absent for apps not usingCUSTOM_AUTH.
- Name
hostingPermissions- Type
- string
- Description
JSON string describing which company resources the hosted app may call (tables, agents, tools, managers, poweruser endpoints, e-sign envelopes). Set as a structured object via
/share; returned here as the stored JSON string.
{
"appId": "V1StGXR8Z5",
"companyId": "cP2mK7dX4v",
"ownerId": "uB7nT2wQ9k",
"appName": "Field Inspection Portal",
"description": "Logs site inspections against the Inspections table.",
"sharingLevel": "SPECIFIC_MEMBER",
"createdAt": "2026-05-12T09:30:00",
"updatedAt": "2026-06-28T17:42:10",
"latestVersion": 5,
"publishedVersion": 4,
"userAccessLevel": "ADMIN",
"hostingMode": "AUTH_CODE",
"publicSlug": "field-inspections",
"publicUrl": "https://builder.autessa.com/app/field-inspections",
"hasAuthCode": true,
"hostingPermissions": "{\"tables\":[{\"tableId\":\"tQ6bF3jN8s\",\"canRead\":true,\"canWrite\":true,\"canDelete\":false}],\"esignatureActsAsUser\":false}"
}
Build lifecycle and access levels
Every app has a single draft workspace of source files, edited through
the file endpoints (and the Vibecode assistant in the UI).
/publish snapshots the draft as a new numbered version and
triggers an asynchronous build — the publish response returns
immediately with buildStatus: "BUILDING". Poll
/build-status until the build reaches SUCCESS or
FAILED; on the first successful check the version is marked PUBLISHED
and the CDN cache is invalidated, so /build-url and the
app's public slug serve the new build.
Endpoints enforce the caller's access level on the app (the poweruser key acts as its linked user):
| Operation | Required access |
|---|---|
get, all, clone (source app), build-status, versions, build-files, build-url, files/list, files/get, files/get-batch, refresh-libraries, get-sharing-details, vibecode/* | Any access (READ or higher) |
update, files/create, files/update, files/delete, files/rename, files/save-batch | WRITE, PUBLISH, or ADMIN |
publish | PUBLISH or ADMIN |
delete, share, transfer-ownership | ADMIN |
check-slug performs no per-app access check — it only validates the slug.
Create an app
/custom-apps-v2/createCreates a new app owned by the linked user and bootstraps its draft workspace with the chosen starter template, including the read-only Autessa library files. The response lists every bootstrapped file path.
Request parameters
- Name
appName- Type
- string
- Description
Display name.
- Name
description- Type
- string
- Description
What the app does.
- Name
templateType- Type
- string
- Description
Starter template for the new app. One of
BOOTSTRAP(minimal starter),LANDING_PAGE(marketing site with hero, features, pricing, and FAQ sections),SAAS_APP(product-app shell with a built-in UI component kit and sample pages), orDASHBOARD(analytics starter with KPI tiles, charts, and data tables). Defaults toBOOTSTRAPwhen omitted, matching the previous behavior.
Response
- Name
app- Type
- App
- Description
The newly created app object.
- Name
files- Type
- array<string>
- Description
Paths of the bootstrapped template files.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
- cURL
- JavaScript
- Python
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/create \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appName": "Field Inspection Portal",
"description": "Logs site inspections against the Inspections table.",
"templateType": "SAAS_APP"
}'
const response = await fetch(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/create',
{
method: 'POST',
headers: {
'Authorization': process.env.POWERUSER_KEY,
'Content-Type': 'application/json'
},
body: JSON.stringify({
appName: 'Field Inspection Portal',
description: 'Logs site inspections against the Inspections table.',
templateType: 'SAAS_APP'
})
}
);
const { app, files } = await response.json();
console.log(app.appId, files.length);
import os
import requests
response = requests.post(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/create',
headers={'Authorization': os.environ['POWERUSER_KEY']},
json={
'appName': 'Field Inspection Portal',
'description': 'Logs site inspections against the Inspections table.',
'templateType': 'SAAS_APP'
}
)
app = response.json()['app']
{
"app": {
"appId": "V1StGXR8Z5",
"companyId": "cP2mK7dX4v",
"ownerId": "uB7nT2wQ9k",
"appName": "Field Inspection Portal",
"description": "Logs site inspections against the Inspections table.",
"sharingLevel": "PRIVATE",
"userAccessLevel": "ADMIN",
"hostingMode": "DEFAULT",
"hasAuthCode": false
},
"files": [
"index.html",
"src/App.jsx",
"src/main.jsx",
"src/autessa/autessa-client.js",
"package.json"
],
"errors": []
}
Get an app
/custom-apps-v2/getRetrieves an app and the file paths in its draft workspace. Calling this
also refreshes the app's src/autessa/ library files to the current
platform version (same effect as /refresh-libraries).
Request parameters
- Name
appId- Type
- string
- Description
The app to fetch.
Response
- Name
app- Type
- App
- Description
The app object.
- Name
files- Type
- array<string>
- Description
Paths of every file in the draft workspace.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
- cURL
- JavaScript
- Python
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/get \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
const response = await fetch(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/get',
{
method: 'POST',
headers: {
'Authorization': process.env.POWERUSER_KEY,
'Content-Type': 'application/json'
},
body: JSON.stringify({ appId: 'V1StGXR8Z5' })
}
);
const { app, files } = await response.json();
import os
import requests
response = requests.post(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/get',
headers={'Authorization': os.environ['POWERUSER_KEY']},
json={'appId': 'V1StGXR8Z5'}
)
data = response.json()
{
"app": {
"appId": "V1StGXR8Z5",
"appName": "Field Inspection Portal",
"latestVersion": 5,
"publishedVersion": 4,
"userAccessLevel": "ADMIN"
},
"files": [
"index.html",
"src/App.jsx",
"src/components/InspectionForm.jsx",
"src/autessa/autessa-client.js"
],
"errors": []
}
List all apps
/custom-apps-v2/allLists every app the linked user can access — owned, shared with them
directly, or shared with the company. Each entry is a full
app object with userAccessLevel set to the caller's
access on that app.
Request parameters
None — send an empty object {}.
Response
- Name
apps- Type
- array<App>
- Description
The accessible apps.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/all \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{}'
{
"apps": [
{
"appId": "V1StGXR8Z5",
"appName": "Field Inspection Portal",
"sharingLevel": "SPECIFIC_MEMBER",
"publishedVersion": 4,
"userAccessLevel": "ADMIN",
"hostingMode": "AUTH_CODE"
},
{
"appId": "aH5cJ1yD7q",
"appName": "Quote Calculator",
"sharingLevel": "COMPANY",
"userAccessLevel": "READ",
"hostingMode": "DEFAULT"
}
],
"errors": []
}
Update an app
/custom-apps-v2/updateUpdates the app's name and description. This endpoint only touches
metadata — edit source code with the file endpoints, and
change sharing or hosting with /share.
Requires WRITE, PUBLISH, or ADMIN access.
Request parameters
- Name
appId- Type
- string
- Description
The app to update.
- Name
appName- Type
- string
- Description
New display name.
- Name
description- Type
- string
- Description
New description.
Response
- Name
app- Type
- App
- Description
The updated app object.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/update \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"appName": "Field Inspection Portal",
"description": "Logs and reviews site inspections."
}'
{
"app": {
"appId": "V1StGXR8Z5",
"appName": "Field Inspection Portal",
"description": "Logs and reviews site inspections.",
"updatedAt": "2026-07-02T10:15:00"
},
"errors": []
}
Delete an app
/custom-apps-v2/deletePermanently deletes the app — its draft workspace, version snapshots, and build outputs are all removed. This cannot be undone.
Requires ADMIN access on the app.
Request parameters
- Name
appId- Type
- string
- Description
The app to delete.
Response
- Name
success- Type
- boolean
- Description
truewhen the app was deleted.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/delete \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
{
"success": true,
"errors": []
}
Clone an app
/custom-apps-v2/cloneCreates a new private app owned by the calling user, copying the source app's draft files. Version history, sharing settings, and hosting configuration are not copied. Any access level on the source app is sufficient.
Request parameters
- Name
appId- Type
- string
- Description
The source app to clone.
- Name
appName- Type
- string
- Description
Name for the clone. Defaults to the source name with
" (Copy)"appended.
Response
Same shape as /create:
- Name
app- Type
- App
- Description
The new app object (private, owned by the caller).
- Name
files- Type
- array<string>
- Description
Paths of the copied draft files.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/clone \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"appName": "Field Inspection Portal (Staging)"
}'
{
"app": {
"appId": "nW2yE9gK4t",
"appName": "Field Inspection Portal (Staging)",
"sharingLevel": "PRIVATE",
"userAccessLevel": "ADMIN",
"hostingMode": "DEFAULT"
},
"files": [
"index.html",
"src/App.jsx",
"src/components/InspectionForm.jsx"
],
"errors": []
}
Publish an app
/custom-apps-v2/publishSnapshots the draft workspace as a new numbered version and triggers an
asynchronous build. The response returns immediately with
buildStatus: "BUILDING" — poll /build-status to follow
the build. The version only goes live once its build succeeds.
Requires PUBLISH or ADMIN access.
Request parameters
- Name
appId- Type
- string
- Description
The app to publish.
Response
- Name
app- Type
- App
- Description
The app object.
- Name
version- Type
- integer
- Description
The new version number.
- Name
buildId- Type
- string
- Description
Identifier of the triggered build.
- Name
buildStatus- Type
- string
- Description
Always
"BUILDING"on a successful publish.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred (for example a failed build trigger — the version is rolled back in that case).
- cURL
- JavaScript
- Python
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/publish \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
const base = 'https://api.autessa.com/autessa_poweruser/custom-apps-v2';
const headers = {
'Authorization': process.env.POWERUSER_KEY,
'Content-Type': 'application/json'
};
const publish = await fetch(`${base}/publish`, {
method: 'POST',
headers,
body: JSON.stringify({ appId: 'V1StGXR8Z5' })
});
const { version } = await publish.json();
// Poll until the build finishes
let status;
do {
await new Promise((r) => setTimeout(r, 5000));
const check = await fetch(`${base}/build-status`, {
method: 'POST',
headers,
body: JSON.stringify({ appId: 'V1StGXR8Z5', version })
});
status = await check.json();
} while (status.status === 'BUILDING');
console.log(status.status, status.outputUrl);
import os
import time
import requests
base = 'https://api.autessa.com/autessa_poweruser/custom-apps-v2'
headers = {'Authorization': os.environ['POWERUSER_KEY']}
version = requests.post(f'{base}/publish', headers=headers,
json={'appId': 'V1StGXR8Z5'}).json()['version']
while True:
time.sleep(5)
status = requests.post(f'{base}/build-status', headers=headers,
json={'appId': 'V1StGXR8Z5', 'version': version}).json()
if status['status'] != 'BUILDING':
break
print(status['status'])
{
"app": {
"appId": "V1StGXR8Z5",
"appName": "Field Inspection Portal",
"latestVersion": 5,
"publishedVersion": 4
},
"version": 6,
"buildId": "3f6c1a9e-8b2d-4e07-9c41-5a12de88f0b3",
"buildStatus": "BUILDING",
"errors": []
}
Get build status
/custom-apps-v2/build-statusReturns the build state of a version. Omit version to check the latest
one. When the latest version's build first reports SUCCESS, this call
also marks the version as PUBLISHED and invalidates the CDN cache so the
new build is served.
Request parameters
- Name
appId- Type
- string
- Description
The app to check.
- Name
version- Type
- integer
- Description
Version to check. Defaults to the latest version.
Response
- Name
version- Type
- integer
- Description
The version that was checked. Absent when the app has no versions yet.
- Name
buildId- Type
- string
- Description
Identifier of the build, when available.
- Name
status- Type
- string
- Description
BUILDING,SUCCESS,FAILED, orNOT_STARTED.
- Name
error- Type
- string
- Description
Build error output, when
statusisFAILED.
- Name
startedAt- Type
- string
- Description
When the build started.
- Name
completedAt- Type
- string
- Description
When the build finished.
- Name
outputUrl- Type
- string
- Description
URL of the published app, present when
statusisSUCCESS.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/build-status \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5", "version": 6 }'
{
"version": 6,
"status": "SUCCESS",
"startedAt": "2026-07-02T10:20:04",
"completedAt": "2026-07-02T10:21:37",
"outputUrl": "https://apps.autessa.com/custom-apps-v2/.../published/index.html",
"errors": []
}
List versions
/custom-apps-v2/versionsLists all versions of the app, newest first, with each version's state and current build status.
Request parameters
- Name
appId- Type
- string
- Description
The app to inspect.
Response
- Name
versions- Type
- array<Version>
- Description
Version records, newest first.
- Name
versions[].versionId- Type
- string
- Description
Unique version identifier.
- Name
versions[].version- Type
- integer
- Description
The version number.
- Name
versions[].state- Type
- string
- Description
DRAFT,PUBLISHED, orARCHIVED.
- Name
versions[].buildId- Type
- string
- Description
Identifier of the version's build.
- Name
versions[].buildStatus- Type
- string
- Description
BUILDING,SUCCESS,FAILED, orNOT_STARTED.
- Name
versions[].sourceS3Path- Type
- string
- Description
Storage path of the version's source snapshot.
- Name
versions[].buildS3Path- Type
- string
- Description
Storage path of the build output, when built.
- Name
versions[].createdAt- Type
- string
- Description
ISO-8601 creation timestamp.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/versions \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
{
"versions": [
{
"versionId": "vJ8pL4sB6m",
"version": 6,
"state": "PUBLISHED",
"buildId": "3f6c1a9e-8b2d-4e07-9c41-5a12de88f0b3",
"buildStatus": "SUCCESS",
"sourceS3Path": "custom-apps-v2/.../versions/6/source/",
"buildS3Path": "custom-apps-v2/.../versions/6/build/",
"createdAt": "2026-07-02T10:19:58"
},
{
"versionId": "vC3xR7hN1z",
"version": 5,
"state": "ARCHIVED",
"buildStatus": "SUCCESS",
"createdAt": "2026-06-28T17:40:12"
}
],
"errors": []
}
Get build files
/custom-apps-v2/build-filesLists the compiled output files of a build, each with a presigned download
URL. Omit version to read the latest published build; pass a version to
read a specific one (fails with an error if that version's build did not
succeed).
Request parameters
- Name
appId- Type
- string
- Description
The app whose build to read.
- Name
version- Type
- integer
- Description
Version whose build output to list. Defaults to the latest published version.
Response
- Name
version- Type
- integer
- Description
The version that was read.
- Name
files- Type
- array<BuildFile>
- Description
Build output files. Each has
path(relative to the build root),url(a presigned download URL),contentType, and optionallysizein bytes.
- Name
expiresInSeconds- Type
- integer
- Description
How long the presigned URLs stay valid (currently one hour).
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/build-files \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
{
"version": 6,
"files": [
{
"path": "index.html",
"url": "https://s3.amazonaws.com/...&X-Amz-Expires=3600",
"contentType": "text/html"
},
{
"path": "assets/index-Bx91k2.js",
"url": "https://s3.amazonaws.com/...&X-Amz-Expires=3600",
"contentType": "application/javascript"
}
],
"expiresInSeconds": 3600,
"errors": []
}
Get a preview URL
/custom-apps-v2/build-urlReturns a signed URL for opening the latest published build in a browser. The URL carries a short-lived token that the CDN validates before serving the app. Fails with an error if the app has no published version.
Request parameters
- Name
appId- Type
- string
- Description
The app to open.
Response
- Name
previewUrl- Type
- string
- Description
Signed URL that loads the published app.
- Name
expiresAt- Type
- integer
- Description
Unix epoch seconds when the URL stops being accepted.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/build-url \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
{
"previewUrl": "https://apps.autessa.com/auth?token=...&redirect=/custom-apps-v2/.../published/index.html",
"expiresAt": 1783420800,
"errors": []
}
List files
/custom-apps-v2/files/listLists every file path in the app's draft workspace, plus the paths of the
platform-managed Autessa library files (under src/autessa/). Library
files are refreshed to the current platform version by this call and are
read-only — writes to them are managed by the platform, not the file
endpoints.
Request parameters
- Name
appId- Type
- string
- Description
The app whose files to list.
Response
- Name
files- Type
- array<string>
- Description
All file paths in the draft workspace.
- Name
readOnlyFiles- Type
- array<string>
- Description
Paths of the platform-managed Autessa library files.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/list \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
{
"files": [
"index.html",
"src/App.jsx",
"src/components/InspectionForm.jsx",
"src/autessa/autessa-client.js"
],
"readOnlyFiles": [
"src/autessa/autessa-client.js"
],
"errors": []
}
Get a file
/custom-apps-v2/files/getReads one file's content from the draft workspace.
Request parameters
- Name
appId- Type
- string
- Description
The app the file belongs to.
- Name
filePath- Type
- string
- Description
Path of the file to read (as returned by
/files/list).
Response
- Name
filePath- Type
- string
- Description
The requested path.
- Name
content- Type
- string
- Description
The file's content.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred (for example
"File not found").
- cURL
- JavaScript
- Python
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/get \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"filePath": "src/App.jsx"
}'
const response = await fetch(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/get',
{
method: 'POST',
headers: {
'Authorization': process.env.POWERUSER_KEY,
'Content-Type': 'application/json'
},
body: JSON.stringify({ appId: 'V1StGXR8Z5', filePath: 'src/App.jsx' })
}
);
const { content } = await response.json();
import os
import requests
response = requests.post(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/get',
headers={'Authorization': os.environ['POWERUSER_KEY']},
json={'appId': 'V1StGXR8Z5', 'filePath': 'src/App.jsx'}
)
content = response.json()['content']
{
"filePath": "src/App.jsx",
"content": "import React from 'react';\n\nexport default function App() { ... }",
"errors": []
}
Get files in batch
/custom-apps-v2/files/get-batchReads several files in one call.
Request parameters
- Name
appId- Type
- string
- Description
The app the files belong to.
- Name
filePaths- Type
- array<string>
- Description
Paths of the files to read.
Response
- Name
files- Type
- object
- Description
Map of file path to content.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/get-batch \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"filePaths": ["src/App.jsx", "index.html"]
}'
{
"files": {
"src/App.jsx": "import React from 'react'; ...",
"index.html": "<!doctype html> ..."
},
"errors": []
}
Create a file
/custom-apps-v2/files/createWrites a new file into the draft workspace. If the path already exists its
content is replaced — files/create and /files/update
behave identically.
Requires WRITE, PUBLISH, or ADMIN access.
Request parameters
- Name
appId- Type
- string
- Description
The app to write into.
- Name
filePath- Type
- string
- Description
Path of the file to create.
- Name
content- Type
- string
- Description
The file's content.
Response
- Name
success- Type
- boolean
- Description
truewhen the file was written.
- Name
filePath- Type
- string
- Description
The written path.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/create \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"filePath": "src/components/StatusBadge.jsx",
"content": "export default function StatusBadge({ status }) { ... }"
}'
{
"success": true,
"filePath": "src/components/StatusBadge.jsx",
"errors": []
}
Update a file
/custom-apps-v2/files/updateReplaces a file's content in the draft workspace. Draft edits never affect
published versions until you /publish.
Requires WRITE, PUBLISH, or ADMIN access.
Request parameters
- Name
appId- Type
- string
- Description
The app to write into.
- Name
filePath- Type
- string
- Description
Path of the file to update.
- Name
content- Type
- string
- Description
The new content.
Response
- Name
success- Type
- boolean
- Description
truewhen the file was written.
- Name
filePath- Type
- string
- Description
The written path.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/update \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"filePath": "src/App.jsx",
"content": "import React from 'react'; // updated ..."
}'
{
"success": true,
"filePath": "src/App.jsx",
"errors": []
}
Delete a file
/custom-apps-v2/files/deleteRemoves a file from the draft workspace.
Requires WRITE, PUBLISH, or ADMIN access.
Request parameters
- Name
appId- Type
- string
- Description
The app the file belongs to.
- Name
filePath- Type
- string
- Description
Path of the file to delete.
Response
- Name
success- Type
- boolean
- Description
truewhen the file was deleted.
- Name
filePath- Type
- string
- Description
The deleted path.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/delete \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"filePath": "src/components/StatusBadge.jsx"
}'
{
"success": true,
"filePath": "src/components/StatusBadge.jsx",
"errors": []
}
Rename a file
/custom-apps-v2/files/renameMoves a file to a new path in the draft workspace.
Requires WRITE, PUBLISH, or ADMIN access.
Request parameters
- Name
appId- Type
- string
- Description
The app the file belongs to.
- Name
oldPath- Type
- string
- Description
Current path of the file.
- Name
newPath- Type
- string
- Description
New path for the file.
Response
- Name
success- Type
- boolean
- Description
truewhen the file was renamed.
- Name
filePath- Type
- string
- Description
The file's new path.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/rename \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"oldPath": "src/Badge.jsx",
"newPath": "src/components/Badge.jsx"
}'
{
"success": true,
"filePath": "src/components/Badge.jsx",
"errors": []
}
Save files in batch
/custom-apps-v2/files/save-batchWrites several files in one call — the batch equivalent of
/files/create / /files/update. Existing
paths are overwritten, new paths are created.
Requires WRITE, PUBLISH, or ADMIN access.
Request parameters
- Name
appId- Type
- string
- Description
The app to write into.
- Name
files- Type
- object
- Description
Map of file path to content.
Response
- Name
savedPaths- Type
- array<string>
- Description
Paths that were written.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
- cURL
- JavaScript
- Python
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/save-batch \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"files": {
"src/App.jsx": "import React from ...",
"src/api.js": "export async function listInspections() { ... }"
}
}'
const response = await fetch(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/save-batch',
{
method: 'POST',
headers: {
'Authorization': process.env.POWERUSER_KEY,
'Content-Type': 'application/json'
},
body: JSON.stringify({
appId: 'V1StGXR8Z5',
files: {
'src/App.jsx': 'import React from ...',
'src/api.js': 'export async function listInspections() { ... }'
}
})
}
);
const { savedPaths } = await response.json();
import os
import requests
response = requests.post(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/files/save-batch',
headers={'Authorization': os.environ['POWERUSER_KEY']},
json={
'appId': 'V1StGXR8Z5',
'files': {
'src/App.jsx': 'import React from ...',
'src/api.js': 'export async function listInspections() { ... }'
}
}
)
saved = response.json()['savedPaths']
{
"savedPaths": ["src/App.jsx", "src/api.js"],
"errors": []
}
Refresh libraries
/custom-apps-v2/refresh-librariesRewrites the app's src/autessa/ library files with the current platform
versions and removes legacy copies from old locations. This also happens
automatically on /get and /files/list — call
it explicitly when you want to force a refresh without another read.
Request parameters
- Name
appId- Type
- string
- Description
The app whose libraries to refresh.
Response
- Name
refreshedFiles- Type
- array<string>
- Description
Paths of the library files that were rewritten.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/refresh-libraries \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
{
"refreshedFiles": [
"src/autessa/autessa-client.js"
],
"errors": []
}
Share an app
/custom-apps-v2/shareConfigures two independent things in one call: code sharing (which company members can see and edit the source) and hosting mode (how end users access the deployed app). Send only the parts you want to change — fields left out are untouched.
Non-default hosting modes (PUBLIC, AUTH_CODE, CUSTOM_AUTH, TOKEN) require a
valid, available publicSlug — check it first with
/check-slug. Switching to CUSTOM_AUTH provisions an
AutessaDB auth table for the app's end users; this is idempotent, so
re-enabling CUSTOM_AUTH reuses the existing table and keeps signed-up
users. Set requireEmailVerification to make new signups confirm an emailed
code before the account is created, and enabledProviders to choose between
email and password, Google, and Microsoft sign-in. Switching to TOKEN
provisions a separate AutessaDB table for the people who get access links;
switching modes never deletes either table. Access links themselves are
managed in the App Builder. An AUTH_CODE code is stored hashed and never
returned.
Requires ADMIN access on the app.
Request parameters
- Name
appId- Type
- string
- Description
The app to configure.
- Name
sharingLevel- Type
- string
- Description
Code sharing level:
PRIVATE,SPECIFIC_MEMBER, orCOMPANY.
- Name
companyPermissionLevel- Type
- string
- Description
When
sharingLevelisCOMPANY, the access level every member gets:READ,WRITE,PUBLISH, orADMIN.
- Name
usersToAdd- Type
- array<UserShare>
- Description
When
sharingLevelisSPECIFIC_MEMBER, users to grant access. Each entry:userId(string), optionaluserEmail, andaccessLevel.
- Name
usersToRemove- Type
- array<UserShare>
- Description
Users whose access to revoke, same entry shape.
- Name
hostingMode- Type
- string
- Description
DEFAULT,PUBLIC,AUTH_CODE,CUSTOM_AUTH, orTOKEN.
- Name
authCode- Type
- string
- Description
The shared access code, when
hostingModeisAUTH_CODE. Stored hashed.
- Name
publicSlug- Type
- string
- Description
URL slug for non-default hosting modes. Must be valid and available.
- Name
hostingPermissions- Type
- object
- Description
Which company resources the hosted app may call on behalf of end users:
tables(array oftableId+canRead/canWrite/canDelete),agentIds,toolIds,managerIds(arrays of ID strings),allowedPoweruserEndpoints(array of endpoint paths),envelopes(array ofenvelopeId+level), andesignatureActsAsUser(boolean).
- Name
authTableName- Type
- string
- Description
Name for the AutessaDB auth table provisioned for
CUSTOM_AUTH.
- Name
authPageConfig- Type
- string
- Description
JSON string with auth page theming for
CUSTOM_AUTH. May also be sent on its own, without ahostingModechange.
- Name
requireEmailVerification- Type
- boolean
- Description
For
CUSTOM_AUTH: require new signups to confirm a code emailed to their address before the account is created. Defaults tofalse. May be sent on its own, without ahostingModechange. Omit to leave the current setting alone. Accounts that already exist are unaffected when this is switched on.
- Name
enabledProviders- Type
- array<string>
- Description
For
CUSTOM_AUTH: the sign-in methods to offer, any ofPASSWORD,GOOGLE, andMICROSOFT. Must name at least one. Omit to leave the current methods alone. New apps offerPASSWORDonly.
Response
- Name
sharingLevel- Type
- string
- Description
The resulting code sharing level.
- Name
companyPermissionLevel- Type
- string
- Description
The resulting company-wide access level, when shared with the company.
- Name
hostingMode- Type
- string
- Description
The resulting hosting mode.
- Name
sharedUsers- Type
- array<UserShare>
- Description
The resulting per-user grants:
userEmail,userId,accessLevel.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred (for example
"publicSlug is already taken").
- cURL
- JavaScript
- Python
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/share \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"sharingLevel": "SPECIFIC_MEMBER",
"usersToAdd": [
{ "userId": "uB7nT2wQ9k", "accessLevel": "WRITE" }
],
"hostingMode": "AUTH_CODE",
"authCode": "site-crew-2026",
"publicSlug": "field-inspections",
"hostingPermissions": {
"tables": [
{ "tableId": "tQ6bF3jN8s", "canRead": true, "canWrite": true, "canDelete": false }
],
"agentIds": ["gD4vM8kP1c"],
"esignatureActsAsUser": false
}
}'
const response = await fetch(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/share',
{
method: 'POST',
headers: {
'Authorization': process.env.POWERUSER_KEY,
'Content-Type': 'application/json'
},
body: JSON.stringify({
appId: 'V1StGXR8Z5',
sharingLevel: 'SPECIFIC_MEMBER',
usersToAdd: [{ userId: 'uB7nT2wQ9k', accessLevel: 'WRITE' }],
hostingMode: 'AUTH_CODE',
authCode: 'site-crew-2026',
publicSlug: 'field-inspections'
})
}
);
const { hostingMode, sharedUsers } = await response.json();
import os
import requests
response = requests.post(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/share',
headers={'Authorization': os.environ['POWERUSER_KEY']},
json={
'appId': 'V1StGXR8Z5',
'sharingLevel': 'SPECIFIC_MEMBER',
'usersToAdd': [{'userId': 'uB7nT2wQ9k', 'accessLevel': 'WRITE'}],
'hostingMode': 'AUTH_CODE',
'authCode': 'site-crew-2026',
'publicSlug': 'field-inspections'
}
)
data = response.json()
{
"sharingLevel": "SPECIFIC_MEMBER",
"hostingMode": "AUTH_CODE",
"sharedUsers": [
{
"userEmail": "sam@acme.com",
"userId": "uB7nT2wQ9k",
"accessLevel": "WRITE"
}
],
"errors": []
}
Check slug availability
/custom-apps-v2/check-slugChecks whether a public slug is valid and free before you commit to it in
/share. Pass appId so the app's own current slug counts
as available. A race with another caller can still lose the slug between
check and share — /share re-validates and returns
"publicSlug is already taken" in that case.
Request parameters
- Name
publicSlug- Type
- string
- Description
The slug to check.
- Name
appId- Type
- string
- Description
The app the slug is intended for; excludes that app's existing slug from the availability check.
Response
- Name
available- Type
- boolean
- Description
Whether the slug can be used.
- Name
reason- Type
- string
- Description
When
availableisfalse:"empty","invalid_format", or"taken".
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/check-slug \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"publicSlug": "field-inspections"
}'
{
"available": true,
"errors": []
}
Transfer ownership
/custom-apps-v2/transfer-ownershipTransfers the app to another member of the company.
Requires ADMIN access on the app.
Request parameters
- Name
appId- Type
- string
- Description
The app to transfer.
- Name
newOwnerId- Type
- string
- Description
User ID of the new owner.
Response
- Name
app- Type
- App
- Description
The updated app object with the new
ownerId.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/transfer-ownership \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{
"appId": "V1StGXR8Z5",
"newOwnerId": "uB7nT2wQ9k"
}'
{
"app": {
"appId": "V1StGXR8Z5",
"ownerId": "uB7nT2wQ9k",
"appName": "Field Inspection Portal"
},
"errors": []
}
Get sharing details
/custom-apps-v2/get-sharing-detailsReturns the app's code sharing configuration, hosting mode, and the calling user's own access level.
Request parameters
- Name
appId- Type
- string
- Description
The app to inspect.
Response
- Name
sharingLevel- Type
- string
- Description
PRIVATE,SPECIFIC_MEMBER, orCOMPANY.
- Name
companyPermissionLevel- Type
- string
- Description
Access level granted company-wide, when
sharingLevelisCOMPANY.
- Name
hostingMode- Type
- string
- Description
DEFAULT,PUBLIC,AUTH_CODE, orCUSTOM_AUTH.
- Name
sharedWith- Type
- array<UserShare>
- Description
Per-user grants:
userEmail,userId,accessLevel.
- Name
userAccessLevel- Type
- string
- Description
The calling user's effective access level.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/get-sharing-details \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5" }'
{
"sharingLevel": "SPECIFIC_MEMBER",
"hostingMode": "AUTH_CODE",
"sharedWith": [
{
"userEmail": "sam@acme.com",
"userId": "uB7nT2wQ9k",
"accessLevel": "WRITE"
}
],
"userAccessLevel": "ADMIN",
"errors": []
}
List Vibecode sessions
/custom-apps-v2/vibecode/sessionsLists the calling user's Vibecode AI assistant sessions for an app, newest first, capped at the 10 most recent. The interactive Vibecode chat itself is UI-only (a WebSocket in the App Builder) and is not exposed through the Poweruser API — these endpoints are read-only session history.
By default only open sessions are returned; set includeClosed to also see
finished ones.
Request parameters
- Name
appId- Type
- string
- Description
The app whose sessions to list.
- Name
includeClosed- Type
- boolean
- Description
Also include
CLOSEDsessions. Defaults tofalse(active sessions only).
Response
- Name
sessions- Type
- array<VibecodeSession>
- Description
Session records, newest first (max 10).
- Name
sessions[].conversationId- Type
- string
- Description
Session identifier — pass to
/vibecode/session.
- Name
sessions[].appId- Type
- string
- Description
The app the session belongs to.
- Name
sessions[].state- Type
- string
- Description
ACTIVE,PENDING_CONFIRMATION(the AI proposed changes awaiting user confirmation), orCLOSED.
- Name
sessions[].createdAt- Type
- string
- Description
ISO-8601 creation timestamp.
- Name
sessions[].updatedAt- Type
- string
- Description
ISO-8601 timestamp of the last activity.
- Name
sessions[].closedAt- Type
- string
- Description
When the session was closed, if it was.
- Name
sessions[].summary- Type
- string
- Description
Short AI-generated summary, set when the session closes.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred.
- cURL
- JavaScript
- Python
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/vibecode/sessions \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "appId": "V1StGXR8Z5", "includeClosed": true }'
const response = await fetch(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/vibecode/sessions',
{
method: 'POST',
headers: {
'Authorization': process.env.POWERUSER_KEY,
'Content-Type': 'application/json'
},
body: JSON.stringify({ appId: 'V1StGXR8Z5', includeClosed: true })
}
);
const { sessions } = await response.json();
import os
import requests
response = requests.post(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/vibecode/sessions',
headers={'Authorization': os.environ['POWERUSER_KEY']},
json={'appId': 'V1StGXR8Z5', 'includeClosed': True}
)
sessions = response.json()['sessions']
{
"sessions": [
{
"conversationId": "vibe_9f2c7a1d4e",
"appId": "V1StGXR8Z5",
"state": "CLOSED",
"createdAt": "2026-06-30T14:02:11",
"updatedAt": "2026-06-30T14:38:47",
"closedAt": "2026-06-30T14:38:47",
"summary": "Added inspection photo upload form"
}
],
"errors": []
}
Get a Vibecode session
/custom-apps-v2/vibecode/sessionFetches one Vibecode session with its full conversation log — user messages, assistant replies, and every tool call the assistant made against the app's files. Sessions are personal: only the user who ran the session can read it, even if others have access to the app.
Request parameters
- Name
conversationId- Type
- string
- Description
The session to fetch (from
/vibecode/sessions).
Response
- Name
session- Type
- VibecodeSession
- Description
The session record, same shape as entries in
/vibecode/sessions.
- Name
logs- Type
- array<VibecodeLog>
- Description
The conversation log, in order.
- Name
logs[].logType- Type
- string
- Description
USER_MESSAGE,ASSISTANT_MESSAGE,TOOL_CALL,TOOL_RESULT, orSYSTEM.
- Name
logs[].content- Type
- string
- Description
Message text, for user and assistant entries.
- Name
logs[].toolName- Type
- string
- Description
Tool name, for
TOOL_CALLandTOOL_RESULTentries.
- Name
logs[].toolCallId- Type
- string
- Description
Matches a
TOOL_CALLto itsTOOL_RESULT.
- Name
logs[].toolArguments- Type
- string
- Description
Tool arguments as a JSON string, for
TOOL_CALLentries.
- Name
logs[].toolResult- Type
- string
- Description
The tool's result, for
TOOL_RESULTentries.
- Name
logs[].timestamp- Type
- string
- Description
ISO-8601 timestamp of the entry.
- Name
errors- Type
- array<string>
- Description
Error messages, if any occurred (for example
"Conversation not found"or"Access denied").
- cURL
- JavaScript
- Python
curl https://api.autessa.com/autessa_poweruser/custom-apps-v2/vibecode/session \
-X POST \
-H "Authorization: $POWERUSER_KEY" \
-H "Content-Type: application/json" \
-d '{ "conversationId": "vibe_9f2c7a1d4e" }'
const response = await fetch(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/vibecode/session',
{
method: 'POST',
headers: {
'Authorization': process.env.POWERUSER_KEY,
'Content-Type': 'application/json'
},
body: JSON.stringify({ conversationId: 'vibe_9f2c7a1d4e' })
}
);
const { session, logs } = await response.json();
import os
import requests
response = requests.post(
'https://api.autessa.com/autessa_poweruser/custom-apps-v2/vibecode/session',
headers={'Authorization': os.environ['POWERUSER_KEY']},
json={'conversationId': 'vibe_9f2c7a1d4e'}
)
logs = response.json()['logs']
{
"session": {
"conversationId": "vibe_9f2c7a1d4e",
"appId": "V1StGXR8Z5",
"state": "CLOSED",
"summary": "Added inspection photo upload form"
},
"logs": [
{
"logType": "USER_MESSAGE",
"content": "Add a photo upload to the inspection form.",
"timestamp": "2026-06-30T14:02:15"
},
{
"logType": "TOOL_CALL",
"toolName": "write_file",
"toolCallId": "call_01",
"toolArguments": "{\"filePath\":\"src/components/PhotoUpload.jsx\", ...}",
"timestamp": "2026-06-30T14:02:44"
},
{
"logType": "TOOL_RESULT",
"toolName": "write_file",
"toolCallId": "call_01",
"toolResult": "File written",
"timestamp": "2026-06-30T14:02:45"
},
{
"logType": "ASSISTANT_MESSAGE",
"content": "Done — I added a PhotoUpload component and wired it into the form.",
"timestamp": "2026-06-30T14:03:02"
}
],
"errors": []
}
Errors
| Status | When |
|---|---|
200 | Success — check errors for validation and access messages ("No access to this app", "Only admin can delete apps", "File not found", "publicSlug is already taken", "No published version available", "Conversation not found"). |
401 | Invalid or missing poweruser key. |
403 | Scoped key without the endpoint in its allow-list. |
408 | Server-side error; errors contains the message. |
Access-level denials come back as messages in errors on a 200 response
rather than as HTTP-level failures — see the
access table for what each endpoint
requires.