[data-reveal]{opacity:1!important;transform:none!important}
AntelopeJS DMS
DocumentationAutomation nodes

Automation nodes

The triggers and actions the DMS registers in the procedure builder of the automation module, their inputs, test runs, and the $ keys their texts use.

When @antelopejs/dms-automation is loaded, the DMS registers its own nodes in the procedure builder. It adds triggers for its events (dms.member-added, dms.member-removed, dms.invite-created, dms.user-registered, dms.record-created, dms.record-updated, dms.record-deleted) and the actions below. Every input of an action is a port. Set it in the inspector, or wire it from a trigger's output or a data node.

dms.send-notification

Sends an in-app notification under the AutomationSubject, built as the Notification() builder builds it.

InputTypeNotes
titlestring, requiredLiteral text, or a $ translation key resolved in each recipient's language
descriptionstringSame as title. Empty by default
paramsobjectInterpolation params of both texts. Strings and numbers are kept, booleans read as their text, and nested values are dropped with a warning
toneneutral primary success warning errorIcon well colour. Unset reads primary while unread
icon, linkTostringi-ph-bell by default, and the page the notification opens
userIdstringOne recipient, such as a trigger's userId
userIdsstringRecipients, combined with userId
roleIdsstringEvery member holding one of the roles
tenantIdstringRestricts roleIds to that tenant's members (toRoles(roleIds, { tenantId })). Empty means the default tenant
idempotencyKeystringStable event key, such as a trigger's deliveryId. A replay of the same event reaches each recipient once

At least one of userId, userIds or roleIds is required. Otherwise the run fails with dms.send-notification requires at least one of userId / userIds / roleIds.

A procedure that welcomes each new member, with its texts in the project's locales, wires a Member added trigger (dms.member-added) to a Send notification node set as follows:

PortValue
userIdwired from the trigger's userId
title$my_app.automation.welcome.title
description$my_app.automation.welcome.body
params{ "team": "Support" }, set in the inspector or wired from a node that outputs an object
tonesuccess
linkTo/getting-started
idempotencyKeywired from the trigger's deliveryId

The keys live in the project's locale files like any other (Localization):

frontend-vue/i18n/locales/my-app-en-GB.json json
{
  "my_app": {
    "automation": {
      "welcome": {
        "title": "Welcome aboard",
        "body": "The {team} team is here to help."
      }
    }
  }
}

A notification node set up with a literal title and description, before these inputs existed, keeps working unchanged.

dms.send-email

Sends an email through the project's interface-email provider (Email templates and rendering).

InputTypeNotes
tostring, requiredRecipient address
subjectstring, requiredSubject line, sent as given
htmlstringThe body, written out
templatestringName of a template registered with RegisterHtmlTemplate, rendered instead of html
propsobjectProps the template is rendered with
languagestringLanguage the template is rendered in. The recipient's own when the address belongs to a user

One of html or template is required. A template that no module registered fails the run instead of sending an empty email. The output holds success, and messageId or error.

dms.invite-user

Invites an address to a tenant, as the members page does. An existing user becomes a member directly. Anyone else receives an invitation, and its email unless sendEmail is false. An address that is already a member is left unchanged.

InputTypeNotes
emailstring, requiredAddress to invite
tenantIdstringTenant to invite into. See the tenantId input
roleIdsstringRoles of the new member
asTenantOwnerbooleanfalse by default
sendEmailbooleantrue by default
languagestringLanguage of the invitation email and of the account it leads to. en when empty
firstname, lastnamestringThe invitee's names, stored with the invitation and used in its greeting
inviterNamestringWho the invitation email says it comes from

The output kind is added, invited or already-member, with the userId or the inviteId.

The tenantId input

An action has no tenant of its own. The execution context carries none, whoever fires the procedure. A node that acts on tenant data therefore takes a tenantId input, which a procedure wires from its trigger. The member, invite and registration triggers output the tenantId of their event.

Left empty, a tenant-scoped node acts on the default tenant (DEFAULT_TENANT_ID, "default", from @antelopejs/interface-dms/constants). A single-tenant project has only that tenant. dms.invite-user invites there, and dms.send-notification matches its roleIds there. In a multi-tenant project, wire the trigger's tenantId into every node that takes one.

Test runs

The three actions declare dryRun. A Test run in the builder checks their input as a real run would, then sends and creates nothing.

ActionIn a test runOutput
dms.send-emailRefuses a missing body or an unregistered template. Renders and sends nothing{ success: true }
dms.send-notificationRefuses a missing recipient, an unknown tone or bad params. Notifies nobody{ ok: true }
dms.invite-userLooks the address up in the tenant. Creates no user, member or invite, and sends no emailalready-member or added with the user's id, else invited with no inviteId

Texts in the builder

The builder shows a node's name and description, and each schema property's title and description, through processI18n. Each one can be a $ key instead of literal text. The DMS nodes carry keys only, under dms.automation.* of the dms-core locales (en and fr):

  • triggers.<trigger> and actions.<action> hold a node's name, its description, and its per-node field descriptions.
  • fields.<property> holds the field labels that its nodes share.

A module that registers nodes of its own does the same under its namespace:

src/automation/my-action.ts ts
export const myAction: ActionType = {
  id: "my_app.archive",
  name: "$my_app.automation.archive.name",
  description: "$my_app.automation.archive.description",
  inputSchema: {
    type: "object",
    properties: {
      reason: { type: "string", title: "$my_app.automation.fields.reason" },
    },
  },
  // ...
};

The builder names an untitled property by its key in words. The canvas labels a port by its key, whatever its title.