---
title: "Block Templates, Combinations That Work · RUAL Documentation"
description: "Copyable block combinations for everyday use cases: API endpoints, forms, validation, file uploads, and email sending."
canonical: https://docs.rual.nl/block-types/block-templates
language: en
---

# Block Templates: Combinations That Work

Copyable block combinations for everyday use cases: API endpoints, forms, validation, file uploads, and email. Wire them once, reuse the shape forever.

Most flows are variations on a handful of proven shapes. These templates give you the exact blocks, in order, with their connections: grab them onto your canvas and adjust the details. Every block type below exists in the current block library; search its name in the editor to add it. For broader recipes with notes and pitfalls. See [Common Blueprint Patterns](https://docs.rual.nl/blueprints/common-patterns).

### 1. API Endpoint

The universal shape of every custom API: trigger, work, reply.

| Block | Purpose | Connects to |
| --- | --- | --- |
| [`on_startup_register_uri_get`](https://docs.rual.nl/block-types/api/on_startup_register_uri_get) | Registers `GET /api/v1/ ` and fires per request. | `function` → trigger's function handler |
| [`trigger_custom_function`](https://docs.rual.nl/block-types/globals/trigger_custom_function) | The handler function entry point. | `flow` → your work blocks |
| [`httpconnection_current_request`](https://docs.rual.nl/block-types/http%20connection/httpconnection_current_request) | The live request connection object. | `connection` → every request/response block that needs it |
| Work blocks (e.g. `function_search`, [`object_new_fields`](https://docs.rual.nl/block-types/object/object_new_fields)) | Read/write data, build the payload. | flow chain; data pins as needed |
| [`httpconnection_set_json`](https://docs.rual.nl/block-types/json/httpconnection_set_json) | Replies with JSON to the caller. | `flow` (end of chain), `connection`, `code` ← `number_default` (200/400/401), `data` ← your payload |

Variants: swap the trigger for [`on_startup_register_uri_post`](https://docs.rual.nl/block-types/http%20connection/on_startup_register_uri_post) (body in, e.g. webhooks), add a `branch` for validation splits, or a second [`httpconnection_set_json`](https://docs.rual.nl/block-types/json/httpconnection_set_json) on the error path. Full walkthrough: [Build Your First API](https://docs.rual.nl/cluster/api-quickstart).

### 2. Form Handling

Collect input on a page and write it to storage on submit.

| Block | Purpose | Connects to |
| --- | --- | --- |
| `state_form` | The form container element. | renders on the page; receives child elements on `content` |
| [`state_input_dynamic`](https://docs.rual.nl/block-types/state%20ui/state_input_dynamic) | A typed input field (text, number, date, etc.). | `state` → form `content` |
| `state_button` | The submit button with a click event. | `state` → form `content`; click triggers the submit flow |
| [`state_form_get`](https://docs.rual.nl/block-types/state%20ui/state_form_get) | Reads the submitted form (`form-object` with all field values, `form-error` on failure). | first block of the submit flow |
| [`mutations_set_bp_field_multiple`](https://docs.rual.nl/block-types/mutations/mutations_set_bp_field_multiple) | Maps form values to document fields. | `mutations` → create/update block |
| [`function_create_document_from_mutations`](https://docs.rual.nl/block-types/storage/function_create_document_from_mutations) | Writes the document. | `flow` ← submit flow, `storage` ← `storage` block |

Step-by-step with screenshots: [Build Your First CRUD App](https://docs.rual.nl/getting-started/first-crud-app).

### 3. Data Validation

Reject bad input before it reaches storage or an external API.

| Block | Purpose | Connects to |
| --- | --- | --- |
| [`condition_not_empty_value`](https://docs.rual.nl/block-types/condition/condition_not_empty_value) | `true` when the checked field is filled. | one per required field, fed from `form-object` or request params |
| `branch` | Splits the flow on a condition into `true`/`false` paths. | `condition` ← the validation blocks |
| [`httpconnection_set_json`](https://docs.rual.nl/block-types/json/httpconnection_set_json) (API) or a UI message (pages) | The rejection: 400 with an error object, or inline form feedback. | `false` path; `true` path continues to the save/work flow |

Keep one condition block per field. The user learns exactly which field failed, instead of "something was wrong".

### 4. File Uploads

Accept files through an API and store them as cluster assets.

| Block | Purpose | Connects to |
| --- | --- | --- |
| [`on_startup_register_uri_post`](https://docs.rual.nl/block-types/http%20connection/on_startup_register_uri_post) | Receives the upload request (multipart body). | function handler |
| Files-group blocks (search `file` in the block library) | Read the uploaded file, its name/type/size. | fed by the request body |
| [`file_from_assets`](https://docs.rual.nl/block-types/files/file_from_assets) | Reads a file from cluster assets (`/public/...` or `/system_assets/...`). | `asset path` ← value; out `file`, `size`, `success` |
| Asset upload API (`POST /api/v1/_system/assets/stream`) | Stores the file into `public` or `system_assets`. | alternative to a custom flow: often enough on its own |

Everything about asset paths, public vs private, and the upload APIs: [Assets](https://docs.rual.nl/blueprints/assets).

### 5. Email Sending

Send transactional email through Postmark, driven by a flow.

| Block | Purpose | Connects to |
| --- | --- | --- |
| Any trigger (form submit, `storage_event`, [`schedule_repeating_event`](https://docs.rual.nl/block-types/events/schedule_repeating_event)) | Decides when an email goes out. | start of the flow |
| Data blocks (search/get) | Collect recipient and content (user profile, order, template values). | value pins into the email fields |
| Postmark send blocks (search `postmark` in the block library) | Send the message via the cluster's Postmark token. | to/subject/body from your data; token from `postmark_token` system setting |
| [`function_console_log`](https://docs.rual.nl/block-types/logging/function_console_log) | Record success/failure while developing. | `message` ← send result or `error` pin |

Prerequisite: `postmark_token` (secure) and `email_default_from` must be set. See [Email configuration](https://docs.rual.nl/blueprints/system-settings-reference#email-setup). For heavy or batched mail, defer to the [queue](https://docs.rual.nl/blueprints/queue) instead of sending inline.

### 6. Template or From Scratch?

- **Use a template shape** when the job is a known pattern: endpoint, form write, validation, upload, notify. It saves wiring and keeps conventions uniform across your cluster.

- **Go from scratch** when the data model or the flow is genuinely yours: unusual branching, multi-storage orchestration, custom UI state. Start from the closest template and prune rather than starting empty.

- **Extract to a function** once you paste the same three blocks twice. See [Blueprint Best Practices](https://docs.rual.nl/blueprints/best-practices).

### Next Steps
