# Page


# Introduction

Ondeva’s **Workflow engine** is where your application logic comes to life. It’s built for **precision automation, powerful integrations**, and **cross-system control**—without writing backend code.

Whether you're building a startup MVP, internal tool, client portal, or enterprise process—Workflows allow you to define the **logic, triggers, and data flow** that make your application smart, dynamic, and autonomous.

Unlike traditional no-code automators, Ondeva workflows combine **developer-grade logic** (API calls, loops, branching, async execution) with a visual builder that’s designed for clarity, speed, and reuse.

***

### **What You Can Do with Workflows**

* Automate actions triggered by **forms, button clicks, page loads, or time schedules**
* **Read, write, transform, and delete data** in your unified data layer
* **Call external APIs**, pass and parse responses
* Build modular logic using conditions, loops, and sub-workflows
* Run **AI-powered steps** like text generation, keyword extraction, and audio transcription
* Handle user identity, enforce licensing, and manage session-based logic
* **Trigger client-side actions** like navigation, downloads, and analytics events

***

### **How It Works**

* You build logic visually on a drag-and-drop **canvas**
* Each workflow consists of **steps** (actions) and **events** (triggers)
* You can pass data via **variables and session parameters**
* Every workflow is fully debuggable and testable before going live
* Once published, it’s available app-wide — and reusable across forms, buttons, APIs, and more


# User Interface

Ondeva’s Workflow Builder provides a visual programming interface that lets you design automations, conditional logic, and data flows without touching code — while remaining powerful enough for real-world, cross-system automation. Here's a breakdown of the UI to help you navigate with confidence.

The Workflow Builder interface is divided into four main regions:

1. **Left Panel – Step Library**
2. **Central Canvas – Workflow Flowchart**
3. **Right Panel – Properties & Configuration**
4. **Top Bar – Workflow Actions & Metadata**

***

### **Left Panel: Step Library**

This is where you select the building blocks of your workflow. Steps are grouped into categories:

* [**Presentation**](/workflow/steps-reference/presentation) (e.g., Show Dialog)
* [**Logic**](/workflow/steps-reference/logic) (e.g., Condition Checks, Loops)
* [**Data**](/workflow/steps-reference/data) (e.g., Save Entry, Load Query)
* [**AI**](/workflow/steps-reference/ai-integration) (e.g., Text Generation, Summarization)
* [**UX & Browser**](/workflow/steps-reference/ux-and-browser-control) (e.g., Redirect, JS Execution)
* [**User Flow & E-Commerce**](/workflow/steps-reference/user-flow-and-e-commerce) (e.g., Login, License Enforcing)

**How to Use:**

* Drag a step from the library and drop it onto the canvas
* Use the scroll or search to find specific steps

***

### **Central Canvas: Visual Flow Editor**

This is your primary working area where you build and connect steps in a flow.

**Key Interactions:**

* **Drag & Drop**: Arrange steps freely
* **Connect Steps**: Click the output node of a step (small circle) and drag to another to define execution order
* **Zoom & Pan**: Use your mouse scroll to zoom and drag the background to navigate across large workflows
* **Right-click (coming soon)**: For fast actions like duplicate, delete

**Structure:**

* Steps execute sequentially based on your visual flow
* Branches (e.g., from conditions or loops) allow complex logic trees

***

### **Right Panel: Properties Editor**

The right-hand panel dynamically shows options for the currently [selected step](/workflow/steps-reference) or global workflow settings if no step is selected.

**Modes:**

* **Step Selected**: Edit fields like target table, variables, conditions, API endpoint, etc.
* **No Selection**: Shows **general workflow settings**, including:
  * `Execute via JS Function`: Allows you to run this workflow from frontend components via a custom JavaScript call.

    ```jsx
    const showBusyIndicator = true;
    const properties = {
    	'variable1': 'value1';
    }
    triggerAction('ID_OF_WORKFLOW', showBusyIndicator, properties);
    ```
  * `Ensure Authentication`: Enforces login before the workflow can execute

***

### **Top Bar: Workflow Controls**

This area contains core controls for saving, testing, and publishing your workflow.

**Controls:**

* **Expand**: Toggles step cards between compact and detailed views
* **Execute**: Runs the workflow immediately with current data (great for testing)
* **Publish**: Makes the workflow live and usable throughout your app (e.g., via buttons, page triggers, time-based events)
* **Workflow Name**: Click to rename your workflow

***

### **Workflow Events & Triggers**

In the global settings panel you can define how this workflow is triggered.

**Supported Event Types:**

* Page Load
* Page Load Completed
* Time Trigger (e.g., every hour, every day at 9am)
* Custom Events

**How to Use:**

* Define one or more triggers per workflow.
* Button click, file upload completed and form submission events are created automatically when you select the workflow in the respective configuration of the UI component.

***

### **Tips for Navigating the UI**

* **Use naming consistently**: Label workflows clearly for reuse across your app
* **Modularize logic**: Use sub-workflows (via "Execute Workflow") to keep flows clean
* **Zoom out often**: Large workflows can get complex — use spacing and grouping visually
* **Preview values**: Use session and variable names consistently to make logic traceable in debugging


# Events

In Ondeva, workflows don’t just sit idle — they respond to **events**. Events define how and when a workflow starts: clicking a button, submitting a form, loading a page, or on a set schedule. You can also trigger workflows from other workflows or via custom events and exposed APIs.

### **Where to Configure Events**

Button click, file upload completed, API call and form submission events are created automatically when you select the workflow in the respective configuration of the UI component.

Other events you can create in the **Workflow Builder**, leave no step selected in the canvas. You’ll find the **Events** section.

You can assign **one or multiple triggers** per workflow.

***

### **Event Types**

#### **Button Click**

**Trigger:**

The workflow runs when a specific button component is clicked.

**How to Use:**

* Select the workflow in the configuration of the Button UI component.

**When to Use:**

* Submit forms
* Trigger dialogs or conditional flows from user actions
* Add items to cart, save entries, start onboarding steps

***

#### **Form Submission**

**Trigger:**

Runs when a form component is submitted.

**How to Use:**

* Select the workflow in the configuration of the Submit Form Button UI component.
* Pair with [“Read Form Fields”](/workflow/steps-reference/data#read-form-fields) in the workflow to extract data

**When to Use:**

* Capture user input and persist it
* Trigger follow-ups like emails or redirects

***

#### **Page Load**

**Trigger:**

Fires when a specific page is loaded by the user.

**Options:**

* Set specific pages this should apply to (or leave blank to apply globally)

**When to Use:**

* Prefill data into components
* Set session parameters
* Check licenses

#### **Page Load Completed**

**Trigger:**

Fires on the `DomReady` event of a specific page loaded by the user.

**Options:**

* Set specific pages this should apply to (or leave blank to apply globally)

**When to Use:**

* Execute JavaScript code after a page is loaded.
* Refresh UI components.

***

#### **Time Trigger**

**Trigger:**

Executes the workflow on a scheduled basis.

**Options:**

* **Interval**: every X minutes, hours, or days
* **Fixed Time**: e.g., every day at 07:00
* **Specific Days**: e.g., every Monday and Friday

**When to Use:**

* Clean up stale records
* Send reminder emails
* Sync with third-party APIs on a schedule

***

#### **Custom Events**

**Trigger:**

Responds to an internal event thrown by another workflow (via [“Throw Event”](/workflow/steps-reference/ux-and-browser-control#throw-event) step) or by the system.

**Options:**

* Set specific pages this should apply to (or leave blank to apply globally)
* Event name to listen for that other actions or the system throws

**When to Use:**

* Decouple logic (e.g., throw `user_created` → handle in multiple places)
* Trigger analytics or secondary flows from one action
* Modularize behavior without chaining logic tightly

***

### Best Practices

* **Execution Conditions**: If you need guardrails, use session parameters and logic steps inside the workflow
* Use **Custom Events** to keep workflows modular and loosely coupled
* Be intentional with **time triggers** — avoid unnecessary load


# Debugging & Testing

Ondeva gives you **real-time visibility** into your workflow’s execution. Whether you're saving data, calling APIs, or processing conditions — you can simulate, inspect, and troubleshoot logic directly in the builder without deploying first.

No more blind spots. No more “why didn’t this run?”

### **How to Run a Workflow for Debugging**

In the Workflow Builder top bar, you’ll find the **Execute** button.

#### **Execute (Test Run)**

* Executes your workflow **immediately** from start to finish using current session state
* No trigger required — even event-based workflows can be run this way
* Results and logs are shown live inside the browser console.

***

### **Debugging Tools & Features**

#### Monitoring

Each action execution is logged in the monitoring area of the platform. You can see the log for each executed workflow there. Logs are cleared after 1h.

#### **API Response Handling**

In [Call API](/workflow/steps-reference/logic#call-api) steps:

* You can store the raw response in a variable
* Test runs show actual response content
* Errors (e.g. bad auth, invalid body) are surfaced immediately

#### **Isolated Workflow Runs**

* You can test subflows ([Execute Workflow](/workflow/steps-reference/logic#execute-workflow)) independently
* Parameters from the parent are passed through — but you can simulate local overrides

***

### Debugging Tips

* Store **API results** into session variables to inspect them mid-flow
* Use **invert condition checkboxes** to test both true/false logic quickly
* Use **Remove Session Parameter** at the start of your workflow to clear stale state
* Label branches and comments using workflow step names to stay organized

***

### Publishing vs. Testing

* **Execute** is for **local test runs** — nothing is made live
* **Publish** makes the workflow available to triggers (form, button, time-based)
* Use Execute to **verify behavior before enabling triggers**


# Steps Reference


# Presentation

The **Presentation** category in Ondeva workflows is designed to let you visually interact with users through dialogs and UI refreshes. These steps are especially useful when coordinating between user actions and front-end responses, such as showing feedback modals, refreshing components, or closing overlays.

### **Reload Components**

**Purpose:**

Refresh components in the user interface—either within the main page or inside dialogs—so they reflect the latest data or state.

**Key Options:**

* **Component IDs**: Specify which component(s) should be reloaded (e.g., tables, charts). This field references the markup id of the component(s) you want to refresh.

**When to Use:**

* After updating data and needing to reflect it immediately on screen.
* After a form is submitted and the UI must show updated totals, filters, or list items.

***

### **Show Dialog**

**Purpose:**

Opens a specific dialog modal to the user.

**Key Options:**

* **Dialog Dropdown**: Select the dialog to display (must be predefined in your application’s UI).

**When to Use:**

* For confirmations ("Are you sure?")
* To show contextual actions or forms ("Edit user profile")
* To provide feedback after a process ("Your request has been submitted")

***

### **Close Dialogs**

**Purpose:**

Closes any currently open dialog for the user.

**Options:**

No configuration needed. It simply closes the currently active dialog context.

**When to Use:**

* After a form is submitted or action completed inside a dialog
* To return users to the main screen after a nested interaction

***

### Best practices

* **Dialogs are reusable components** that can contain forms, summaries, or multi-step wizards. These steps let you orchestrate clean UI transitions between them.
* The **reload mechanism is context-aware**, meaning only visible components are updated. Efficient for keeping UI fast and responsive.


# Logic

The **Logic** category enables decision-making, control flow, and integration within workflows. These steps are used to create dynamic, reactive applications that can branch, loop, or integrate with external systems — without writing a single line of backend code.

### **Check Condition (If / Else)**

**Purpose:**

Evaluates one or more conditions and executes different branches of the workflow based on the result (true or false).

**Key Options:**

* **Logic Operator**: `AND` / `OR` — controls how multiple conditions are combined.
* **Conditions**: Define comparisons using left-hand value, operator, and right-hand value (e.g., `user.age > 18`).
* **Invert Result**: Flips the result of the condition (true becomes false, and vice versa).

**Outputs:**

* Two required outputs: one for the **true** branch, one for the **false** branch.

**When to Use:**

* Gate logic based on user roles, values in a form, or backend response.
* Control what happens next depending on whether conditions are met.

***

### **Execute Workflow**

**Purpose:**

Calls another existing workflow (sub-workflow), allowing you to modularize logic and reuse workflows.

**Key Options:**

* **Workflow Selector**: Choose any existing workflow from your app.

**When to Use:**

* To reduce repetition by reusing logic across workflows.
* When creating a "parent" workflow that delegates subtasks.
* For clean separation of logic (e.g., “Send email”, “Log event”, “Sync CRM”).

***

### **For Each**

**Purpose:**

Loops over a list (table, array, query result) and executes a workflow for each item.

**Key Options:**

* **Workflow**: The workflow to execute for each item.
* **Variable**: The list or table to iterate through.
* **Async Mode**: When enabled, Ondeva will process the items in a separate thread / task. Therefore not blocking the user interface and allow the user to continue navigating.

**Optional Enhancements:**

* **After Completion**: Dialog to show after all iterations complete.
* **Progress Dialog**: Dialog to show to the user during async execution. When creating a custom progress dialog you have to mark the places for the progress information with these CSS classes: `progress-current` for the current progress value and `progress-total` for the total amount of items.

**When to Use:**

* Batch-update rows in a table.
* Call external APIs for multiple records.
* Send personalized emails to a filtered group.

***

### **Call API**

**Purpose:**

Connects to external services by calling any HTTP endpoint and stores the response in session variables.

**Key Options:**

* **Endpoint URL**: The target URL of the API.
* **Method**: `GET`, `POST`, `PUT`, `DELETE`, etc.
* **Auth Profile**: Preconfigured authentication (OAuth, token, etc.).
* **Content Type**: Defines the body format (`application/json`, etc.).
* **Body**: Raw JSON body sent with the request. If the request method allows for a payload.
* **Response Handling**:
  * If **Text**: Store in a session variable.
  * If **File**: Save the response to a specified table field.

**Optional Enhancements:**

* **Headers**: Custom headers (optional).

**When to Use:**

* Integrating with third-party tools (CRMs, payment systems, external DBs).
* Sending dynamic data from Ondeva to another system.
* Consuming REST APIs without needing backend code.

***

### Best Practices

* **Keep steps modular**: Use “Execute Workflow” to isolate logic and improve readability.
* **Use session variables to pass state** between condition checks and API calls.
* **Always handle error cases**, especially for external API calls (e.g., use condition checks on HTTP response codes).


# Data

The **Data** category is where Ondeva’s power as a backend platform comes to life. These steps allow you to load, transform, persist, and delete structured data from tables or forms. Whether your data originates from a form, API, or external file — you can capture, manipulate, and store it precisely.

### **Load Query**

**Purpose:**

Executes a saved query and loads its result into the session for later use in the workflow or UI.

**Key Options:**

* **Source**: Choose from any prebuilt query in your project.

**When to Use:**

* Preloading data before branching logic.
* Feeding a “For Each” loop.
* Populating UI components with live query results.

***

### **Save Entry**

**Purpose:**

Creates or updates an entry in a database table.

**Key Options:**

* **Table**: Select which table to write into.
* **Query**: Define filters to find an existing entry (optional). If left blank, a new entry will be created. If filled only matching entries will be updated. The system will not “upsert” records.
* **Fields**: Set which fields to update or insert, and their values (supports function editor and session variables).

**When to Use:**

* Updating rows based on form inputs or calculations.
* Storing processed data from APIs or loops.

***

### **Delete Entry**

**Purpose:**

Deletes a specific row from a table based on its ID.

**Key Options:**

* **Table**
* **Entry ID**: Static or calculated via formula.

**When to Use:**

* Cleanup after user deletion or canceled transactions.
* Removing outdated records via time-based workflows.

***

### **Duplicate Entry**

**Purpose:**

Creates a copy of a specific entry (row) from a table.

**Key Options:**

* **Entry ID**: The original entry to copy.

**When to Use:**

* Cloning templates (e.g., tasks, documents).
* Generating reusable rows from predefined models.

***

### **Read File**

**Purpose:**

Loads data from an external file (Excel, CSV, JSON) into the session for manipulation or saving.

**Key Options:**

* **Path**: File location: You can load a file from three different sources:
  * an external URL
  * a file that was uploaded by the user and the current workflow is executed after upload completion. In that case use the variable `{var_file-path}`
  * or read a JSON file directly, in which case you can reference a variable holding your JSON data in the field.
* **File Type**: Select the file type to load
* **Parsing Options**: Header, sheet number (Excel), date/number format (CSV), JSON path (for nested parsing).

**When to Use:**

* Importing datasets via workflows.
* Syncing data from external exports.
* Processing uploaded files on form submission.

***

### **User Data**

**Purpose:**

Manipulates user-related information such as resetting passwords, managing roles, or triggering invitations.

**Key Actions:**

* Create user
* Send invitation/reset links
* Update roles (add/remove)
* Generate API token
* Logout user

**When to Use:**

* Onboarding flows.
* Automating user role changes.
* Integrating with external identity providers.

***

### **Read Form Fields**

**Purpose:**

Extracts values from a form submitted by a user.

**Key Options:**

* **Form**: The form you're targeting. The form must be present on the page and the workflow must be executed on form submit.
* **Variables**: Map each form field to a named variable for later use.

**When to Use:**

* Triggering workflows from form submissions.
* Capturing input for condition checks, database saves, or emails.
* Replacing backend form handlers with Ondeva-native logic.

***

### **Set Form Validation**

**Purpose:**

Sets whether a form submission passes or fails validation based on custom workflow logic.

**Key Options:**

* Can be dynamically used after `Check Condition` or external checks (e.g. API, duplicate check).

**When to Use:**

* Implementing custom validations (e.g., email uniqueness, license limits).
* Returning dynamic error messages to the user interface.

***

### Best Practices

* Combine **Read Form Fields** → **Save Entry** for complete form handling pipelines.
* Use **Load Query** + **For Each** for bulk data updates.
* Remember: session parameters persist across steps and allow data reuse within the same workflow.


# Parameters & Variables

Ondeva workflows use two types of runtime values to hold and pass data: **Session Parameters** and **Workflow Variables**. These are critical for making workflows dynamic, data-driven, and responsive to user inputs or external API responses.

### **Set Session Parameter**

**Purpose:**

Creates or updates key-value pairs that persist across the user’s entire session.

**Key Options:**

* **Parameter Name**: Any label (e.g., `user_id`, `submission_status`)
* **Value**: Can be static, calculated (via function editor), or fetched from previous workflow steps

**Scope & Availability:**

* Session-wide: Available in **all workflows**, **queries**, and **UI conditions**
* Reference format: `{parameters_parameterName}`

**Use Cases:**

* Store user or environment state (e.g., `{parameters_isAdmin}`)
* Control conditional UI logic (e.g., show/hide components)
* Pass session state into queries or Save Entry steps

***

### **Remove Session Parameter**

**Purpose:**

Deletes an existing session parameter.

**Key Options:**

* Choose from a list of parameters

**Use Cases:**

* Cleanup state after a critical branch completes
* Remove sensitive data from session memory

***

### **Set Variable**

**Purpose:**

Creates a local variable that exists only for the current workflow run.

**Key Options:**

* **Variable Name**: Identifier (e.g., `user_email`, `apiResponse`)
* **Value**: Set via static input or dynamic expressions (function editor)

**Scope & Availability:**

* Available only in:
  * The **current workflow**
  * Any **sub-workflows** triggered from this one
  * Any **queries** loaded within this workflow
* Reference format: `{var_variableName}`

**Use Cases:**

* Store API responses for use in the same flow
* Handle intermediate values like counters or temporary results
* Pass values into Save Entry, API, or condition checks

***

### **Create Object**

**Purpose:**

Constructs a structured object in JSON and stores it as a variable.

**Key Options:**

* **Definition**: Use the editor to build a JSON object
* **Target Variable**: Define where the object will be stored

**Use Cases:**

* Build a request payload before calling an API
* Create a multi-field object to pass into a save or update step
* Package data to hand off to a sub-workflow

***

### **How to Reference Parameters & Variables**

You can use parameters and variables **almost anywhere** in Ondeva workflows — in inputs, field mappings, conditions, and even API bodies.

#### **Syntax:**

* **Variable**: `{var_variableName}`
* **Parameter**: `{parameters_parameterName}`

#### **Where You Can Use Them:**

* **All Workflow Inputs**: Including `Save Entry`, `Call API`, `Check Condition`, `Send Email`, etc.
* **All Queries**: When loaded via workflow, queries can reference workflow variables and session parameters.
* **Design Conditions**: Visibility, enable/disable logic for UI components (parameters only).
* **Sub-Workflows**: Inherit all variables from the parent workflow.
* **Javascript code:** You can access variables and parameters when executing JavaScript code through the “Code” step of a workflow. All variables and parameters are available through the `individee.meta` object.

  ```jsx
  console.log(individee.meta.paramters['var_variableName'];
  ```

### Quick Comparison

| Feature         | Session Parameters                 | Workflow Variables                      |
| --------------- | ---------------------------------- | --------------------------------------- |
| Scope           | Global (across all workflows & UI) | Local (within current + sub workflows)  |
| Lifetime        | Until manually removed or logout   | Until workflow finishes execution       |
| Syntax          | `{parameters_someName}`            | `{var_someName}`                        |
| Use in UI Logic | ✅ (visibility/enabled conditions)  | ❌                                       |
| Use in Queries  | ✅                                  | ✅ (when triggered by workflow)          |
| Best For        | Shared session state               | Internal calculations & short-term data |

***

### Best Practices

* Use **variables** for scoped values that don’t need to persist (API result, loop index, form temp values).
* Use **session parameters** to drive cross-workflow logic and UI behavior (permissions, active user state).
* Clean up unused parameters to avoid polluting the session state.


# AI Integration

Ondeva integrates AI directly into your workflows — allowing you to generate, extract, and analyze data using Large Language Models (LLMs) without needing to wire up external services. AI becomes just another building block in your application logic, enabling personalized automation, rich content generation, and powerful classification.

All AI steps store their results in session variables or table entries, making them immediately usable in downstream logic, queries, and UI components.

### **Text to Variable**

**Purpose:**

Generates AI-powered text from a prompt and stores the result in a session variable.

**Key Options:**

* **Prompt**: The input text, question, or command given to the model (can include dynamic variables)
* **Variable**: Name of the variable to store the result

**When to Use:**

* Generate product descriptions or summaries
* Rephrase or complete user input
* Dynamically fill message templates or notification content

***

### **Image to Content Field**

**Purpose:**

Generates an image based on a prompt and saves it into a specific field in a table entry.

**Key Options:**

* **Prompt**: Describes what the AI should generate
* **Target Table, Entry ID, Field**: Where to store the resulting image

**When to Use:**

* Automatically generate hero or thumbnail images for new content
* Create profile avatars or decorative assets from user prompts

***

### **Keywords Saved as List**

**Purpose:**

Extracts keywords from a text prompt and stores them as an array of strings in a variable.

**Key Options:**

* **Prompt**: Text to analyze (e.g., a blog post or support ticket)
* **Variable**: Where the array of keywords will be saved

**When to Use:**

* Tag content for search or filtering
* Analyze sentiment topics in support logs or survey data

***

### **Text Summarization**

**Purpose:**

Condenses a long input text into a shorter, coherent summary.

**Key Options:**

* **Prompt**: The original long-form text
* **Variable**: Where the summary is stored

**When to Use:**

* Summarize meeting notes, emails, or documentation
* Offer TL;DR versions of user-generated content

***

### **Audio to Text**

**Purpose:**

Transcribes an audio file into plain text using AI.

**Key Options:**

* **Variable**: Name of the session variable holding the audio input
* **Target Table / Entry / Field**: Where to store the transcription result

**When to Use:**

* Process voice submissions (e.g., customer feedback, voice forms)
* Extract speech from uploaded interviews or podcast clips

***

### Best practices:

* AI prompts support full use of `{parameters_x}` and `{var_x}` references, allowing you to dynamically personalize inputs per user/session.
* Results can be directly used in downstream steps like `Save Entry` or `Send Mail`.
* Use **Text to Variable** before API calls or UI rendering to dynamically generate values based on live context.


# UX & Browser Control

These steps are designed to control the **user’s experience directly** — whether that means navigating between pages, triggering downloads, injecting JS, or throwing custom events inside your frontend. Together, they let you seamlessly blend logic with UI behavior.

### **Go to URL**

**Purpose:**

Redirects the user to another page — either internal (within the app) or external.

**Key Options:**

* **Internal Link**: Dropdown of your app’s defined pages
* **Custom URL**: External or dynamically built URL (can use `{parameters_}` or `{var_}` references)
* **Parameters**: Add query parameters to internal links
* **Open in New Tab**: Optional checkbox for opening internal or external links in a new tab.

**When to Use:**

* Redirect user after form submission or login
* Navigate based on user selection or logic (e.g., "Go to dashboard if logged in")
* Link into third-party tools or portals

***

### **Execute JavaScript**

**Purpose:**

Runs a block of custom JavaScript in the user’s browser.

**Key Options:**

* **Code Editor**: Paste your JS snippet
* **Timeout (ms)**: Execution timeout (prevents runaway scripts)

**When to Use:**

* Extend the possibilities of Ondeva with custom code that consumes variables and data collected via Ondeva.
* Modify client-side DOM manually
* Call browser APIs (clipboard, localStorage, etc.)

**Best Practices:**

* Keep scripts short and well-scoped. Don’t overload the client with unnecessary scripts.
* Use `try/catch` inside your script if needed
* Use the data provided by the `individee.meta` object safely. You have access to the variables and parameters `individee.meta.parameters` as well as to loaded queries `individee.meta.tables` .

***

### **Trigger Download**

**Purpose:**

Initiates a file or visual component download for the user.

**Modes Supported:**

* **Chart Snapshot**: Download an image of a chart component on the current page. Pass the markup id of the chart component.
* **Map Snapshot**: Download an image of a map on the current page. Pass the markup id of the map component.
* **File Field of Table Entry**: Downloads a file stored in a specific field in a table
* **Generated Document**: PDF or spreadsheet generated by Ondeva’s document engine

**Key Options:**

* **Component or Table Reference**: Depending on the mode
* **Filename**: Set static or dynamic file names

**When to Use:**

* Export reports or dashboards
* Let users download file attachments (e.g., invoices, submissions)
* Offer dynamic content based on data or session state

***

### **Throw Event**

**Purpose:**

Fires a custom event into Ondeva’s event system — useful for analytics, real-time responses, or syncing across components.

**Key Options:**

* **Event Name**: Unique identifier (e.g., `user_registered`, `plan_upgraded`)
* **Persist Event**: When checked, the event is stored for analysis in the performance area
* **Metadata**: Optional values like session ID, user ID, or URL context

**When to Use:**

* Custom instrumentation (track clicks, conversions, form usage)
* Fire off workflows based on frontend actions (when listening via another workflow)
* Log milestones for performance dashboards

***

### Best Practices

* **Use named events** consistently to track workflows (e.g., `invoice_paid`, `support_request_opened`)
* Always set a fallback for **Go to URL** when depending on variables (avoid broken redirects)
* Leverage **download triggers** for user-facing confirmations or exports, especially in enterprise tools


# User Flow & E-Commerce

Ondeva gives you precise control over user access, session behavior, and monetization flows. These steps are essential for any SaaS or productized app built on Ondeva — enabling authentication, license enforcement, and seamless e-commerce actions from within workflows.

### **Login**

**Purpose:**

Forces the user to authenticate. If already logged out, they’ll be redirected to the login page and returned to their current screen upon success.

**When to Use:**

* Guard protected content
* Require login before form submission
* Secure workflows that write to user-specific data

***

### **License Enforcing**

**Purpose:**

Checks whether the user has a valid license (or set of licenses). If the check fails, the user is blocked from progressing.

**Key Options:**

* **License Selection**: Choose one or more required licenses

**When to Use:**

* Gate workflows or features based on paid plan
* Handle upsells for premium components
* Limit access to internal tools or downloads

***

### **Add Item to Cart (E-Commerce)**

**Purpose:**

Adds a product or license to the current user’s shopping cart.

**Key Options:**

* **Product / License**: Select the item to be added
* **Clear Cart First**: Optional — clears the current cart before adding the new item

**When to Use:**

* Trigger a checkout flow (e.g. “Buy Now” button)
* Offer upgrade paths (add license for additional features)
* Support dynamic pricing tiers or modular subscriptions

***

### **Register Session**

**Purpose:**

Logs a session-level tracking entry with optional metadata for analysis. The Session ID is stored in a variable: `{var_sessionId}`

**Key Options:**

* **User ID** (optional)
* **Session ID** (optional)
* **URL** (context page)

**When to Use:**

* Record usage sessions for metrics
* Tie workflows to performance data
* Build your own internal analytics pipeline

***

### **Register Page View**

**Purpose:**

Tracks a page visit for the current session and user. The Visit ID is stored in a variable: `{var_visitId}`

**Fields:**

* **User ID** (optional)
* **Session ID** (optional)
* **URL** (context page)

**When to Use:**

* Funnel tracking
* Custom conversion attribution
* Heatmap or flow visualization features

***

### Best Practices

* Combine **License Enforcing** with **Design Visibility** rules for a seamless UX.
* Use **Add to Cart** in pricing tables, modals, or gated content dialogs.
* Log sessions and page views if you want to collect analytics event from other sources then the automatic tracking of Ondeva’s analytics system.


# Custom Tables


# User Interface

Ondeva’s **Custom Tables** area is split into two functional tabs — **Structure** and **Data** — both accessible from within the Data section of the platform. The UI is designed to help you move fluidly between modeling data and interacting with live entries.

This overview breaks down how the user interface works specifically when working with a table in Ondeva.

### Navigating to Custom Tables

To access your custom tables:

1. Click the **Data** icon in the left-hand navigation.
2. Select a table from the list — or create a new one.
3. Once selected, the table editor opens with two tabs:
   * **Structure**
   * **Data**

***

### Structure Tab UI

The **Structure** tab is where you define the schema (fields/columns) of your table.

#### Layout

* **Center panel**:\
  Displays the list of fields currently in the table (columns). Each field shows:
  * Field label
  * Data type
  * Identifying column indicator (if applicable)
* **Top bar**:\
  Shows the current table name. Click it to rename the table inline.
* **Right-hand panel**:\
  When a field is selected, this panel displays field-specific settings:
  * Field name
  * Data type
  * Validation rules
  * Default values
  * Required toggle
  * Custom logic (varies by field type)
* **Floating actions**:
  * **Add Field**: Button at the bottom of the field list
  * **Delete Field**: Trash icon appears when hovering over a field
* **Empty canvas click**:\
  Clicking in an empty space reveals **Table Settings.**

***

### Data Tab UI

The **Data** tab lets you view and manipulate actual entries (rows) inside the table.

#### Layout

* **Top bar**:
  * **Add Entry** button
  * **Export to CSV** button
* **Center panel (Table View)**:
  * Spreadsheet-style table with one row per entry
  * Each column matches a field from your structure
  * Checkboxes to select rows for deletion
* **Right-hand panel (Entry Editor)**:\
  When a row is selected:
  * Shows all fields and values for that row
  * Supports inline editing per field type
  * Autosaves all changes instantly
* **Pagination Navigation**:\
  Shown at the bottom once entries exceed 20 rows. Navigate pages to view more data.

***

### UI Behaviors Worth Noting

* **Autosave**:\
  Changes in both Structure and Data tabs are saved instantly — there’s no Save button.
* **Validation Feedback**:\
  Required fields and invalid entries are flagged in real time in both field settings and data entry.
* **Drag & Drop Support** (Structure Tab):
  * Reorder fields by dragging them in the list.
  * The order is reflected in Data view and UI components.
* **Persistent Context**:\
  Switching between tabs (Structure ↔ Data) retains your selected table and open row/field.

***

### Summary

Ondeva’s custom table UI is optimized for live, real-world development:

* Two powerful tabs (Structure + Data)
* Clear side-by-side editing
* No-code field config with real-time validation

Whether you're defining schemas or running operations, the interface keeps you focused and fast.


# Table Structure

In Ondeva, **tables define your application's data model**. Think of them as the backbone of your backend — every form, automation, query, or dashboard ultimately connects to data that lives here.

The **Table Structure** view is where you define fields, their types, validations, and behavior. It's also where you configure table-level settings like per-user limits or identifying columns. Ondeva ensures changes are saved instantly, so structure editing is frictionless and production-safe.

### Accessing the Table Structure

To edit a table:

* Navigate to the **Data** tab from the left sidebar.
* Select a table from the list (or create a new one).
* You'll be taken directly to the **Structure** tab — the schema editor for your table.

Here, you'll define columns, choose their types, configure field properties, and manage table-level settings.

### Table Settings

Clicking on an empty space in the **Structure** view reveals general settings for the table in the right-hand panel.

#### Available Table-Level Settings

* **Table Name**\
  Editable directly from the top title bar. The name is persisted across all references (queries, workflows, API exposure).
* **One Entry Per User**\
  When enabled, this restricts each frontend user to a single entry in the table. Ideal for profiles, preferences, or single submissions.

### Working with Fields

Each table is composed of [**fields**](/data/custom-tables/field-types-and-configuration) (columns).\
You can:

* Add fields with the "+" button
* Rename by clicking the label
* Reorder by drag-and-drop
* Remove fields via the trash icon

Fields can also be marked as:

* **Identifying Column**: This becomes the default display label across UI components, dropdowns, and table references.

{% hint style="info" %}
Note: Every structural change — adding fields, renaming columns, changing types — is **persisted immediately**. You can refresh or return later and all definitions will remain intact.
{% endhint %}

### Summary

The **Table Structure** area in Ondeva gives you full control over your data model with:

* Instant updates
* Developer-grade validations
* A wide range of input types
* Full support for relationships, geodata, and advanced field logic

Whether you're modeling a CRM, form backend, analytics dashboard, or a marketplace database, your table starts here.


# Table Data

Ondeva's **Table Data** interface lets you view, create, edit, and manage the actual records that live in your app’s backend — directly inside your browser. It’s a fast, developer-friendly interface designed for real-world teams building products, internal tools, or complex workflows.

Whether you’re running a CRM, building a marketplace, collecting form submissions, or managing operational datasets, this view gives you full control over your live application data — no SQL required.

From this screen, you can:

* Create and update entries inline
* Upload files or toggle values instantly
* Export everything to CSV
* Navigate large datasets with pagination
* Inspect every field type, exactly as it behaves in production

### Accessing the Data View

1. Open the **Data** section from the left sidebar.
2. Select a table.
3. Switch to the **Data** tab at the top of the screen.

The interface displays your data in a spreadsheet-style view — every row is an entry, and every column reflects a field from your table schema.

***

### Working with Entries

#### Editing a Row

Click any row to open its full details in the right-side editor. You’ll see all fields (columns), editable based on their data type.

Common editing behaviors:

* **Text / Number**: Type directly
* **Date**: Select from a date picker
* **Checkbox**: Toggle with one click
* **Dropdown / Multi-Select**: Choose from options
* **File**: Upload or replace files inline
* **Rich Text**: Edit via a rich input (viewed as plain text here)

Changes are automatically saved.

***

#### Creating a New Entry

Click the **“Add Entry”** button to open a blank record. Fill in fields — any default values (if configured) will be pre-filled — and your changes are saved as you go.

***

#### Deleting Entries

* Select any row
* Click the trash icon
* Confirm deletion in the dialog

{% hint style="danger" %}
**Note**: Deletes are permanent. For reversible workflows, consider adding a “status” or “archived” field instead.
{% endhint %}

***

### Pagination

Ondeva automatically paginates tables to maintain performance. Each page shows **20 entries** by default. Use the navigation controls at the bottom to move through your dataset.

***

### CSV Export

Click the **“Export to CSV”** button to download the full table contents in `.csv` format.

The export includes:

* Every field (column)
* One row per entry
* Raw values, suitable for spreadsheets, databases, or analytics tools

***

### Field Behavior in the Data Tab

| Field Type      | Data Tab Behavior               |
| --------------- | ------------------------------- |
| Text / Number   | Inline editable                 |
| Date            | Opens a calendar picker         |
| Checkbox        | Toggle on/off instantly         |
| Dropdown        | Select single value             |
| Multiple Choice | Select multiple values          |
| File            | Upload & replace                |
| File Manager    | **Not editable here** (UI-only) |
| Table Reference | Select another entry            |
| Location        | Edit address and geodata        |
| Password        | Write-only, hidden              |
| Rich Text       | Text only (no formatting)       |
| GeoJSON         | Not editable in backend UI      |

***

### Bulk Data via Workflows

Ondeva’s workflow engine lets you work with data programmatically:

* **Load Query** to retrieve matching entries
* **Save Entry** to add or update entries
* **Delete Entry**, **Duplicate Entry**, **For Each**, and more

This is especially useful for:

* Automating form submissions
* Importing files
* Syncing external systems
* Updating many rows at once

Learn more in the [**Workflows**](/workflow/introduction) chapter.

***

### Summary

The **Data view** gives you hands-on access to the heart of your application: its live records.

With fast editing, file support, and CSV export built-in, it’s perfect for:

* Testing and verifying backend behavior
* Managing operations workflows
* Editing production data with confidence

No database admin panel needed. Just click, edit, and move fast.


# Field Types & Configuration

Each field (column) in an Ondeva table defines the type of data it stores, the validation rules it follows, and how it's presented in both backend and frontend contexts.

Below is a reference of all supported field types and their configuration options.

## Shared Properties

Most field types include:

* **Field Name** (Label): Required for all fields.
* **Identifying Column** toggle: Used for display in dropdowns/reference pickers.
* **Required**: User must provide this field in forms.
* **Default Value**: Applied to new entries unless overwritten.

## Core Field Types

### **Text**

* Single-line input for strings.
* Options: default value
* Validation: regex, length, uniqueness.

### **Number**

* Integer-only numeric input.
* Options: default value
* Validation: min, max, uniqueness, regex, formula-based.

### **Float Number**

* Allows decimal numbers (e.g. 3.14, 19.99).
* Options: default value
* Same validations as Number.

### **Rich Text**

* Formatted text (HTML-friendly).
* Used for long content fields, email templates, etc.
* Same validations as Text

### **Date**

* Stores a date (with optional time).
* Options: Include time toggle, Default date picker

### **Checkbox**

* Boolean value (true/false).
* Options: Default checked state

***

## Select Field Types

### **Dropdown**

* Single select from predefined options.
* Options: Choices list, Default selection

### **Multiple Choice**

* Multi-select dropdown (returns array).
* Same options as Dropdown.

***

## File & Media Fields

### **File**

* Upload and store a single file.
* Option: Max file size, File type restrictions

### **File Manager**

* Stores multiple files (advanced component).
* No direct backend data entry (used via front-end components).
* Same options as File

***

## Reference Fields

### **Table Reference**

* Points to another table's entry (foreign key).
* Options: Default referenced entry, Restrict selectable entries

### **Page Reference**

* Stores a reference to an internal page in your app (useful for redirections).

### **Roles**

* Reference one or more roles to this entry.
* Used for permissioning or UI personalization.

***

## Location & Geo Fields

### **Location**

* Stores geolocation metadata:
  * Address
  * Latitude / Longitude
  * Region
  * Country
* Validations: action, regex, formula, unique

### **GeoJSON**

* For storing geo boundaries, polygons, zones.
* No additional config

***

## Advanced Types

### **Password**

* Write-only field, encrypted.

{% hint style="danger" %}
The content of this field is encrypted not hashed. DON'T use this field for sensitive passwords. A possible use case can be temporary tokens.
{% endhint %}

### **Business ID**

* Auto-incrementing, uneditable ID.
* Used for internal tracking or display.
* No configuration options.

***

## Field-Level Validation

Ondeva supports multiple validation types:

* **Required**\
  User must provide a value before saving.
* **Default Value**\
  Auto-fills this value on new entries.
* **Maximum / Minimum**\
  For numbers or string lengths.
* **Regex (Regular Expressions)**\
  Pattern matching for input (e.g., emails, postal codes).
* **Unique (global or per user)**\
  Ensures no duplicates in this column.
* **Formula-Based Validation**\
  Define logic expressions that must evaluate true.
* **Action-Based Validation**\
  Delegate validation to a separate workflow or script for complex checks.


# Best Practices

### **Design for Queryability**

Structure your tables to make querying easy and predictable:

* Use **identifying columns** for anything users will pick in dropdowns or reference selectors.
* Prefer **flat fields** for filterable or sortable data (e.g. status, type, created\_at).
* If you’ll be using filters in UI components or automation, keep field names short and consistent (`status`, `owner`, `is_published`).

{% hint style="info" %}
Use **Dropdown** or **Multiple Choice** fields for controlled vocabularies like categories, states, or tags.
{% endhint %}

***

### **Normalize for Relationships — But Don’t Overdo It**

Ondeva supports **table references** (like foreign keys), allowing you to link entries across tables. Use them when:

* Data is **reused** in multiple places (e.g. users, clients, roles)
* You need to enforce **consistency** across submissions or components

**But avoid excessive normalization** for operational or analytical data. For example:

* If you're tracking tasks, log entries, or user actions — and frequently need to **group, sort, or filter** by related values — it’s often better to keep those fields **in the same table**.

{% hint style="info" %}
Good rule of thumb:\
**Normalize for reusability and UI clarity.**\
**Denormalize for filtering, grouping, and performance.**
{% endhint %}

#### When to Use Table References

* “One-to-one” or “many-to-one” relationships where a dropdown picker makes UX cleaner
* Data that’s maintained separately (e.g. Teams, Plans, Categories)

#### When to Flatten into the Same Table

* Metrics, submissions, or logs you’ll run analytics on
* Dynamic data where query speed matters more than data purity

{% hint style="warning" %}
Avoid deep reference chains — they create overhead and slow down performance in large apps.
{% endhint %}

***

### **Use ‘One Entry Per User’ for Personal Data**

For profile-like data (user preferences, application forms, onboarding data), enable the **One Entry Per User** setting:

* Prevents duplicate submissions
* Simplifies queries and access control
* Automatically ties data to the logged-in user

{% hint style="info" %}
Ideal for forms like “My Account”, “Startup Registration”, “Grant Application”, etc.
{% endhint %}

***

### **Model State Transitions Explicitly**

Use fields like `status`, `phase`, or `is_active` to represent the state of your entries. These fields allow:

* Workflows to branch based on state
* UI to show dynamic labels or badges
* Queries to filter logically (e.g. “only active”, “only pending approval”)

{% hint style="info" %}
Combine with [**Workflow steps**](/workflow/steps-reference) that update these fields in automation flows.
{% endhint %}

***

### **Use Default Values to Streamline Entry Creation**

For operational tables (e.g. task tracking, logs, form submissions), set defaults to:

* Reduce user input friction
* Ensure consistency across manual and automated inserts
* Prevent missing or inconsistent data downstream

Example: Set default `status = pending`, `priority = normal`, or `country = DE`.

***

### **Validate Where It Matters**

Field-level validation prevents fragile downstream logic. Use:

* **Required** fields to avoid nulls
* **Regex** to ensure structure (e.g. emails, phone numbers)
* **Unique per user** for IDs, usernames, emails
* **Formula validations** for business rules (e.g. start\_date < end\_date)

{% hint style="info" %}
Don’t over-validate early. Start with must-haves, then layer in business logic over time.
{% endhint %}

***

### **Avoid Complex JSON in Text Fields**

Ondeva supports complex logic — but don’t overuse `Text` fields to store structured blobs. Instead:

* Use **rich text** for formatted content
* Use **JSON-compatible** structures only when paired with processing logic in workflows

{% hint style="info" %}
If you need to store complex objects, consider breaking them into related tables or use [`Create Object`](/workflow/steps-reference/parameters-and-variables#create-object) + [`Save Entry`](/workflow/steps-reference/data#save-entry) via workflows.
{% endhint %}

***

### **Tag and Track Metadata When Needed**

For audit trails or analytics, add fields like:

* `created_at` (date)
* `created_by` (user reference)
* `last_updated` (date)
* `is_deleted` (soft delete flag)

These can power:

* Admin interfaces
* Time-based automations
* Conditional access to data

***

### Summary

Strong data modeling leads to strong apps. When building with Ondeva:

* Keep schemas clean, normalized, and queryable
* Use built-in settings to simplify access control and validation
* Combine structured tables with workflows to build powerful, self-sustaining systems

**Tables aren’t just storage — they’re the living logic of your app.**


