Data & connectionsGuide

Integrations

An integration is a saved connection to something outside Waiso — a database, a bucket, an AI account, an API. You set it up once on the project’s Integrations page; after that, scripts, flow steps, the SQL workbench and the AI features use it by name, and nobody types a password into code again.

9 min readBefore this: Create a projectOpen in Waiso
What you will learn
  • Know the kinds of connection and what each one is for
  • Add a connection and confirm the secret variables it creates
  • Reach a database on a private network through an SSH or Tailscale tunnel
  • Test a connection and read what a failure means

What a connection holds

A connection has two halves. The settings — host, port, database, bucket, region, base address — stay on the connection and anyone with access to the page can read them. The credentials — a password, an access key, an API key — are not kept on the connection at all: saving turns each one into a secret variable of the project, and the connection reads it from there every time it is used.

IntegrationsConnect databases, storage and services to use them from the workbench and your scripts.
Add integration
Search integrations…Ctrl KAll · 5DatabasesStorageServices
shop_dbPostgreSQL · db.internal:5432/docs_demoKindDatabaseStatusConnectedLast used6 min ago
shop_filesS3 · shop-files · us-east-1KindStorageStatusConnectedLast usedjust now
claudeAI provider · AnthropicKindServiceStatusConnectedLast used2 h ago
sales_sheetsGoogle · ana@shop.devKindServiceStatusConnectedLast usedtoday
EmailSend emails from scripts and flows.KindServiceStatusEnabledLast used—
Each card shows the kind, the address it points at, its last test and when it was last used.

Connections belong to one project. The page lists them as cards you can search and filter by Databases, Storage and Services; a card’s Open takes a database to its SQL workbench, Browse Files takes a bucket to its file browser, and the ⋯ menu holds Test connection, Edit and Delete.

The kinds of connection

KindGroupUsed bySecret variables
PostgreSQLDatabasesSQL scripts, flow SQL steps, the workbenchPG_<NAME>_PASSWORD
MySQLDatabasesSQL scripts, flow SQL steps, the workbenchMYSQL_<NAME>_PASSWORD
Amazon S3StorageThe SDK’s s3 functions, the file browserS3_<NAME>_ACCESS_KEY_ID, …_SECRET_ACCESS_KEY
AI providerServicesThe assistants, the AI step, the AI ScraperAI_<NAME>_API_KEY
API (HTTP)ServicesThe flow’s HTTP Request stepDepends on the sign-in
EmailServicesThe flow’s Email step, the Email pageOne per provider credential

The AI provider and API (HTTP) kinds have their own pages: Connect an AI provider and API (HTTP) connections. Email is a service you switch on here and configure on its own page — see Email.

Add a connection

  1. Open the dialog

    On Integrations, click Add integration (or right-click an empty area of the page). The dialog Connect a data source lists every kind on the left, grouped and searchable with Search integrations…; About on the right says what each one is for.

  2. Name it and fill the settings

    The Name matters twice: it is how scripts and steps pick the connection, and it names its variables. A database asks for Host, Port (5432 or 3306 filled in), User, Database, Password and SSL mode; or switch to the Connection string tab, paste postgresql://user:password@host:5432/dbname and press Apply to fill them.

  3. Choose how to reach a database

    Under How to reach the database, keep Direct when it has a public address, or pick SSH tunnel or Tailscale (next section).

  4. Confirm the variables

    Save connection first opens Variables this connection creates, listing the exact names. Click Confirm and save. A name that is already taken is marked already exists — change the connection name, and the save waits until you rename the connection.

Credentials are secret variables

The variable names are derived from the connection’s name, never typed: the kind’s prefix, then the name in capitals with every other character turned into _, then the field. A PostgreSQL connection named Main DB stores its password as PG_MAIN_DB_PASSWORD; an S3 connection named S3 Data gives S3_DATA_ACCESS_KEY_ID and S3_DATA_SECRET_ACCESS_KEY (the prefix is not repeated). Only credentials become variables — host, user and bucket stay settings.

Variables & SecretsProject-scoped environment variables and encrypted secrets
Copy from globalImport .envNew variable
Search variables…Ctrl KAllVariablesSecretsFrom integrations
PG_SHOP_DB_PASSWORDfrom shop_db TypesecretValue••••••Updated6 min ago
REPORT_TITLEPlain value, readable by scripts and flowsTypeplainValueDaily salesUpdated11 h ago
S3_SHOP_FILES_ACCESS_KEY_IDfrom shop_files TypesecretValue••••••Updated11 h ago
S3_SHOP_FILES_SECRET_ACCESS_KEYfrom shop_files TypesecretValue••••••Updated11 h ago
SHOP_API_KEYEncrypted at rest, never shown in logsTypesecretValue••••••Updated11 h ago
Variables made by a connection carry its icon and a “from …” link back to it.
  • Editing the connection shows each credential as a chip with the variable’s name — Stored as the secret variable … Click to edit its value. — instead of a password box. Changing the value there or on the Variables page is the same thing: it re-keys the connection.
  • Renaming the connection renames its variables; the confirmation lists the names that go away. The values are kept.
  • Renaming the variable yourself does not break anything: the connection finds its credential by what it is, not by its name.
  • Deleting the variable leaves the connection without a credential. Its card says Credential missing: … — open the connection and enter it again., runs that use it fail with credential_missing, and typing the value in the connection creates the variable again.
  • Deleting the connection deletes the variables it made. A connection that scripts still use cannot be deleted: the dialog lists them (Used by …).

Secret values are encrypted at rest with AES-256-GCM and never come back in any list or answer. Like every variable, they also reach your scripts as environment variables — see Variables and secrets.

Databases on a private network

Runs can only reach public addresses. A host on a private network — 10.x, 192.168.x, 172.16–31.x, localhost, link-local or CGNAT ranges — is refused, and the test says so: This host is on a private network (an internal address). Runs cannot reach it — use the database public address. To reach it anyway, pick a tunnel:

RouteWhenWhat you fill
DirectThe database has a public addressNothing more
SSH tunnelThrough a bastion host you already haveBastion host, Port, User, a Private key (with its passphrase) or a Password
TailscaleThe database is in your tailnetAn Auth key and, optionally, a Device name

With a tunnel, Host is the database address as seen from inside the private network. The first test of an SSH tunnel shows the bastion’s fingerprint — Confirm the bastion’s identity, check it with whoever runs the server, and press Trust and test. If that identity changes later, connections stop until you trust the new key. Tunnel secrets are stored as secret variables like every other credential.

Test a connection

Test connection does the real thing: a database test opens a connection and runs a query, an S3 test checks the bucket with your keys, an AI test sends one tiny request. The card then shows Connected or Failed with the time, and a failure gives a reason in plain words — the tunnel could not open, the database refused the credentials, the host did not answer. Databases and buckets are re-tested by themselves when you open the page and their last test is more than five minutes old; AI providers are tested only when you press the button, because a test spends your own quota.

Codes you may meet

  • credential_missing — the connection’s secret variable was deleted. Open the connection and enter the value again.
  • host_not_allowed — an outbound address the worker refused because it is private: a custom SMTP host, a file uploaded from an internal URL.
  • variable_name_taken — a variable with one of the derived names already exists. Rename the connection.

Limits and rules

  • A connection’s kind cannot change after it is created (Integration type cannot be changed after creation).
  • One S3 connection per project: the SDK’s uploads always go to the project’s bucket.
  • On the cloud, SQL and S3 connections are counted per plan — Free 1, Pro 3, Team 10, Business unlimited. The dialog says how many you use before you try.
  • Your script code never opens a socket: user code runs with no network. Queries and file transfers are done by the worker on the script’s behalf, through the connection.