Flow introduction
Flows are the core of lensless — configurable pipelines that chain multiple computation steps into a single, reusable workflow. You can keep them private for your own use or publish them publicly for anyone to run (and pay for).
What is a Flow?
A Flow is a sequence of steps, each performing a specific action:
- ObjectGenerator — generates structured JSON via LLMs
- ModelGenerator — fine-tunes a model on custom data
- ImageGenerator — creates images from prompts or trained models
- ObjectTransformer — transforms JSON data with Flow Language operators
- Zipper — bundles outputs into a downloadable archive
Every Flow has:
- Schema-based input — a JSON Schema that defines what the user provides.
- Step definitions — the list of steps describing what to do and in what order.
- UI configuration — how the form and results are presented.
Fields overview
titlestringrequiredA human-readable title for your Flow. Displayed on the Flow page and in dashboards.
descriptionstringrequiredShort text explaining what your Flow does. Also shown on the Flow page.
publicbooleanWhether the Flow is publicly accessible. Public Flows can be run by anyone with the link and can have a price set.
runPricenumber (4–200)Price charged per run if the Flow is public, in the currency specified by
runPriceCurrency.
runPriceCurrencystringISO currency code for the runPrice (e.g., "USD", "EUR", "BRL").
payoutMethodstring: Wallet | ConnectHow you receive money from paid Flow runs. "Wallet" credits your
organization balance; "Connect" pays out via your connected payout account.
inputobject (JSON Schema)Describes the user input form. See Flow Input & Form for details.
stepsarrayThe sequence of computation steps. Each step has an id, type, and
parameters. See Steps for details.
storeobjectA global object available to all steps during a run. Useful for static data like prompt lists or configuration values that multiple steps need.
uiobjectControls how the Flow page looks and how results are displayed. See UI Configuration and Results & Widgets.
slugstringA unique identifier for the Flow URL. If not provided, one is auto-generated. Must be unique across all Flows.
Example Flow
Here’s a Flow that takes user photos and a recipe type, trains a model, generates images, and zips everything:
{
title: 'You with different recipes!',
description: 'Train a model using photos of yourself and generate images with different recipes!',
public: true,
runPrice: 12,
runPriceCurrency: 'USD',
input: {
type: 'object',
required: ['userDatasetId'],
properties: {
recipeType: {
type: 'string',
title: 'Recipe type',
placeholder: 'Homemade Japanese dishes',
},
userDatasetId: {
type: 'string',
title: 'Your photos',
dataset: true,
},
},
},
steps: [
{
id: 'recipesGenerator',
type: 'ObjectGenerator',
parameters: {
description: 'You are an experienced chef. Generate creative recipes.',
input: '$.input.recipeType',
schema: {
type: 'object',
required: ['recipes'],
properties: {
recipes: {
type: 'array',
items: {
type: 'object',
properties: {
name: { type: 'string' },
imagePrompt: { type: 'string' },
},
},
},
},
},
},
},
{
id: 'recipeModelTrainer',
type: 'ModelGenerator',
parameters: {
datasetId: '$.input.userDatasetId',
settings: {
baseModel: 'stable-diffusion-v1-5/stable-diffusion-v1-5',
epochs: 50,
resolution: 1024,
},
},
},
{
id: 'recipeImageGenerator',
type: 'ImageGenerator',
parameters: {
trainingId: '$.results.recipeModelTrainer.id',
baseModel: 'stable-diffusion-v1-5/stable-diffusion-v1-5',
images: [
[
'@Map($.results.recipesGenerator.recipes)',
{
prompt: '$$.imagePrompt',
negativePrompt: 'blurry, low quality',
steps: 25,
},
],
],
},
},
{
id: 'zipOutput',
type: 'Zipper',
parameters: {
sources: ['recipeImageGenerator', 'recipesGenerator'],
},
},
],
}
When this Flow runs, it:
- Asks the user for a recipe type and a dataset of photos.
- Generates a list of recipes with the ObjectGenerator.
- Trains a custom model on the user’s photos.
- Generates images using the trained model and recipe prompts.
- Zips everything for easy download.
Key concepts
Public vs. private Flows
- Private Flows: Only you and your organization can access and run these. Costs deduct from your organization balance.
- Public Flows: Anyone with the URL can run them. You can set a price per run and receive payouts.
Store
The store is a global object defined in your Flow configuration that’s available to all steps during a run. It’s useful for static data that multiple steps need — like a list of prompts or shared configuration:
{
store: {
styles: ['cyberpunk', 'watercolor', 'oil painting'],
negativePrompt: 'blurry, low quality, deformed',
},
steps: [
{
id: 'imageGen',
type: 'ImageGenerator',
parameters: {
images: [
[
'@Map($.store.styles)',
{
prompt: '$$',
negativePrompt: '$.store.negativePrompt',
},
],
],
},
},
],
}
Results
Steps can read from each other’s results using JSON Path, like $.results.previousStepId.field. The user sees a final set of widgets after the run completes (images, JSON objects, downloadable zip, etc.). See Results & Widgets.
Costs and billing
Each step has an associated cost that deducts from the organization balance. When a Flow is public and has a price, external users pay via Stripe and you receive the payout. See Billing for the full pricing table.