SDK API

Import sdk from the dedicated runtime entry point:

import { sdk } from '@theaiplatform/miniapp-sdk/sdk';

The sdk export is a lazy MiniAppPlatformApi. Importing it is safe in tests and build tools. Reading any property before The AI Platform installs the capability session throws an unsupported-environment error, so keep host access at a target or surface boundary.

Every host operation can cross a process or network boundary. Always await its result even when the type also permits a synchronous value through MiniAppMaybePromise.

Declare Permissions

Every host-backed method must be declared before installation. Add each action ID you use to a permission.catalog, include it in a package level, and reference it from the calling contribution's authorization.allOf. The autonomy value below is the minimum ceiling required by that method. Declarations are requests, not grants: installation review and current workspace policy decide whether a call is allowed, and a later revocation makes the operation reject.

Public methodPermission action IDRequired autonomy
sdk.channels.createchannels.createdo
sdk.channels.listchannels.listlisten
sdk.channels.sendMessagechannels.send-messagedo
sdk.channels.sendSpecialistMessagechannels.send-messagedo
sdk.channels.getAccesschannels.readlisten
sdk.channels.getTimelinechannels.readlisten
sdk.projects.createprojects.createdo
sdk.projects.getprojects.readlisten
sdk.projects.updateprojects.updatedo
sdk.workflows.listworkflows.listlisten
sdk.workflows.invokeSavedworkflows.invokedo
sdk.workflows.invokeworkflows.invokedo
sdk.navigation.opennavigation.opendo
sdk.chat.sendTextToChatchat.composedo
sdk.chat.joinChannelSpecialistchannels.manage-specialistsdo
sdk.chat.archiveConversationchannels.archivedo
sdk.auth.getUserProfileprofile.readlisten
sdk.vfs.provisionProjectChatvfs.provision-project-chatdo
sdk.vfs.writeFilevfs.writedo
sdk.vfs.mkdirvfs.writedo
sdk.specialist.joinToChannelchannels.manage-specialistsdo
sdk.specialist.listWorkspacespecialists.listlisten
sdk.specialist.createspecialists.createdo
sdk.specialist.upsertManagedspecialists.managedo
sdk.specialist.runTurnWithToolsspecialists.invokedo
sdk.http.requestnetwork.requestdo
sdk.http.request with a credentialcredentials.usedo
sdk.credentials.listHttpcredentials.readlisten
openEditorProjecteditor.opendo

The browser-only openEditorProject helper appears in the table because it requests a host action even though it is imported from /web. Theme helpers, type exports, getPlatform, and capability-flag checks do not request a host action and therefore need no permission action.

sdk.storage, sdk.presence, sdk.http, and sdk.credentials use descriptor effects in addition to the calling contribution's ordinary permission binding. Declare a storage or presence effect whose resources contains each namespace the contribution uses. HTTP requires an external-network effect for each exact URL origin, such as https://api.vanta.com. Credential listing or use also requires { "kind": "credentials", "resources": ["http"] }. Wildcards do not match an origin. The host derives workspace, package, instance, document, and participant identity from the verified frame; none of those are caller inputs.

The quickstart shows a complete catalog, level, role recommendation, and surface binding for channels.list. For a package that uses several methods, list each action once and bind only the actions needed by each contribution.

Namespaced Storage

sdk.storage stores bounded, non-secret JSON under a package-controlled namespace and key. The host prepends the authenticated workspace and exact package identity, so two packages cannot address each other's data. get returns a value and optimistic revision; a missing entry returns both as null. Pass that exact revision to set or delete. Pass null only to create a missing key.

const address = { namespace: 'canvas', key: 'scene/main' };
const current = await sdk.storage.get(address);
const saved = await sdk.storage.set({
  ...address,
  expectedRevision: current.revision,
  value: { title: 'Launch plan', nodes: [] },
});
console.log(saved.revision);

Values are limited to plain finite JSON and five MiB. Secrets, credentials, binary assets, and signed URLs do not belong in this API. A revision conflict rejects; reload, merge, and retry instead of silently overwriting another realm's update.

Presence

sdk.presence carries bounded ephemeral JSON in a host-scoped namespace and room. Call subscribe before join, refresh state with update, and call leave during explicit teardown. The host also removes a participant when its document or frame is retired.

const address = { namespace: 'canvas', room: 'scene/main' };
const unsubscribe = sdk.presence.subscribe(address, (snapshot) => {
  const collaborators = snapshot.participants.filter(
    (participant) => participant.participantId !== snapshot.selfParticipantId,
  );
  renderCollaborators(collaborators);
});

await sdk.presence.join({
  ...address,
  state: { cursor: { x: 120, y: 80 }, selection: ['node-1'] },
});

Participant IDs, display names, and timestamps are host-stamped. App state cannot replace them. Presence is not durable storage or a permission grant; participants expire after missed heartbeats and must be prepared to rejoin.

HTTP and credentials

Feature-detect sdk.http, sdk.credentials, and hasHostHttpRequest === true because non-desktop targets may omit these capabilities. sdk.http.request sends bounded HTTP(S) through the native transport, so it is not subject to the miniapp iframe's browser CORS path. The host validates the URL and limits, requires persisted package grants, and asks the signed-in human for origin consent. Credential-backed requests additionally revalidate the active workspace and user before resolving a secret.

if (!sdk.http || !sdk.credentials || sdk.hasHostHttpRequest !== true) {
  throw new Error('Host-mediated HTTP is unavailable in this target.');
}

const credentials = await sdk.credentials.listHttp();
const credential = credentials.find(
  (candidate) => candidate.credentialType === 'http_bearer',
);
if (!credential) throw new Error('Configure an HTTP bearer credential first.');

const response = await sdk.http.request(
  { method: 'GET', url: 'https://api.vanta.com/v1/controls' },
  { credentialRef: credential.id },
);

listHttp returns IDs, types, display names, and non-secret metadata only. A miniapp cannot read credential values. The host injects the selected secret, redacts credential material from reflected response fields, suppresses binary bodies on credential-backed requests, and rejects destination conflicts. Request timeouts are capped at 120 seconds after consent; the SDK itself does not race the native human-decision prompt with a shorter client timeout.

Channels

sdk.channels provides six operations:

MethodInputResult
createCreateChannelOptionsCreateChannelResult
listOptional ListChannelsOptionsListChannelsResult
sendMessageSendChannelMessageOptionsSendChannelMessageResult
sendSpecialistMessageSendChannelSpecialistMessageOptionsSendChannelSpecialistMessageResult
getAccessGetChannelAccessOptionsGetChannelAccessResult
getTimelineGetChannelTimelineOptionsGetChannelTimelineResult

MiniAppChannel describes a visible channel. MiniAppChannelMessage is intentionally opaque, bounded MiniAppJsonValue: the host versions timeline-row shapes independently, so narrow and validate a row before reading any fields. The timeline result also supplies the visible sequence. A former participant can remain readable through GetChannelAccessResult.visibleUntilSequence; do not interpret that as permission to write.

const access = await sdk.channels.getAccess({ channelId });
if (access.capabilities.includes('message:create')) {
  await sdk.channels.sendMessage({
    channelId,
    content: 'The report is ready.',
    body: 'The report is ready.',
  });
}

Access can change after a check. Handle rejection from the operation itself and do not infer authority from cached channel data.

Projects

sdk.projects uses CreateProjectOptions, GetProjectOptions, and UpdateProjectOptions. The corresponding CreateProjectResult, GetProjectResult, and UpdateProjectResult return the project ID or a MiniAppProject snapshot.

const result = await sdk.projects.get({ projectId });
if (result.project) {
  await sdk.projects.update({
    projectId,
    name: `${result.project.name} copy`,
  });
}

GetProjectResult.project can be null when the project is missing or outside the current capability scope.

Workflows

sdk.workflows.list accepts optional ListWorkflowsOptions and returns ListWorkflowsResult, whose entries are MiniAppWorkflow values. invokeSaved accepts InvokeSavedWorkflowOptions; the optional invoke method accepts InvokeWorkflowOptions. Both return InvokeWorkflowResult.

const result = await sdk.workflows.invokeSaved({
  workflowId,
  payload: { source: 'miniapp' },
});
if (!result.success) {
  throw new Error(result.error ?? result.message);
}

Feature-detect the optional inline invoke method. A successful request reports status and may include a run ID; it does not imply that unrelated follow-up operations are authorized.

Authentication

sdk.auth is an optional MiniAppAuthApi. Its getUserProfile method returns a MiniAppUserProfile or null. The profile exposes a subject when available and host-approved public fields; it never contains raw platform credentials.

const profile = (await sdk.auth?.getUserProfile()) ?? null;
if (profile) {
  console.log(profile.sub, profile.email ?? 'No email was shared');
}

Treat a missing capability and a signed-out profile as normal states. Request the profile again after an account or scope change.

Virtual Files

sdk.vfs is an optional MiniAppVfsApi with provisionProjectChat, mkdir, and writeFile. File paths are relative to the selected conversation storage, not operating-system paths.

const vfs = sdk.vfs;
if (vfs) {
  const provisioned = await vfs.provisionProjectChat({
    conversationId,
    projectId,
  });
  console.log(provisioned.mountedRoots);
  await vfs.mkdir(conversationId, 'notes');
  await vfs.writeFile(
    conversationId,
    'notes/README.md',
    new TextEncoder().encode('# Notes\n'),
  );
}

The VFS API does not expose raw host filesystem access. Handle unavailable scope, conflicts, and deletion as recoverable failures.

Specialists

sdk.specialist is an optional MiniAppSpecialistApi. It can join a specialist to a channel, list a workspace, and create a specialist. A compatible host can additionally expose upsertManaged and runTurnWithTools.

Managed upsert can return MiniAppManagedSpecialistResult. A supported turn accepts MiniAppSpecialistTurnOptions and returns MiniAppSpecialistTurnResult. Feature-detect both optional methods before showing their actions.

const specialists = sdk.specialist;
if (specialists) {
  const available = await specialists.listWorkspace(workspaceId);
  const first = available[0];
  if (first) {
    const sessionId = await specialists.joinToChannel(channelId, first.id);
    console.log(`Joined specialist session ${sessionId}`);
  }
}

MiniAppCreateSpecialistOptions and MiniAppCreateSpecialistResult describe a basic created specialist. MiniAppManagedSpecialist is the bounded, author-controlled manifest accepted by upsertManaged; the result always contains the effective specialist ID. Ownership, workspace, visibility, installation, and verification metadata are derived by the host and are rejected if a miniapp supplies them. MiniAppSpecialistInteractionMode, MiniAppSpecialistConversationPart, and the turn option/result types describe the complete request and terminal response for a supported tool-enabled turn. Hosts reject invalid IDs, unsupported modes, out-of-range timeouts, unauthorized channel access, and malformed manifests.

Chat

sdk.chat is the required MiniAppChatApi. sendTextToChat selects the active conversation, reveals the shared composer, and places text there. Compatible hosts can also expose joinChannelSpecialist and archiveConversation.

await sdk.chat.sendTextToChat('Summarize the current project.');

The method places text for the user; do not describe it as silently sending a user-authored message.

joinChannelSpecialist takes a channel and specialist ID and resolves with null after the roster update. archiveConversation takes workspace, user, conversation, and project IDs and resolves with null after archival. Both are optional and can reject when the current package session lacks authority.

sdk.navigation.open accepts OpenNavigationOptions with a platform-relative path. It is not a general URL or script launcher.

hasEditorView and hasHostHttpRequest are optional boolean feature flags. Treat values other than true as unavailable. When hasHostHttpRequest is true, the desktop host also supplies sdk.http and sdk.credentials; portable code should still check the objects before calling them.

await sdk.navigation.open({
  path: `/workspace/${workspaceId}/channels/${channelId}`,
});

if (sdk.hasEditorView === true) {
  // Render an action that uses the documented web editor helper.
}

Navigation rejects malformed or out-of-scope paths. Feature flags are snapshots; re-check them after a new surface realm mounts.

Public Export Contract

Every exported name below is public. “Type only” rows have no runtime lifecycle of their own; the linked working example shows where the contract is consumed.

ExportPurposeInputs and resultLifecycle and errorsWorking example
MiniAppChannelDescribes one channel visible to the package session.Contains identity, display, visibility, archive, and timestamp fields.Type only; channel snapshots can become stale and operations can still reject.Channels
CreateChannelOptionsSupplies fields for creating a channel.Accepts a name plus optional workspace, description, project, and visibility; creation returns CreateChannelResult.Type only; the host rejects invalid fields or missing authority.Channels
CreateChannelResultReports the created channel identity.Contains the resulting roomId.Type only; it exists only after a successful create operation.Channels
ListChannelsOptionsSelects the workspace used for channel listing.Accepts an optional workspace ID; listing returns ListChannelsResult.Type only; omitted scope uses the current authorized workspace.Channels
ListChannelsResultReturns visible channels and the applied read mode.Contains rooms and readMode.Type only; results are snapshots and do not grant write access.Channels
SendChannelMessageOptionsDescribes a user-visible channel message write.Accepts channel, content, and optional display or structured fields; returns SendChannelMessageResult.Type only; duplicate IDs, invalid content, or lost authority can reject.Channels
SendChannelMessageResultIdentifies a persisted channel message.Contains server and client message IDs.Type only; returned only after persistence succeeds.Channels
SendChannelSpecialistMessageOptionsDescribes one completed specialist-authored channel row.Accepts channel, project, specialist, client ID, body, and optional structured content.Type only; the host verifies specialist ownership and participation.Channels
SendChannelSpecialistMessageResultIdentifies a persisted specialist message.Contains server and client message IDs.Type only; returned only after the authorized write completes.Channels
GetChannelAccessOptionsSelects a channel for an access snapshot.Accepts channel and optional workspace IDs; returns GetChannelAccessResult.Type only; access can change immediately after the read.Channels
GetChannelAccessResultDescribes current channel participation and capabilities.Returns archive, participation, capabilities, and optional retained sequence.Type only; callers must still handle operation-level rejection.Channels
GetChannelTimelineOptionsSelects a channel timeline.Accepts channel and optional workspace IDs; returns GetChannelTimelineResult.Type only; unreadable channels reject and retained reads may be bounded.Channels
MiniAppChannelMessageRepresents one opaque host-versioned timeline row.Provides bounded MiniAppJsonValue that callers narrow to a known row shape.Type only; validate every field before rendering or acting on it.Channels
GetChannelTimelineResultReturns a timeline snapshot and sequence.Contains messages and the last visible sequence.Type only; later writes or revocation do not mutate the snapshot.Channels
MiniAppProjectDescribes a project and its channel membership.Contains identity, name, workspace, discovery, and channel lists.Type only; project state can change between calls.Projects
CreateProjectOptionsSupplies fields for creating a project.Accepts a name plus optional identity, workspace, and discovery flag.Type only; invalid identity or missing authority can reject.Projects
CreateProjectResultReports the created project identity.Contains projectId.Type only; returned after successful creation.Projects
GetProjectOptionsSelects a project snapshot.Accepts project and optional workspace IDs; returns GetProjectResult.Type only; an unavailable project produces null rather than authority.Projects
GetProjectResultWraps an optional project snapshot.Contains a MiniAppProject or null.Type only; callers must handle deletion and scope changes.Projects
UpdateProjectOptionsDescribes mutable project fields.Accepts project identity and optional name, discovery, and channel lists.Type only; stale or unauthorized updates reject.Projects
UpdateProjectResultReturns the updated project snapshot.Contains the resulting MiniAppProject.Type only; returned after the host commits the update.Projects
InvokeWorkflowOptionsSupplies an inline workflow and optional payload.Accepts serialized workflow JSON and a typed payload; returns InvokeWorkflowResult.Type only; the optional operation can be absent or reject invalid workflow input.Workflows
MiniAppWorkflowDescribes a saved workflow.Contains identity, name, type, and timestamps.Type only; listed workflows are point-in-time snapshots.Workflows
ListWorkflowsOptionsSelects the workspace for saved workflows.Accepts an optional workspace ID; returns ListWorkflowsResult.Type only; the host filters by the active package scope.Workflows
ListWorkflowsResultReturns saved workflow summaries.Contains a workflows array.Type only; entries can disappear or become unauthorized later.Workflows
InvokeSavedWorkflowOptionsSelects a saved workflow and payload.Accepts workflow ID and an optional typed payload; returns InvokeWorkflowResult.Type only; missing workflows and rejected payloads report failure or reject.Workflows
InvokeWorkflowResultReports workflow dispatch status.Contains success, status, message, and optional run or error data.Type only; success means accepted execution, not authority for later calls.Workflows
MiniAppMaybePromiseModels APIs that may complete immediately or asynchronously.Wraps one result type as a direct value or promise.Type only; callers should always await host operations to catch rejection.Channels
MiniAppJsonValueConstrains public configuration and tool data to JSON values.Accepts null, scalar, array, or string-keyed JSON object values.Type only; cyclic, binary, and undefined values are invalid.Specialists
MiniAppStorageAddressAddresses one package-owned storage entry.Contains a namespace and key; the host prepends workspace and package identity.Type only; invalid or oversized partitions reject.Namespaced Storage
MiniAppStorageEntryReturns a stored JSON value and optimistic revision.Contains nullable value and revision; both are null for a missing key.Type only; snapshots can become stale immediately.Namespaced Storage
MiniAppStorageSetOptionsCreates or replaces one storage entry.Adds bounded JSON and an exact nullable expected revision to a storage address.Revision mismatch or invalid JSON rejects without overwriting.Namespaced Storage
MiniAppStorageDeleteOptionsDeletes one existing storage entry.Adds a required positive expected revision to a storage address.Missing or stale revisions reject without deleting.Namespaced Storage
MiniAppStorageMutationResultReports the new storage revision.Contains the positive revision produced by set.Type only; use it for the next optimistic mutation.Namespaced Storage
MiniAppStorageApiGroups namespaced get, set, and delete operations.Accepts the storage option types and returns entries, revisions, or void.Every operation is asynchronous and host-authorized.Namespaced Storage
MiniAppPresenceAddressAddresses one ephemeral presence room.Contains a namespace and room inside the host-derived workspace/package scope.Type only; it carries no durable or authorization state.Presence
MiniAppPresenceParticipantDescribes one host-stamped participant.Contains participant ID, display name, bounded state, and host timestamp.Type only; entries expire and app state cannot replace identity fields.Presence
MiniAppPresenceSnapshotReports a room's current participant snapshot.Contains address, self participant ID, and participants.Snapshots are ephemeral and can change between callbacks.Presence
MiniAppPresenceUpdateOptionsSupplies bounded app-owned presence state.Adds JSON state to a presence address.Join and update reject invalid, oversized, or unauthorized state.Presence
MiniAppPresenceListenerReceives presence snapshots.Accepts one MiniAppPresenceSnapshot and returns void.Observer failures are isolated; unsubscribe during teardown.Presence
MiniAppPresenceApiGroups join, update, leave, and subscribe operations.Accepts presence addresses/state and returns snapshots, void, or an unsubscribe callback.Presence is ephemeral, host-stamped, and removed with the frame.Presence
MiniAppHttpHeaderInputSupplies one ordered request header.Contains name, value, and an optional enabled flag.Type only; native validation rejects invalid or oversized headers.HTTP and credentials
MiniAppHttpQueryInputSupplies one ordered request query row.Contains name, value, and an optional enabled flag.Type only; native validation rejects invalid or oversized query data.HTTP and credentials
MiniAppHttpRequestInputDescribes one bounded host-mediated request.Accepts method, URL, query, headers, body, timeout, response limit, and redirect policy.Only HTTP(S) is accepted; native limits and origin consent apply.HTTP and credentials
MiniAppHttpRequestOptionsSelects optional host-managed request authentication.Accepts only an opaque credentialRef.Secret material is resolved natively and never returned to JavaScript.HTTP and credentials
MiniAppHttpHeaderDescribes one ordered response header.Contains name and value.Type only; credential-derived material is redacted by the host.HTTP and credentials
MiniAppHttpResponseReturns a bounded native HTTP response.Contains URL, status, headers, text or base64 body, truncation, size, timing, and content type.Invalid host responses reject; credential-backed binary bodies are suppressed.HTTP and credentials
MiniAppHttpCredentialTypeEnumerates supported stored HTTP credential kinds.Bearer, Basic, header-auth, and header/query API-key records are supported.Type only; OAuth and raw keychain reads are excluded.HTTP and credentials
MiniAppHttpCredentialMetadataDescribes one safe stored credential reference.Contains opaque ID, type, display name, and non-secret metadata fields.Metadata can become stale; use is reauthorized at request time.HTTP and credentials
MiniAppHttpApiGroups host-mediated HTTP operations.request accepts a request plus optional opaque credential reference and returns MiniAppHttpResponse.Optional per target; effects, grants, consent, and native bounds apply.HTTP and credentials
MiniAppCredentialsApiGroups metadata-only credential discovery.listHttp returns MiniAppHttpCredentialMetadata[].Optional per target; requires an active workspace, human, effect, and grant.HTTP and credentials
MiniAppUserProfileDescribes host-approved public identity claims.Contains a required subject and optional standard profile fields.Type only; fields can be absent and the profile can become null after account changes.Authentication
MiniAppProvisionProjectChatOptionsSelects a conversation work area to provision.Accepts conversation, project, and optional reference branch.Type only; invalid scope, branch, or project state can reject.Virtual files
MiniAppProvisionProjectChatResultReports mounted roots and optional worktree metadata.Returns root paths, branch, and base commit fields.Type only; values identify the provisioned conversation realm.Virtual files
MiniAppSpecialistInteractionModeEnumerates supported specialist turn modes.Supplies one documented mode to a turn request.Type only; unsupported modes are rejected before dispatch.Specialists
MiniAppSpecialistSummaryDescribes a specialist visible in the workspace catalog.Contains public identity, presentation, availability, and capability fields.Type only; summaries are scoped snapshots with no machine-local source data.Specialists
MiniAppCreateSpecialistOptionsSupplies a basic specialist definition.Accepts name, domain, nullable description, and JSON configuration.Type only; malformed or unauthorized definitions reject.Specialists
MiniAppCreateSpecialistResultReports the created specialist.Contains identity, display fields, and active state.Type only; returned after successful creation.Specialists
MiniAppManagedSpecialistSupplies a bounded author-controlled specialist manifest.Accepts identity, presentation, and documented optional JSON metadata; host-stamped authority fields are forbidden.Type only; unknown, malformed, or differently owned manifests reject.Specialists
MiniAppManagedSpecialistResultReports the effective managed specialist identity.Contains a required specialistId.Type only; returned after create or reconciliation succeeds.Specialists
MiniAppSpecialistConversationPartModels text, tool, and step-end turn output.Returns discriminated terminal parts with JSON-safe tool data.Type only; validate the type discriminator before reading fields.Specialists
MiniAppSpecialistTurnOptionsDescribes one bounded tool-enabled specialist turn.Accepts workspace, channel, specialist, content, model, mode, null message ID, and timeout.Type only; invalid bounds, access, or unavailable methods reject.Specialists
MiniAppSpecialistTurnResultReturns the terminal specialist completion.Contains typed parts plus optional finish reason and model name.Type only; malformed host results reject instead of crossing the public boundary.Specialists
MiniAppAuthApiGroups the optional public profile operation.getUserProfile returns MiniAppUserProfile or null.Feature-detect per realm; account and authorization changes can alter the result.Authentication
MiniAppVfsApiGroups conversation-scoped provision, directory, and file writes.Methods accept relative paths and return typed provision data or null.Feature-detect per realm; invalid paths and unavailable scope reject.Virtual files
MiniAppSpecialistApiGroups workspace specialist discovery and actions.Methods return session IDs, public summaries, created specialists, or terminal turns.Feature-detect optional methods; ownership, access, and timeout failures reject.Specialists
MiniAppChatApiGroups composer, roster, and archive operations.Accepts text or exact resource IDs and returns void or null.The base composer method is required; optional methods can be absent or reject.Chat
MiniAppPlatformApiDefines the complete public API installed for a miniapp realm.Groups storage, presence, channels, projects, workflows, navigation, chat, and optional HTTP/credential capabilities.One proxy lives for the module; each property read requires an installed host session.SDK API
OpenNavigationOptionsSupplies a platform-relative navigation path.Accepts one path; navigation resolves without a result.Paths outside the authorized platform route space reject.Navigation and feature flags
sdkProvides the lazy public API proxy.Exposes MiniAppPlatformApi; operations return the results documented above.Import is safe anywhere; property use before host installation throws.SDK API