Skip to content
SBDocs

Customers · API reference

Workflow format

The workflow definition you send to create a workflow: steps, handles, port types, what may connect to what, and every node type.

Before you start
  • An API key with the workflows:write scope, and the id of a project or agent.
You'll end with
A workflow definition that passes validation the first time.

A workflow is a list of steps and the connections between them. You can create one from code by sending that list to Create a workflow; Sushibelt lays it out as a graph on the canvas, where your team can open and edit it. This page is the full format: the request, how steps connect, the port types, and every node type.

Tip: the easiest way to get a workflow right

Build and test it on the canvas, then run it by its id. Create workflows from code when you need many similar ones, or when an agent designs them.

The request#

A workflow belongs to an agent, inside a project. Pass agentId to add the workflow to an agent you already have, or projectId to create a new agent for it. In the app, both ids are in the address bar when you open an agent: /your-team/workspace/PROJECT_ID/AGENT_ID/canvas.

Create a workflow: request body
NameDescription
namestring · RequiredThe workflow's name.
agentIdstring (uuid) · OptionalAdd the workflow to this agent.
projectIdstring (uuid) · OptionalCreate a new agent in this project and add the workflow to it.
agentNamestring · OptionalThe new agent's name, when you pass projectId. Defaults to name.
stepsarray of WorkflowStep · RequiredNo description.

When you create a new agent, or add to an agent that has no active workflow, the new workflow becomes the one Run an agent runs. Adding a workflow to an agent that already has an active one leaves it unchanged.

Steps#

Each step is one node on the canvas.

A step
NameDescription
keystring · RequiredA name for this step, unique within the request. Other steps refer to it in inputs.
typestring · RequiredThe node type. One of 55 values; see the list below.
labelstring · OptionalThe name shown on the canvas. Defaults to the node type's name.
configobject · OptionalThe node's settings; the fields depend on the node type. Set apiInputKey on a TextEntry or PromptBuilder step to let a run replace its value.
inputsarray of one of: string, WorkflowStepInput · OptionalThe steps this step reads from. A step key alone connects first output to first input.

Connecting steps#

A step's inputs list the steps it reads from. A node has named ports, called handles: inputs on one side, outputs on the other. There are two ways to connect:

  • By key alone, such as "inputs": ["prompt"]: connects the other step's first output to this step's first input. Right for most nodes, which have one of each.
  • With handles, such as { "from": "style", "targetHandle": "input-b" }: names the ports, for a node with more than one input or output.
A connection with handles
NameDescription
fromstring · RequiredThe key of the step to connect from.
sourceHandlestring · OptionalThe output handle on that step.
targetHandlestring · OptionalThe input handle on this step.

The handle ids of every node are in the node types table below.

Port types#

Every handle carries a type, which decides what may connect to it.

Port types
TypeDescription
stringText: a prompt, an answer, a caption.
imageAn image file.
fileAny file.
jsonStructured data.
codeSource code, such as a GLSL shader.
configSettings for a model step, overriding its own.
mapOne map image, such as depth.
mapsA set of texture maps for one material: albedo, normal, roughness, metal.
meshA 3D mesh (GLB and similar).
rigA skeleton for a mesh.
audioAn audio file.
booleanTrue or false.
anyAnything. Used by pass-through inputs.
sameWhatever arrived at the node's pass-through input.
numA number.
arrayA list.

What may connect to what#

  • An output connects to an input of the same type.
  • An any input takes every output, and an any output connects to every input.
  • A same output carries the type of whatever reached the node's pass-through input, and is checked as that type.
  • An input that lists several kinds, such as a delivery step's asset, takes any of them.
  • number and num are the same type, and so are model3d and mesh.

For each input type, the outputs it takes besides any and same:

Input types and the outputs they take
Input typeDescription
stringstring, json, code, boolean, num
imageimage
filefile
jsonjson
codecode
configconfig
mapmap
mapsmaps
meshmesh
rigrig
audioaudio
booleanboolean
numnum
arrayarray

Validation#

A workflow is checked when you create it and again every time it runs, by the same rules the canvas uses. Creating one that fails answers 422; so does starting a run of one. The rules:

  • Every step has a key, unique in the request, and a known type.
  • Every connection names a key in the same request.
  • No node with ports is left unconnected.
  • Every required input is connected.
  • Every required setting is filled, such as a Text node's text or a Prompt builder's template, unless a connection supplies it.
  • Every connection joins types that fit, by the rules above.
  • There are no loops: a step cannot depend on itself through other steps.
  • No step uses a node type that cannot run (see Older type ids).

The answer lists each problem in errors, each with a message naming the node and, usually, its nodeId. A problem with the step list itself — an unknown type, a repeated key, a connection to no step — answers with a single error instead.

Settings#

A step's config holds its settings: the same values the inspector on the canvas shows. The ones you are most likely to set from code:

Common settings
Node type and settingDescription
TextEntry · textThe text the node passes on, exactly as written.
TextEntry · apiInputKeyA name that lets a run replace text. See Pass inputs to a run.
PromptBuilder · templateA template with {{input-a}} and {{input-b}} slots, filled from what is connected to those inputs.
PromptBuilder · apiInputKeyA name that lets a run replace template.
DiffusionWorker · providerKey, modelThe provider and model that make the image. Leave them out to let Sushibelt choose. Each image model's page shows the values under Run it from code.
Delivery nodes · repo, branch, path, commitMessage, manifestWhere and how files are committed. See Deliver to GitHub, GitLab or Unity.

A complete example#

Two pieces of text joined into a prompt, made into an image, and shown in a gallery. The subject is exposed as an input named subject, so each run can change it.

Create a workflow with named handles
curl -X POST "https://app.sushibelt.ai/api/v1/workflows" \
  -H "Authorization: Bearer $SUSHIBELT_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Fox in oils",
    "projectId": "YOUR_PROJECT_ID",
    "steps": [
      {
        "key": "subject",
        "type": "TextEntry",
        "config": {
          "text": "a red fox",
          "apiInputKey": "subject"
        }
      },
      {
        "key": "style",
        "type": "TextEntry",
        "config": {
          "text": "as an oil painting"
        }
      },
      {
        "key": "prompt",
        "type": "PromptBuilder",
        "config": {
          "template": "{{input-a}}, {{input-b}}"
        },
        "inputs": [
          {
            "from": "subject",
            "targetHandle": "input-a"
          },
          {
            "from": "style",
            "targetHandle": "input-b"
          }
        ]
      },
      {
        "key": "image",
        "type": "DiffusionWorker",
        "inputs": [
          "prompt"
        ]
      },
      {
        "key": "preview",
        "type": "ImageGallery",
        "inputs": [
          "image"
        ]
      }
    ]
  }'
Example response (201 Created)JSON
{
  "workflowId": "3f1c9a52-8d4e-4b7a-9c61-2e5f0d7a1b90",
  "agentId": "5e0b7c3d-2a61-4f8e-b9d4-07c1a6e2f853",
  "projectId": "00000000-0000-0000-0000-000000000000",
  "stepsCount": 5
}

Then run it with { "inputs": { "subject": "a white wolf" } }. See Pass inputs to a run.

Node types#

Every node the canvas offers, grouped as the canvas groups them. The type is what you send; the name under it is what the canvas calls it. Each row lists the node's input and output handles with their port types.

Start#

Bring something in to work with.

Node types: Start
TypeDescription
TextEntryTextType a prompt or any text. No inputs. Output: output (string).
ImageLoaderImageStart from a picture you have. No inputs. Output: output (image).
FileUploaderFileUpload a file from your machine. No inputs. Output: output (file).
JsonLoaderDataSupply a fixed block of data. No inputs. Output: output (json).
WebhookListenerWebhook triggerStart the run from an HTTP request. No inputs. Output: output (json).
S3BucketWatcherWatch an S3 folderRun when a new file lands. No inputs. Output: output (file).
ShaderSnippetShader codeSupply GLSL to run later. No inputs. Output: output (code).

2D#

Generate, guide, enlarge and cut out pictures.

Node types: 2D
TypeDescription
DiffusionWorkerImage generatorMake a picture from a description. Inputs: prompt (string, required), image (image), config (config). Output: output (image).
ControlNetFilterComposition guideForce a pose, edge or depth layout. Inputs: image (image, required), control (string, required). Output: output (image).
UpscalerUpscalerEnlarge an image 2× or 4×. Inputs: input (image, required). Output: output (image).
BackgroundRemoverBackground removerCut the subject out of a picture. Inputs: input (image, required). Output: output (image).
ImageCropperCropCut an image to a region. Inputs: input (image, required). Output: output (image).

Maps#

Depth and material maps from a picture.

Node types: Maps
TypeDescription
DepthEstimatorDepth mapEstimate depth from a picture. Inputs: input (image, required). Output: output (map).
PbrSynthesizerMaterial makerTurn a texture into PBR maps. Inputs: input (image, required). Output: output (image).
TextureManifestTexture setBundle maps into one material. No inputs. Output: output (maps).

3D#

Meshes from pictures, made game-ready.

Node types: 3D
TypeDescription
TwoDToThreeDImage to 3DBuild a mesh from a picture. Inputs: image (image, required), maps (maps), prompt (string). Output: output (mesh).
MeshDecimatorDecimateCut a mesh to a triangle budget. Inputs: input (mesh, required). Output: output (mesh).
ThreeDStudioViewer3D previewLook at a mesh in the canvas. Inputs: mesh (mesh, required), maps (maps). No output: it ends a chain.

Motion#

Skeletons and animation for a mesh.

Node types: Motion
TypeDescription
AutoRiggerRiggerAdd a skeleton to a mesh. Inputs: mesh (mesh, required), rig (rig). Output: output (mesh).
RigImporterRig importerBring in an existing rig. No inputs. Output: output (rig).

Audio#

Speech and sound.

Node types: Audio
TypeDescription
AudioGenAudio generatorTurn text into speech. Inputs: prompt (string, required), config (config). Output: output (audio).

Text#

Write, describe, template and embed text.

Node types: Text
TypeDescription
LlmWorkerWriterAsk a language model for text. Inputs: prompt (string, required), config (config). Output: output (string).
VisionInterrogatorImage describerSay what is in a picture. Inputs: input (image, required). Output: output (string).
PromptBuilderPrompt builderFill a template with upstream values. Inputs: input-a (string, required), input-b (string). Output: output (string).
EmbedderEmbedderTurn text into a vector for search. Inputs: input (string). Output: output (json).

Logic#

Route, repeat and reshape data.

Node types: Logic
TypeDescription
CustomApiCallCustom APICall any HTTPS API with your own key. Inputs: prompt (string), image (image). Output: text (string), images (image).
ConditionalSwitchBranchSend data one way or the other. Inputs: condition (boolean, required), input (any, required). Output: output (same).
MathOperatorMathsDo arithmetic on a number. Inputs: a (num, required), b (num, required). Output: output (num).
VariableMapperRename fieldsMatch one node’s output to another’s input. Inputs: input (any, required). Output: output (same).
JsonExtractorPick a valuePull one field out of data. Inputs: json (json, required), key (string, required). Output: output (json).

Show & send#

Look at results, or deliver them.

Node types: Show & send
TypeDescription
ImageGalleryImage galleryShow the pictures a run made. Inputs: input (image, required). No output: it ends a chain.
AudioPlayerAudio playerHear what a run made. Inputs: input (audio, required). No output: it ends a chain.
TextConsoleText outputShow text as it arrives. Inputs: input (string, required). No output: it ends a chain.
JsonInspectorInspect dataRead raw output. Inputs: input (json, required). No output: it ends a chain.
ShaderPlaybackShader playbackRun a shader with live controls. Inputs: input (code, required). No output: it ends a chain.
GithubDeliveryGitHubCommit results to a repo. Inputs: asset (image, audio, mesh, maps, map, rig, file, required). No output: it ends a chain.
GitlabDeliveryGitLabCommit results to a repo. Inputs: asset (image, audio, mesh, maps, map, rig, file, required). No output: it ends a chain.
PlasticDeliveryPlastic SCMCheck results in to a repo. Inputs: asset (image, audio, mesh, maps, map, rig, file, required). No output: it ends a chain.
UnityDeliveryUnitySend assets to a Unity project. Inputs: asset (image, audio, mesh, maps, map, rig, file, required). No output: it ends a chain.
S3UploaderUpload to S3Put results in a bucket. Inputs: input (image, audio, mesh, maps, map, rig, file, required). No output: it ends a chain.
DiscordSlackDiscord or SlackPost results to a channel. Inputs: text (string), image (image). No output: it ends a chain.
ApiPostActionSend to a URLPOST the result somewhere. Inputs: input (json, string, num, boolean, array, image, audio, mesh, maps, map, rig, file, required). No output: it ends a chain.

Older type ids#

The API also accepts these type ids, so that older workflows keep working. Do not use them in new workflows: they are not on the canvas, and some are refused when a run starts.

InputStage, ProcessingStage, ExportStage, Prompt, Knowledgebase, Service, Github, CloudStorage, ImageGen, 3DTransform, BatchSplitter, IterationGate, PythonSandbox

Next steps