Back offices
Look up and edit customers, orders and coupons without building an admin.
TypeScript · one Node process · your own app
Write each tool as an async TypeScript function. Every await io asks a person in the browser and waits for the answer. The server and the UI run inside your own app, so there is nothing else to host.
How it works
Every await io.input… shows a form to the person running the action and pauses your function until they answer. Then it simply goes on.
Components
Each one is a call on io that shows a control and returns a typed value. Missing one? Write it.
io.input.textDocs →One line of text
io.input.emailDocs →An email address
io.input.urlDocs →A web address, returned as a URL
io.input.textareaDocs →Longer text
io.input.numberDocs →A number with min, max and decimals
io.input.booleanDocs →Yes or no, with a checkbox
io.input.datetimeDocs →A date and time, as a luxon DateTime
io.input.dateDocs →A day, as a luxon DateTime
io.select.singleDocs →One option from a drop-down
io.select.multipleDocs →Any number of options
io.select.tableDocs →Rows picked from a table
io.confirmDocs →Ask before something irreversible
io.groupDocs →Several inputs on one screen
io.display.tableDocs →Rows from your database, with links and paging
io.display.metadataDocs →Label and value tiles
io.display.linkDocs →A link inside or outside the app
io.display.headingDocs →A section title
io.display.imageDocs →A picture, such as a file preview
io.display.markdownDocs →Formatted text in a step
io.display.objectDocs →A record as a JSON tree
io.display.htmlDocs →HTML markup, sanitized first
io.input.yours()What people build
Anything a person should run, fill in or approve, written as one async function next to the code it needs.
Look up and edit customers, orders and coupons without building an admin.
Give support the few safe buttons they need, each one checked in code.
Turn the migration you would run from a laptop into an action with inputs and a confirmation.
Ask for a month or a customer and return a table, straight from your database.
A handler is a plain function in your own process. Your Prisma client, services, utilities and environment variables work as they are.
A component is plain React in one file, with its props and the value it returns. Register it next to the built-in ones and await it like any io method.
Production, staging and local are separate servers with their own secrets and data. AwaitIO deploys with the rest of your app, and the header switches between them.
Email and password login with scrypt hashes and signed cookies, runs visible only to the person who started them, and nothing sent anywhere: no hosted service, no telemetry.
Up to 3 users free, including commercial use. Larger teams pay one flat monthly price, and it is the same software either way.