— Documentation

Objects, flows and formulas

Three notions are enough to build an application on Slamflow: objects that describe your data, flows that make it live, and formulas that compute whatever needs computing. This page covers all three, in that order.

01

Objects

An object is a data type you define: a customer, an order, a ticket. It acts as table, form and screen at once — you describe its fields, the rest follows.

The record

One occurrence of the object: a given customer, a given order. This is what your users create and edit every day.

The field

A piece of information carried by the object. Its type decides input, display and checks — a date is not a piece of text.

The relation

A field pointing to another object: an order belongs to a customer. Both sides are kept in step.

Field types

The type does more than store: it decides what users can enter, what is displayed and what gets checked.

TextFieldTextAreaNumberCurrencyCheckboxDateDateAndTimeEmailPhoneURLValuesListRelatedObjectIncludedObjectFileFormulaAutoNumberBarCodeAddressUserSubOrganizationHtmlContent

Worth knowing. A Formula field computes itself and is never typed in. An AutoNumber field assigns a number on creation, following the pattern you give it. Those two remove most manual entry.

02

Flows

A flow is a sequence of tasks run in order. It sends an email, creates a record, calls an external service or shows a screen — without a line of code.

What starts a flow

manualA button, on a record page or in a list.
object_after_upsertAfter a record is created or changed.
object_before_upsertBefore the record is saved — where you complete or reject it.
scheduledAt a fixed time, on a schedule.
webhookAn incoming call from another piece of software.
received_mailAn email arriving in a watched mailbox.

Tasks

Each task does one thing only. Here are the most common ones; the platform ships about thirty.

getdecisionupsert_cobjectupdate_cobjectdelete_cobjectvariable_affectationloopemailsmsscreengenerate_pdfhttp_requestgoto_task

Worth knowing. A task publishes its result under its own name: a get task called theCustomer is then read as theCustomer.company_name in later tasks. That is what lets you chain tasks without copying anything.

03

Four flows, end to end

Each example gives the trigger, the sequence of tasks and the exact formulas. They can be copied as they are, replacing the field names with your own.

1. Acknowledge a request

object_after_upsert

As soon as a request is saved, the customer receives a personal confirmation carrying its reference.

  1. 1getLoad the customer the request belongs to.id == context.new.client[0]
  2. 2emailSend them the confirmation.leClient.email

2. Raise an alert above an amount

object_after_upsert

A request above ten thousand euros goes to approval: the manager is notified, the others trigger nothing.

  1. 1decisionOnly carry on when the amount is above the threshold.context.new.montant > 10000
  2. 2getLoad the manager named on the request.id == context.new.responsable[0]
  3. 3emailSend them the alert.leResponsable.email

3. Chase quotes with no answer

scheduled

Every morning, sent quotes whose validity has passed are chased, one by one.

  1. 1getFind quotes that were sent and have expired.statut == 'Envoyé' && date_validite < $System.currentDate
  2. 2loopWalk through the resulting list.lesDevis ?? []
  3. 3emailChase the contact on the current quote.leDevis.contact_email

4. Send an order summary

manual

From a button on the record, the summary is built as a PDF then sent to the customer with the document attached.

  1. 1getReload the full order.id == context.commande.id
  2. 2generate_pdfBuild the PDF from the template.
  3. 3emailSend it to the customer, as an attachment.laCommande.client_email

The email body

The email content is HTML in which you place formulas between double braces. Each one is evaluated when the email is sent.

<p>Bonjour {{ leClient.prenom }},</p>

<p>Nous avons bien reçu votre demande
   {{ context.new.reference }} du
   {{ context.new.date_creation }}.</p>

<p>Montant estimé : {{ context.new.montant }} €</p>

Everything available in a formula is available here: the record's fields, the result of earlier tasks, the system variables.

04

Formulas

A formula is an expression returning a value: a computation, a condition, a composed piece of text. It is the only place in the platform where you write something resembling code — and it stays one line, not a program.

Where you write them

  • In a Formula field, for a value computed at all times.
  • In a decision task, to choose how a flow continues.
  • In a task's values: an email recipient, a field to write.
  • In a validation rule, which rejects the record when it returns false.

Syntax

The usual operators work: the four operations, comparisons, and logical and/or. A field is referred to by its technical name. ?? provides a fallback when the first value is empty.

prix_ht * 1.2
quantite > 0 && statut == 'Validé'
prenom + ' ' + nom
date_fin ?? $System.currentDate

Functions

Eight functions are available, with no prefix and in upper case.

FunctionWhat it does
NOW()The current instant, for timestamping.
ISBLANK(texte)True when the text is empty or missing.
ADD(a, b)Adds two integers.
MROUND(valeur, multiple)Rounds to the nearest multiple — to the quarter hour, to the ten.
ROUNDUP(valeur, multiple)Rounds to the multiple above, never below.
ROUND_HALFUP(valeur, décimales)Rounds to a number of decimals, half upwards.
GETOBJECT('type', identifiant)Loads a record by its identifier and returns its fields.
DEBUG(valeur)Writes a value to the logs, while you work out a computation.

This list will grow: further functions — text, dates, totals across records — are planned, and we add more as the need arises. In the meantime, concatenate with + and have a flow write a running total.

Available variables

Besides the record's own fields, three variables are always there:

$User.id$User.organization$System.currentDate

Inside a flow, the input data is read under context, followed by the name you gave the variable. In a flow triggered by a record, context.new is the record that has just been written.

context.demande.montant
context.new.email
GETOBJECT('client', context.demande.client[0]).raison_sociale

Four pitfalls worth knowing

A relation is a list

Even when it points to a single record. Write context.request.customer[0], never context.request.customer on its own.

Apostrophes inside text

Use the typographic apostrophe ’ or escape it with \'. Two straight apostrophes in a row make the expression ambiguous and it fails.

The context prefix

In a manual flow, the input record is only reachable under context. Dropping the prefix returns an empty value, with no error message.

Empty values

Concatenating an empty field yields an empty result. Guard with (my_field ?? ') as soon as a field may be left blank.

05

Granting access to an AI

Slamflow exposes an MCP server: an assistant such as Claude can read and configure your organization — create objects, write flows, search records. Access goes through a key attached to a user.

Creating the key

  1. 1

    In the administration, open Users then the record of the person who will carry the access. You must be an administrator of the organization.

  2. 2

    In the "API key" block, click Generate an API key.

  3. 3

    Copy the key shown. It starts with sk- and is displayed only once.

  4. 4

    Paste the configuration offered by the screen into your AI client, then restart it.

The key is shown only once. No screen lets you read it again afterwards. If it is lost, regenerate it — the previous one is invalidated immediately.

Client configuration

There is nothing to compose or adapt: the screen that generates the key asks which tool you use, and shows the configuration that suits it — your instance URL included — with a button to copy it. All that is left is to paste it into the file shown.

{
  "mcpServers": {
    "slamflow-mon-organisation": {
      "type": "http",
      "url": "https://<votre-instance>/mcp",
      "headers": { "x-api-key": "sk-…" }
    }
  }
}

Supported tools

Pick yours on the key screen: the configuration then takes the shape it expects, and the file to paste it into is shown just above.

  • Claude Code

    .mcp.json

    Restart, then approve the server when asked.

  • Cursor

    ~/.cursor/mcp.json

  • VS Code (Copilot)

    .vscode/mcp.json

  • Claude Desktop

    claude_desktop_config.json

    It cannot yet reach a remote server with a header; the screen then gives you a configuration that goes through the mcp-remote bridge.

  • ChatGPT

    Settings → Connectors (developer mode)

    It is configured in its own interface, with no file: the screen gives you the URL and the key to enter there, choosing API key authentication.

Your first exchange

Once the client is connected, describe what you want in plain words. There is nothing else to learn:

In my Slamflow organization, build a field-service app: customers, sites, jobs with a date, a technician, a status and time spent; a list of jobs to schedule and a dashboard per technician.

The assistant creates the object types, the fields, the lists and the screens, then hands back. You open your application and fix whatever does not suit you, by asking.

What the key allows, and what it does not

  • It only grants access to its user's organization, never another one.
  • It acts with that user's rights: their role, their field-level security. A key held by a non-administrator account cannot change the configuration.
  • It is only used for the MCP server, and is revoked from the same screen, with immediate effect.

Ready to deploy your solution?

Get in touch, or start your free trial today.

Slamflow© 2026 · About us · slamflow.com