Skip to main content

What is the SDK?

The Kittl SDK is the bridge between your sandboxed app and the editor host. It exposes async APIs through:

  • kittl.design for design operations
  • kittl.state for editor/app state
  • kittl.upload for image uploads
  • kittl.auth for OAuth helper flows

Add the SDK to your app

You can load the SDK in two ways.

pnpm add @kittl/sdk
import { kittl } from '@kittl/sdk';

Option 2: Script tag

<script src="https://static.kittl.com/sdk/staging/v0/sdk.js"></script>

The URL uses staging and the major version (v0 for 0.x). Use window.kittl in this mode:

const { kittl } = window;

Wait for readiness

Call SDK APIs only after the bridge is ready:

import { kittl } from '@kittl/sdk';

kittl.onReady(async () => {
const result = await kittl.state.getSelectedObjectsIds();
if (result.isOk) {
console.log('Selected object IDs:', result.result);
}
});

Response format

All SDK calls return a SdkResult object: { isOk: true, result: T } on success, or { isOk: false, error: E } on failure. Check isOk and use result before accessing the value:

const addResult = await kittl.design.text.addText({ ... });
if (addResult.isOk) {
const text = addResult.result;
await kittl.state.setSelectedObjectsIds([text.id]);
}

Error types

For APIs that return SdkError (for example, most design APIs), the error property is a discriminated union you can narrow by error.name. Some SDK methods (e.g. font.createFont, ai.spendCredits) instead return a generic Error, so error.name should only be used as a discriminator when the specific API documents SdkError:

Error TypenameWhen
SdkBadInputError'SdkBadInputError'Invalid or missing parameters (validation failure)
SdkInternalError'SdkInternalError'Unexpected internal error in the SDK or host

These SdkError variants extend Error and include message and an optional cause:

const result = await kittl.design.image.addImage({ ... });

if (!result.isOk) {
const { error } = result;

if (error.name === 'SdkBadInputError') {
console.error('Invalid input:', error.message);
} else if (error.name === 'SdkInternalError') {
console.error('Internal error:', error.message);
}

// Optionally inspect the underlying cause
if (error.cause) {
console.error('Caused by:', error.cause);
}
}

Async vs Sync results

Most SDK methods return SdkResultAsync<T> (a Promise). Some synchronous design methods return SdkResult<T> directly — both have the same { isOk, result, error } shape.

Minimal example

import { kittl } from '@kittl/sdk';

kittl.onReady(async () => {
const addResult = await kittl.design.text.addText({
text: 'Hello from my app',
position: { absolute: { left: 120, top: 120 } },
size: { width: 320, height: 80 },
});

if (addResult.isOk) {
await kittl.state.setSelectedObjectsIds([addResult.result.id]);
}
});

Image upload example

Use kittl.upload.image.upload to upload a blob, then add it to the canvas with kittl.design.image.addImage:

const uploadResult = await kittl.upload.image.upload({ blob });
if (uploadResult.isOk) {
const { objectName } = uploadResult.result[0];
await kittl.design.image.addImage({
src: objectName,
size: { width: 200, height: 200, applyViewportScale: false },
position: { relative: { to: 'viewport', location: 'center' } },
});
}

Notes

  • The SDK is designed for sandboxed app frames.
  • Every API call is async in app context.
  • Declare required SDK permissions in your manifest metadata.scopes; see SDK scopes.