Integration Node SDK

Build custom nodes for Integration Studio workflows — define the node, its inputs and config, and what it does when it runs.

Integration Studio workflows are built from nodes — each node is one step that runs and passes its output to the next. The platform ships a catalog of common nodes (HTTP request, send email, transform, filter, conditionals, and more). When you need a step that isn't in the catalog, the Integration Node SDK is how you build your own.

Status: shipped (1.x). @revenexx/integrations-node-sdk is published and past its 1.0. Check the package's release notes before upgrading across a major version.

This page covers writing a node. For building and running workflows in the editor, see Integration Studio.

Install

The SDK package is @revenexx/integrations-node-sdk, published on the public npm registry. It needs Node 20.3 or newer.

npm
npm install @revenexx/integrations-node-sdk

No registry configuration and no token are needed to install it.

Define a node

A node is a class that implements the SDK's INode interface. It has a description (what the node is, its inputs and outputs, and its config fields) and an execute method (what it does when the workflow reaches it).

Node
import type {
  INode,
  INodeContext,
  INodeDescription,
  INodeResult,
} from "@revenexx/integrations-node-sdk";

export class GreetNode implements INode {
  readonly description: INodeDescription = {
    slug: "acme:greet",
    name: { en: "Greet", de: "Begrüßen" },
    description: { en: "Builds a greeting string." },
    version: "1.0.0",
    category: "transform",
    inputs: [{ name: "in" }],
    outputs: [{ name: "out" }],
    config: [
      { key: "name", type: "string", label: { en: "Name" }, required: true },
    ],
  };

  async execute(
    _ctx: INodeContext,
    input: { name: string },
  ): Promise<INodeResult> {
    return { outputs: { out: { greeting: `Hello, ${input.name}!` } } };
  }
}

The category is one of trigger, action, transform, control, or io — it tells the editor where the node belongs. Names, descriptions, and labels are keyed by locale so the editor can show them in the user's language.

Export your nodes

Export your nodes from a NODES array. The package's build step reads it and generates the manifest the platform uses to discover the nodes.

index.ts
import type { INode } from "@revenexx/integrations-node-sdk";
import { GreetNode } from "./nodes/greet/GreetNode.js";

export const NODES: INode[] = [new GreetNode()];

Build the package

The SDK ships a CLI, rvnxx-nodes, with exactly one subcommand: manifest. It reads your NODES array and writes the manifest the platform uses to discover the nodes. Wire it into your build:

package.json
{
  "scripts": {
    "build": "tsup && rvnxx-nodes manifest"
  }
}
Build
npm run build

That produces the compiled package plus a manifest.json.

There is deliberately no publish command. An earlier rvnxx-nodes publish was removed: node packages are not published from their own repo.

Getting your package registered

Registration is operator-mediated, not self-service. There is no public endpoint and no Cockpit flow that lets you register a node package on a tenant yourself. You hand the built package to revenexx, and a platform operator registers it for the tenant; the nodes then appear in the Integration Studio editor for that tenant's workflows.

Plan for that turnaround in your release process — it is a human step, not a deploy.

Authenticating to external systems

When a node calls an external system, it uses a credential — a typed, named secret your tenant configures once and reuses across nodes. A node references a credential by type; the platform supplies the resolved secret at run time. For example, a node that calls an HTTP API with a bearer token references an HTTP-bearer credential and sends Authorization: Bearer <token> on its request.

A real node to learn from

The platform's own catalog of built-in nodes — HTTP request, transforms, file I/O, and the rest — is built with this same SDK, so every entry in it is an INode implementation shaped exactly like yours. Its source isn't published, so read the shapes from the SDK's own type definitions and the behaviour from Node types; ask your revenexx contact if you need to see a full implementation.

Where to go next

Was this page helpful?