diff --git a/content/nginx-one-console/nginx-configs/config-templates/add-multiple-services.md b/content/nginx-one-console/nginx-configs/config-templates/add-multiple-services.md index 061844ae1..b86dedc02 100644 --- a/content/nginx-one-console/nginx-configs/config-templates/add-multiple-services.md +++ b/content/nginx-one-console/nginx-configs/config-templates/add-multiple-services.md @@ -11,7 +11,7 @@ weight: 400 This guide shows how to extend a working submission from the [Submit Templates Guide]({{< ref "submit-templates.md" >}}) by adding server augments for new services with dedicated location augments. -{{< call-out "note" "Note" >}}Because you can’t retrieve previous submissions, you must include the full request with any updates.{{< /call-out >}} +{{< call-out "note" "Note" >}}Submissions are persistent objects. Use the [Get a submission]({{< ref "submit-templates.md#get-a-submission" >}}) operation to retrieve the stored values from a previous submission before building an update.{{< /call-out >}} ## Import template diff --git a/content/nginx-one-console/nginx-configs/config-templates/author-templates.md b/content/nginx-one-console/nginx-configs/config-templates/author-templates.md index 2acd57e3f..e5b916e08 100644 --- a/content/nginx-one-console/nginx-configs/config-templates/author-templates.md +++ b/content/nginx-one-console/nginx-configs/config-templates/author-templates.md @@ -23,7 +23,7 @@ This guide explains how to write NGINX configuration templates for NGINX One Con | **Context Path** | A path notation representing the hierarchical structure of NGINX configuration blocks (e.g., `http`, `http/server`, `http/server/location`). Used to specify where augments can be inserted in base templates via `augment_includes` and where augments target during submission via `target_context`. | | **Extension Point** | A placeholder in a template using `{{ augment_includes "context_path" . }}` that marks where augment content can be inserted during rendering. Base templates use extension points to enable modular composition with augments. | | **Schema** | A JSON Schema Draft 7 file (YAML or JSON format) that defines template variables, their types, descriptions, and validation rules. Required for templates that use variables. Schema properties become available as template variables via dot notation. | -| **Template Submission** | The process of composing base and augment templates with values to render a complete NGINX configuration. Submissions are currently preview-only and generate rendered configurations that can be saved as Staged Configs. | +| **Template Submission** | The process of composing base and augment templates with values to render and deploy a complete NGINX configuration. Submissions are persistent objects that can be retrieved, updated, and deleted. A submission targets one or more existing staged configs, Config Sync Groups, or instances, and automatically re-publishes when updated. | | **Template Variable** | A placeholder in a template (e.g., `{{ .backend_url }}`) that gets replaced with user-provided values during rendering. All variables must be defined in the template's schema and provided during submission if marked as required. | {{}} @@ -80,6 +80,73 @@ add_header 'Access-Control-Allow-Origin' '*' always; add_header 'Access-Control-Allow-Methods' 'GET, POST' always; ``` +### Static include files + +Templates can bundle static, non-templated files that are deployed alongside the rendered NGINX configuration. These are declared with `file_type: include` and are referenced from within the template using a standard NGINX `include` directive. + +**When to use include files:** + +- Bundling `mime.types` or other standard NGINX data files that the template requires +- Shipping shared configuration snippets (for example, TLS cipher lists, proxy header sets) as separate files that are included into the rendered output +- Any file that should be deployed to the NGINX host as-is, without Go template processing + +**How include files work:** + +When a submission is rendered, include files are written to the same directory as the rendered base configuration (derived from `conf_path`). The template references them using a relative or absolute `include` path matching the deployed filename. + +**Example:** + +`reverse-proxy.tmpl` (references an include file): +```nginx +user nginx; +worker_processes auto; + +http { + include mime.types; + + server { + listen {{ .listen_port }}; + proxy_pass {{ .backend_url }}; + } +} +``` + +`mime.types` (the bundled static file): +```nginx +types { + text/html html htm; + text/css css; + # ... +} +``` + +When importing using the API, declare the include file alongside the template file: + +```json +{ + "name": "reverse-proxy", + "type": "base", + "items": [ + { + "name": "reverse-proxy.tmpl", + "file_type": "template", + "file_format": "plain", + "mime_type": "text/plain", + "contents": "..." + }, + { + "name": "mime.types", + "file_type": "include", + "file_format": "plain", + "mime_type": "text/plain", + "contents": "types {\n text/html html;\n}" + } + ] +} +``` + +When using the import archive (`.tar.gz`), include files are placed at the root of the archive alongside the `.tmpl` and schema files. See [Import templates]({{< ref "import-templates.md" >}}) for archive structure details. + ### Type declaration during import When [Importing]({{< ref "import-templates.md#ready-to-import" >}}) templates, you must explicitly declare the type. @@ -678,11 +745,78 @@ additionalProperties: false ## Template Limitations - Template files must use the `.tmpl` file extension -- Templates cannot reference external files - all configuration must be contained within the template content -- External file references (such as `include /etc/nginx/mime.types`) are not supported +- Static files that a template references via NGINX `include` directives must be bundled with the template as `file_type: include` files. See [Static include files](#static-include-files) for details. + +## Template lifecycle management + +After a template has been imported, several API operations are available to manage its metadata and create copies. + +### Update template metadata + +Use the [Update template metadata]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/updateTemplateMetadata" >}}) API operation (`PUT /templates/{templateObjectID}`) to replace all metadata on the latest template version. The `name` field is required; `description` and `state` are optional. + +**Example request body:** + +```json +{ + "name": "reverse-proxy-v2", + "description": "Updated reverse proxy configuration", + "state": "final" +} +``` + +### Partially update template metadata + +Use the [Patch template metadata]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/patchTemplateMetadata" >}}) API operation (`PATCH /templates/{templateObjectID}`) to update only the fields provided. Omitted fields retain their existing values. + +**Example — promote a draft version to final:** + +```json +{ + "state": "final" +} +``` + +{{< call-out "caution" >}} +Promoting a template version from `draft` to `final` is **irreversible**. A `final` version cannot be edited. Any subsequent content changes (via [Create a new template version]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/createTemplateVersion" >}})) will create a new draft version rather than modifying the finalized one. +{{< /call-out >}} + +### Copy a template + +Use the [Copy a Template]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/copyTemplate" >}}) API operation (`POST /templates/{templateObjectID}/copy`) to create a new template from the latest version of an existing template. + +The new template starts at version 1 in `draft` state. All files, the template type, and context configuration are copied from the source template. The `name` and `description` fields are optional — if omitted, the values are inherited from the source template. + +**Example request body:** + +```json +{ + "name": "reverse-proxy-copy", + "description": "Variant of the reverse proxy template" +} +``` + +**Example response (201 Created):** + +```json +{ + "object_id": "tmpl_-xeR3F2TQGm18jnl7bpaAw", + "latest_template_version_object_id": "tmplv_-xeR3F2TQGm18jnl7bpaAw", + "version": 1, + "latest_version": 1, + "state": "draft", + "name": "reverse-proxy-copy", + "description": "Variant of the reverse proxy template", + "type": "base" +} +``` + +This is useful for creating variations of a production template without modifying the original, or for experimenting with changes before promoting a new version. ## See also - [Import Templates]({{< ref "import-templates.md" >}}) +- [View template details]({{< ref "template-detail-view.md" >}}) +- [View template versions]({{< ref "template-versions.md" >}}) - [Submit Templates Guide]({{< ref "submit-templates.md" >}}) diff --git a/content/nginx-one-console/nginx-configs/config-templates/import-templates.md b/content/nginx-one-console/nginx-configs/config-templates/import-templates.md index bdf6ed9ba..214fd29ab 100644 --- a/content/nginx-one-console/nginx-configs/config-templates/import-templates.md +++ b/content/nginx-one-console/nginx-configs/config-templates/import-templates.md @@ -37,13 +37,14 @@ Each template archive must contain: - **Exactly one `.tmpl` file** (required) - contains your NGINX configuration template - **One `schema.yaml` or `schema.json` file** (optional) - required only if your template uses variables. For more information, see [Schema Definitions]({{< ref "author-templates.md#schema-definitions" >}}) -- **No other files** - additional files will be ignored or cause import failure +- **Static include files** (optional) - additional files referenced by NGINX `include` directives within the template. Any file extension is valid (`.conf`, `.types`, etc.). See [Static include files]({{< ref "author-templates.md#static-include-files" >}}) for details. ```text .tar.gz │ ├── .tmpl -└── .yaml +├── .yaml # optional +└── .conf # optional, one or more include files ``` ### Naming conventions @@ -170,6 +171,7 @@ ls -la /tmp/verify-archive/ ``` text reverse-proxy.tmpl schema.yaml +mime.types # only if template references include files ``` ### Complete example workflow @@ -268,7 +270,7 @@ ls -la *.tar.gz ### Tips -1. **Do not create nested directories in archives** + 1. **Do not create nested directories in archives** ```bash # Avoid - nested directory structure is not supported tar -czf template.tar.gz template-dir/ @@ -282,8 +284,8 @@ ls -la *.tar.gz # Avoid - hidden files, backups or other file extensions will be ignored tar -czf template.tar.gz *~ .* *.bak *.tmpl schema.yaml - # Correct - only include required files - tar -czf template.tar.gz *.tmpl schema.yaml + # Correct - only include required files and any desired static content files + tar -czf template.tar.gz *.tmpl schema.yaml *.conf *.types ``` 3. **Include a schema for templates with variables** @@ -294,6 +296,11 @@ ls -la *.tar.gz - Each archive must contain exactly one `.tmpl` file - Create separate archives for related templates +5. **Include files referenced by `include` directives** + - If your template uses a standard NGINX `include` directive to reference a static file (for example, `include mime.types;`), that file must be present in the archive. + - Include files are placed at the root of the archive alongside the `.tmpl` and schema files. + - Any file extension is valid (`.conf`, `.types`, etc.). + ### Ready to import After creating the archives, import them using the [Import a template API]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/importTemplate" >}}) operation. diff --git a/content/nginx-one-console/nginx-configs/config-templates/save-as-staged-config.md b/content/nginx-one-console/nginx-configs/config-templates/save-as-staged-config.md index 0267276a2..a59b46fa6 100644 --- a/content/nginx-one-console/nginx-configs/config-templates/save-as-staged-config.md +++ b/content/nginx-one-console/nginx-configs/config-templates/save-as-staged-config.md @@ -9,43 +9,195 @@ weight: 300 # Overview -This guide explains how to save a [Submission]({{< ref "submit-templates.md#make-the-request" >}}) response as a new [Staged Config]({{< ref "/nginx-one-console/nginx-configs/staged-configs" >}}). +This guide explains how to save a rendered NGINX configuration as a [Staged Config]({{< ref "/nginx-one-console/nginx-configs/staged-configs" >}}) using the Templates API. -# How to save +There are two approaches: -The workflow involves two main steps: +- **[Direct submission](#direct-submission-recommended)** (recommended) — Submit templates with `preview_only=false` (the default). The API renders the configuration and automatically creates or updates a staged config in a single step. A persistent submission object is created to track the composition and allow future updates. +- **[Preview then save](#preview-then-save-alternative)** (alternative) — Submit templates with `preview_only=true` to get the rendered configuration for review, then manually call the staged config API to save it. No submission object is created. -1. **Submit templates for preview** - Use the [Submit Templates Guide]({{< ref "submit-templates.md" >}}) to render configuration -2. **Save as staged config** - Create a staged configuration object from the preview +Use the direct submission approach unless you specifically need to inspect or modify the rendered output before saving. -## Step 1: Submit templates for preview +## Direct submission (recommended) -First, use the [Submit templates]({{< ref "submit-templates.md#make-the-request" >}}) API operation to preview the configuration. +The direct approach renders the configuration and creates or updates the staged config in one API call, and stores a persistent submission that can be retrieved and re-used. -## Step 2: Save as staged configuration +### Create a new staged config + +Use the [Submit Templates]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/submitTemplates" >}}) API operation with `preview_only=false` (or omit the parameter — `false` is the default). Omit `target_object_ids` from the request body to create a new staged config automatically. + +**Required fields:** + +- `conf_path` - The absolute path for the NGINX configuration file +- `base_template` - The base template version and input values +- `augments` - Ordered list of augment templates (can be empty) +- `description` - A description for the submission + +**Example request body:** + +```json +{ + "conf_path": "/etc/nginx/nginx.conf", + "description": "API Gateway reverse proxy", + "base_template": { + "object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", + "values": { + "backend_url": "http://api-service:8080" + } + }, + "augments": [ + { + "object_id": "tmplv_AFVNBQcoRDeV9jk9panxbw", + "target_context": "http/server/location", + "values": { + "cors_allowed_origins": "https://app.example.com", + "cors_allowed_methods": "GET, POST, PUT, DELETE, OPTIONS" + } + } + ] +} +``` + +**Successful response (202 Accepted):** + +```json +{ + "object_id": "tmplsm_frBobKIAQ_21grAwV83VYz", + "target_results": [ + { + "staged_config_status": { + "status": "succeeded" + }, + "target_object_id": "sc_cEoiYCVJRuekVpYOvV1raA" + } + ] +} +``` + +The `object_id` (`tmplsm_...`) is your **submission ID**. Save this value to retrieve, update, or delete the submission in the future. The `target_object_id` is the ID of the newly created staged config. + +### Update an existing staged config + +Include `target_object_ids` in the request body with the ID of an existing staged config. The API renders and publishes the configuration to that target. + +```json +{ + "conf_path": "/etc/nginx/nginx.conf", + "description": "API Gateway - updated backend", + "base_template": { + "object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", + "values": { + "backend_url": "http://api-service-v2:8080" + } + }, + "augments": [], + "target_object_ids": ["sc_cEoiYCVJRuekVpYOvV1raA"] +} +``` + +### Update a saved submission + +Once a submission exists, use the [Update a Template Submission]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/updateTemplateSubmission" >}}) or [Update a single template's values]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/updateSingleTemplateSubmission" >}}) operations to re-render and re-publish to the same target(s) without specifying the target again. See [Manage template submissions]({{< ref "submit-templates.md#manage-template-submissions" >}}) for details. + +## Preview then save (alternative) + +Use this approach when you need to review or modify the rendered NGINX configuration before committing it as a staged config. This two-step workflow does not create a persistent submission object. {{< call-out "tip" >}} You can save an NGINX configuration preview as a staged config, even if it contains parse errors. {{< /call-out >}} -Use the `config` object from the API response in step 1 to create a staged configuration. +### Step 1: Submit templates for preview -### Make the request +Use the [Submit Templates]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/submitTemplates" >}}) API operation with `?preview_only=true`. This renders the full configuration and returns it in the response without creating any submission or publishing to any target. -Use the [Create a staged config]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/createStagedConfig" >}}) API operation. +**Example request URL:** `POST /api/v1/namespaces/{namespace}/templates/submissions?preview_only=true` -### Request body +**Example request body:** -Take the entire `config` object from the template submission response and wrap it in a `name` field. +```json +{ + "conf_path": "/etc/nginx/nginx.conf", + "base_template": { + "object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", + "values": { + "backend_url": "http://api-service:8080" + } + }, + "augments": [ + { + "object_id": "tmplv_AFVNBQcoRDeV9jk9panxbw", + "target_context": "http/server/location", + "values": { + "cors_allowed_origins": "https://app.example.com", + "cors_allowed_methods": "GET, POST, PUT, DELETE, OPTIONS" + } + } + ] +} +``` + +**Example preview response (200 OK):** + +```json +{ + "config": { + "aux": [], + "conf_path": "/etc/nginx/nginx.conf", + "config_version": "17qlLiPmAqIWhhYxmVieE9mC5t92e+/7gIvz0GFRj/E=", + "configs": [ + { + "name": "/etc/nginx", + "files": [ + { + "name": "nginx.conf", + "contents": "", + "mtime": "0001-01-01T00:00:00Z", + "size": 371 + } + ] + }, + { + "name": "/etc/nginx/conf.d/augments", + "files": [ + { + "name": "cors-headers.tmpl.4aaf36d4a643.conf", + "contents": "", + "mtime": "0001-01-01T00:00:00Z", + "size": 159 + }, + { + "name": "health-check.tmpl.78346de4dae4.conf", + "contents": "", + "mtime": "0001-01-01T00:00:00Z", + "size": 109 + } + ] + } + ] + }, + "errors": null +} +``` + +Review the rendered configuration. If you see parse errors in the `errors` array, refer to [Template Limitations]({{< ref "author-templates.md#template-limitations" >}}) for guidance. + +### Step 2: Save as staged configuration + +Use the `config` object from the preview response to create a staged configuration. + +Use the [Create a staged config]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/createStagedConfig" >}}) API operation. + +Take the entire `config` object from the preview response and wrap it with a `name` field. **Required fields:** - `name` - Descriptive name for the staged configuration -- `config` - The complete `config` object from the template submission response +- `config` - The complete `config` object from the preview response **Optional fields:** - `description` - Details about the configuration purpose or changes -Here's an example of what you need to include with the API request: +**Example request body:** ```json { @@ -89,8 +241,6 @@ Here's an example of what you need to include with the API request: } ``` -### Response format - **Successful response (201 Created):** ```json @@ -104,5 +254,3 @@ Here's an example of what you need to include with the API request: - [Submit Templates Guide]({{< ref "submit-templates.md" >}}) - [Staged Configs]({{< ref "/nginx-one-console/nginx-configs/staged-configs" >}}) - - diff --git a/content/nginx-one-console/nginx-configs/config-templates/submit-templates.md b/content/nginx-one-console/nginx-configs/config-templates/submit-templates.md index 71da228b1..2d98eb508 100644 --- a/content/nginx-one-console/nginx-configs/config-templates/submit-templates.md +++ b/content/nginx-one-console/nginx-configs/config-templates/submit-templates.md @@ -6,32 +6,26 @@ toc: true weight: 200 --- -# Template submission and preview guide +# Template submission guide -This guide explains how to submit templates for rendering NGINX configurations and preview the results using the Templates API. +This guide explains how to submit templates to render and deploy NGINX configurations, and how to manage existing submissions using the Templates API. -Before submitting templates for preview, you need to import templates into NGINX One Console. +Before submitting templates, you need to import them into NGINX One Console. -- See the [Import Templates Guide]({{< ref "import-templates.md" >}}) for instructions on creating templates. +- See the [Import Templates Guide]({{< ref "import-templates.md" >}}) for instructions on creating and importing templates. - For guidance on writing templates, see the [Template Authoring Guide]({{< ref "author-templates.md" >}}). ## Overview -Template submission allows you to compose templates that generate complete NGINX configuration. The process involves: +Template submission allows you to compose templates that generate a complete NGINX configuration and deploy it to a target. The process involves: 1. **Discovering templates** - Find base and augment templates that match your infrastructure needs 1. **Understanding capabilities** - Review what contexts and features the base template supports 1. **Selecting augments** - Choose augments for additional features (CORS, rate limiting, SSL, etc.) 1. **Providing values** - Supply values for all template variables -1. **Preview and validate** - Generate and review the complete NGINX configuration -1. **Save as staged config** - Use NGINX One Console to save the preview as a staged configuration for deployment +1. **Submit** - Submit the composed request to render the NGINX configuration and create a staged config -## Current limitations - -- **Preview only:** Template submission currently only supports preview mode (`preview_only=true`) -- **No submission persistence:** Submissions are not saved as objects (planned for future release) -- **Manual staged config creation:** After preview, use the NGINX One Console to manually save the rendered configuration as a staged config for deployment to instances or Config Sync Groups -- **Static includes:** Templates cannot include external static files (planned for future release) +To review the rendered configuration before committing, use [preview mode](#preview-mode-preview_onlytrue) with `preview_only=true`. See [Save rendered config as staged config]({{< ref "save-as-staged-config.md" >}}) for the preview-first workflow. ## Template discovery @@ -76,7 +70,7 @@ Use the [List Templates]({{< ref "/nginx-one-console/api/api-reference-guide/#op "http/server", "http/server/location" ], - "created_at": "2025-09-25T19:20:47.473935Z", + "created_at": "2025-09-25T19:20:47.473955Z", "description": "", "name": "reverse-proxy-base", "object_id": "tmpl_0rQSkSNSTamthLQVtSZb1g", @@ -101,6 +95,7 @@ Use the [List Templates]({{< ref "/nginx-one-console/api/api-reference-guide/#op - **type** - Identifies base templates (use exactly one) vs augment templates (use zero or more) - **allowed_in_contexts** - Shows where augment templates can be applied within a base template - **augment_includes** - Shows which contexts the base template supports for augments +- **is_f5_default** - When `true`, the template is provided by F5 and is immutable. These templates are also identified in the NGINX One Console by the F5 logo icon in the templates list. The API response contains all information needed for creating a submission to render NGINX configurations. You need template details **only** if you want to examine the actual template content or variable requirements. @@ -125,12 +120,12 @@ Use the [Retrieve a Template]({{< ref "/nginx-one-console/api/api-reference-guid "http/server", "http/server/location" ], - "created_at": "2025-09-25T19:20:47.473935Z", + "created_at": "2025-09-25T19:20:47.473955Z", "description": "", "items": [ { "contents": "user nginx;\nworker_processes auto;\n\nhttp {\n {{ augment_includes \"http\" . }}\n \n server {\n listen 80;\n server_name _;\n\n {{ augment_includes \"http/server\" . }}\n \n location / {\n proxy_pass {{ .backend_url }};\n {{ augment_includes \"http/server/location\" . }}\n }\n }\n}\n", - "ctime": "2025-09-25T19:20:47.473935Z", + "ctime": "2025-09-25T19:20:47.473955Z", "file_format": "FILE_FORMAT_PLAIN", "file_type": "FILE_TYPE_TEMPLATE", "mime_type": "FILE_MIME_TYPE_TEXT", @@ -139,7 +134,7 @@ Use the [Retrieve a Template]({{< ref "/nginx-one-console/api/api-reference-guid }, { "contents": "$schema: \"http://json-schema.org/draft-07/schema#\"\ntype: object\nproperties:\n backend_url:\n type: string\n description: \"Backend server URL\"\nrequired:\n - backend_url\nadditionalProperties: false\n", - "ctime": "2025-09-25T19:20:47.473935Z", + "ctime": "2025-09-25T19:20:47.473955Z", "file_format": "FILE_FORMAT_PLAIN", "file_type": "FILE_TYPE_SCHEMA", "mime_type": "FILE_MIME_TYPE_YAML", @@ -161,17 +156,20 @@ Use the [Retrieve a Template]({{< ref "/nginx-one-console/api/api-reference-guid ## API endpoint -Use the [Submit templates for previewing NGINX configuration]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/submitTemplates" >}}) API operation to render and preview NGINX configurations from templates. - -## Request structure +Use the [Submit templates for previewing NGINX configuration]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/submitTemplates" >}}) API operation to render NGINX configurations from templates. -The following sections describe what you need for the request: +The `preview_only` query parameter controls the mode: -### Required parameters +{{}} +| `preview_only` | Behavior | Response | +|---|---|---| +| `false` (default) | Renders the configuration, creates a persistent submission, and publishes to the target(s). | `202 Accepted` with submission `object_id` and target results. | +| `true` | Renders the configuration for inspection **without** creating a submission or publishing. | `200 OK` with the rendered NGINX configuration. | +{{}} -**Query Parameter:** +## Request structure -- `preview_only=true` - Currently the only supported mode. Renders configuration for preview without creating a submission object. +The following sections describe what you need for the request. ### Configuration path (`conf_path`) @@ -200,12 +198,12 @@ Where `base_dir` is derived from `conf_path`: **Base Template:** -- `object_id` - Template unique identifier (use a template where `type` is `base`) +- `object_id` - Template version unique identifier (`tmplv_...`) for the version to use - `values` - Key-value pairs for template variables **Augment Templates:** -- `object_id` - Template unique identifier (use a template where `type` is `augment`) +- `object_id` - Template version unique identifier (`tmplv_...`) - `target_context` - NGINX context where the augment should be applied - `values` - Key-value pairs for template variables (optional if template has no variables) - `child_augments` - Optional nested augments that render within this augment's output @@ -231,9 +229,103 @@ See the [Template Authoring Guide]({{< ref "author-templates.md#config-templates For more information, see [Understanding Rendering Order](#understanding-rendering-order). -## Make the request +## Submission mode (default) + +Use the [Submit Templates]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/submitTemplates" >}}) API operation without `preview_only=true` (or explicitly with `preview_only=false`) to render and persist a submission. + +{{< call-out "note" >}} +**Current limitation:** Submission targets are currently limited to staged configurations. Targeting Config Sync Groups or instances directly is not yet supported. +{{< /call-out >}} + +### Create a new staged config + +Omit `target_object_ids` from the request body. The API renders the configuration and automatically creates a new staged config. + +**Required fields:** + +- `conf_path` - Configuration file path +- `base_template` - Base template version and values +- `augments` - Ordered list of augment templates (can be empty) +- `description` - A description for the submission (required in submission mode) + +**Request body:** + +```json +{ + "conf_path": "/etc/nginx/nginx.conf", + "description": "Reverse proxy with rate limiting", + "base_template": { + "object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", + "values": { + "backend_url": "http://example.com:8080" + } + }, + "augments": [ + { + "object_id": "tmplv_-abR3F2TQGm18jnl7bpaXw", + "target_context": "http", + "values": { + "zone_name": "req_limit", + "memory": "10m", + "rate": "10r/s" + } + } + ] +} +``` -Use the [Submit Templates]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/submitTemplates" >}}) API operation with your composed request and the required `preview_only=true` parameter. +**Successful response (202 Accepted):** + +```json +{ + "object_id": "tmplsm_frBobKIAQ_21grAwV83VYz", + "target_results": [ + { + "staged_config_status": { + "status": "succeeded" + }, + "target_object_id": "sc_cEoiYCVJRuekVpYOvV1raA" + } + ] +} +``` + +The `object_id` in the response is your **submission ID** (`tmplsm_...`). Save this value — it is used to retrieve, update, or delete the submission later. The `target_object_id` is the newly created staged config. + +### Update an existing staged config + +Include `target_object_ids` in the request body with the ID of an existing staged config. The API renders the configuration and publishes it to the specified target. + +**Request body:** + +```json +{ + "conf_path": "/etc/nginx/nginx.conf", + "description": "Reverse proxy with rate limiting - updated", + "base_template": { + "object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", + "values": { + "backend_url": "http://example.com:8080" + } + }, + "augments": [ + { + "object_id": "tmplv_-abR3F2TQGm18jnl7bpaXw", + "target_context": "http", + "values": { + "zone_name": "req_limit", + "memory": "10m", + "rate": "10r/s" + } + } + ], + "target_object_ids": ["sc_cEoiYCVJRuekVpYOvV1raA"] +} +``` + +## Preview mode (`preview_only=true`) + +Add `?preview_only=true` to the request URL to render the configuration for inspection without creating a submission or publishing to any target. This is useful for validating your template values before committing. ### Request body @@ -243,14 +335,14 @@ Here's an example of what you need to include with the API request: { "conf_path": "/etc/nginx/nginx.conf", "base_template": { - "object_id": "", + "object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", "values": { "backend_url": "http://example.com:8080" } }, "augments": [ { - "object_id": "", + "object_id": "tmplv_AFVNBQcoRDeV9jk9panxbw", "target_context": "http/server/location", "values": { "cors_allowed_origins": "https://app.example.com", @@ -258,7 +350,7 @@ Here's an example of what you need to include with the API request: } }, { - "object_id": "", + "object_id": "tmplv_rT6Ul8RvQtSZPkNfsIExPQ", "target_context": "http/server" } ] @@ -312,7 +404,7 @@ Here's an example of what you need to include with the API request: #### Response with parse errors (200 OK) -If the rendered configuration has NGINX syntax errors. You can use this information to debug and correct your submission request. +If the rendered configuration has NGINX syntax errors, you can use this information to debug and correct your submission request. {{< call-out "caution" >}} Parse errors indicate the rendered configuration has NGINX syntax issues, often due to missing include files or incomplete template logic. See [Template Limitations]({{< ref "author-templates.md#template-limitations" >}}). @@ -328,30 +420,13 @@ Parse errors indicate the rendered configuration has NGINX syntax issues, often { "files": [ { - "contents": "dXNlciBuZ2lueDsKd29ya2VyX3Byb2Nlc3NlcyBhdXRvOwoKaHR0cCB7CiAgICAKICAgIAogICAgc2VydmVyIHsKICAgICAgICBsaXN0ZW4gODA7CiAgICAgICAgc2VydmVyX25hbWUgXzsKCiAgICAgICAgaW5jbHVkZSAvZXRjL25naW54L2NvbmYuZC9hdWdtZW50cy9oZWFsdGgtY2hlY2sudG1wbC43ODM0NmRlNGRhZTQuY29uZjsKCiAgICAgICAgCiAgICAgICAgbG9jYXRpb24gLyB7CiAgICAgICAgICAgIHByb3h5X3Bhc3MgaHR0cDovL2FwaS1zZXJ2aWNlOjgwODA7CiAgICAgICAgICAgIGluY2x1ZGUgL2V0Yy9uZ2lueC9jb25mLmQvYXVnbWVudHMvY29ycy1oZWFkZXJzLnRtcGwuNGFhZjM2ZDRhNjQzLmNvbmY7CgogICAgICAgIH0KICAgIH0KfQo=", + "contents": "", "mtime": "0001-01-01T00:00:00Z", "name": "nginx.conf", "size": 371 } ], "name": "/etc/nginx" - }, - { - "files": [ - { - "contents": "YWRkX2hlYWRlciAnQWNjZXNzLUNvbnRyb2wtQWxsb3ctT3JpZ2luJyAnaHR0cHM6Ly9hcHAuZXhhbXBsZS5jb20nIGFsd2F5czsKYWRkX2hlYWRlciAnQWNjZXNzLUNvbnRyb2wtQWxsb3ctTWV0aG9kcycgJ0dFVCwgUE9TVCwgUFVULCBERUxFVEUsIE9QVElPTlMnIGFsd2F5czsK", - "mtime": "0001-01-01T00:00:00Z", - "name": "cors-headers.tmpl.4aaf36d4a643.conf", - "size": 159 - }, - { - "contents": "bG9jYXRpb24gL2hlYWx0aCB7CiAgICBhY2Nlc3NfbG9nIG9mZjsKICAgIHJldHVybiAyMDAgImhlYWx0aHlcbiI7CiAgICBhZGRfaGVhZGVyIENvbnRlbnQtVHlwZSB0ZXh0L3BsYWluOwp9Cg==", - "mtime": "0001-01-01T00:00:00Z", - "name": "health-check.tmpl.78346de4dae4.conf", - "size": 109 - } - ], - "name": "/etc/nginx/conf.d/augments" } ] }, @@ -365,6 +440,122 @@ Parse errors indicate the rendered configuration has NGINX syntax issues, often } ``` +## Manage template submissions + +Submissions are persistent objects that store the template composition and input values used to generate a configuration. Each submission tracks its target(s) and can be retrieved, updated, or deleted. + +### Get a submission + +Use the [Get a Template Submission]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/getTemplateSubmission" >}}) API operation (`GET /templates/submissions/{submissionObjectID}`) to retrieve the full details of a submission, including the templates used, their input values, and target object IDs. + +**Example response:** + +```json +{ + "object_id": "tmplsm_frBobKIAQ_21grAwV83VYz", + "description": "Reverse proxy with rate limiting", + "target_object_ids": ["sc_cEoiYCVJRuekVpYOvV1raA"], + "created_at": "2025-09-25T19:20:47.473955Z", + "modified_at": "2025-09-25T19:20:47.473955Z", + "templates": [ + { + "template_object_id": "tmpl_-uvR3F2TQGm18jnl7bpaGw", + "template_version_object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", + "name": "reverse-proxy-base", + "type": "base", + "state": "final", + "version": 1, + "latest_version": 1, + "values": { + "backend_url": "http://example.com:8080" + } + } + ] +} +``` + +### Update a submission + +Use the [Update a Template Submission]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/updateTemplateSubmission" >}}) API operation (`PUT /templates/submissions/{submissionObjectID}`) to fully replace the input values and payloads for all templates in the submission. + +The `conf_path` and target object IDs are preserved from the original submission and cannot be changed through this endpoint. After the update, the configuration is re-rendered and re-published to the existing target(s). + +**Request body:** + +```json +{ + "base_template": { + "object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", + "values": { + "backend_url": "http://new-backend.example.com:9090" + } + }, + "augments": [ + { + "object_id": "tmplv_-abR3F2TQGm18jnl7bpaXw", + "target_context": "http", + "values": { + "zone_name": "req_limit", + "memory": "20m", + "rate": "20r/s" + } + } + ] +} +``` + +**Successful response (202 Accepted):** + +```json +{ + "object_id": "tmplsm_frBobKIAQ_21grAwV83VYz", + "target_results": [ + { + "staged_config_status": { + "status": "succeeded" + }, + "target_object_id": "sc_cEoiYCVJRuekVpYOvV1raA" + } + ] +} +``` + +To preview the updated configuration before persisting, add `?preview_only=true` to the request. The response returns the re-rendered configuration as a `200 OK` without saving any changes. + +### Update a single template's values + +Use the [Update a single template's values in a submission]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/updateSingleTemplateSubmission" >}}) API operation (`PUT /templates/{templateObjectID}/submissions/{submissionObjectID}`) to update the input values for one specific template within a submission, without changing any other template's values. + +All other templates in the submission retain their stored values. Payloads, target objects, and `conf_path` are preserved. The full configuration is re-rendered using the merged values and re-published to the existing target(s). + +This is useful when only one template's configuration needs to change — for example, updating a rate limiting zone name without resubmitting the full composition. + +**Request body:** + +```json +{ + "values": { + "zone_name": "api_limit", + "memory": "10m", + "rate": "5r/s" + } +} +``` + +**Successful response (202 Accepted):** Same shape as the full update — the submission `object_id` and updated target results. + +To preview the change before persisting, add `?preview_only=true`. The response returns the re-rendered configuration as a `200 OK` without saving any changes. + +### Delete a submission + +Use the [Delete a Template Submission]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/deleteTemplateSubmission" >}}) API operation (`DELETE /templates/submissions/{submissionObjectID}`) to permanently remove a submission. + +{{< call-out "caution" >}} +Deleting a submission is **irreversible** and removes all stored input values and payloads for that submission. The target staged config is not affected — only the submission record is deleted. +{{< /call-out >}} + +**Successful response:** `204 No Content` + ## Rendered file structure When templates are successfully rendered, the system creates multiple files: @@ -462,18 +653,18 @@ When multiple augments target the same context, they render in the order specifi { "conf_path": "/etc/nginx/nginx.conf", "base_template": { - "object_id": "", + "object_id": "tmplv_-uvR3F2TQGm18jnl7bpaGw", "values": { "backend_url": "http://example.com:8080" } }, "augments": [ { - "object_id": "tmpl_rate_limit_zone", + "object_id": "tmplv_rate_limit_zone", "target_context": "http" }, { - "object_id": "tmpl_upstream_definition", + "object_id": "tmplv_upstream_definition", "target_context": "http" } ] @@ -504,9 +695,10 @@ For example: - Upstream blocks should be defined before server blocks reference them - Map directives typically appear early in the http block -When composing templates submissions, arrange your augments array to match the required directive order for valid NGINX configuration. +When composing template submissions, arrange your augments array to match the required directive order for valid NGINX configuration. ## See also - [Template Authoring Guide]({{< ref "author-templates.md" >}}) -- [Add More Services]({{< ref "add-multiple-services.md" >}}) +- [Add Service-Specific Locations]({{< ref "add-multiple-services.md" >}}) +- [Save rendered config as staged config]({{< ref "save-as-staged-config.md" >}}) diff --git a/content/nginx-one-console/nginx-configs/config-templates/template-detail-view.md b/content/nginx-one-console/nginx-configs/config-templates/template-detail-view.md new file mode 100644 index 000000000..0ee1e0e6d --- /dev/null +++ b/content/nginx-one-console/nginx-configs/config-templates/template-detail-view.md @@ -0,0 +1,62 @@ +--- +f5-content-type: how-to +f5-docs: DOCS-000 +f5-product: NONECO +title: View template details +toc: true +weight: 110 +--- + +# Overview + +This guide explains how to view detailed information about a template using the NGINX One Console. The Template Detail page provides key metadata about a template and its version history through two tabs: **Details** and **Versions**. + +## Navigate to the Template Detail page + +1. In the NGINX One Console, go to **Manage > Config Templates**. +2. Select a template name from the list. Templates provided by F5 are identified by the F5 logo icon in the list. + +The Template Detail page opens showing the **Details** tab by default. Select the **Versions** tab to view the full version history. + +## Details tab + +The **Details** tab displays a summary card with the following fields: + +{{}} +| Field | Description | +|-------|-------------| +| **Created** | The date and time the template was originally created. | +| **Type** | The template type: `base` or `augment`. See [Template types]({{< ref "author-templates.md#template-types" >}}) for details. | +| **Is F5 Default** | Displayed for templates provided by F5. F5 default templates are immutable and cannot be modified or deleted. | +| **Object ID** | The unique identifier for the template (`tmpl_...`). Use the copy button to copy this value for template-level API operations such as [updating metadata]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/updateTemplateMetadata" >}}) or [copying a template]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/copyTemplate" >}}). | +| **State** | The state of the latest template version: `draft` (editable) or `final` (immutable, shown with a lock icon). | +| **Latest Version** | The version number of the most recent template version. | +| **Description** | The human-readable description of the template, if one was provided. | +| **Latest Object ID** | The unique identifier for the latest template version (`tmplv_...`). Use the copy button to copy this value for version-level API operations, such as providing the `object_id` when [submitting templates]({{< ref "submit-templates.md" >}}). | +{{}} + +{{< call-out "tip" >}} +Both **Object ID** and **Latest Object ID** are copyable directly from the UI. + +- **Object ID** (`tmpl_...`) identifies the template itself and is used for template-level operations (metadata updates, copy, delete, listing versions). +- **Latest Object ID** (`tmplv_...`) identifies the current version and is used as the `object_id` in submission requests. +{{< /call-out >}} + +## Versions tab + +The **Versions** tab lists every version created for the template, along with submission counts and modification timestamps. See [View template versions]({{< ref "template-versions.md" >}}) for full details. + +## Refresh + +Select **Refresh** at the top right of the page to reload the template details from the server. + +## API reference + +The Template Detail page uses the [Retrieve a Template]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/getTemplate" >}}) API operation, which returns the latest version details including metadata, file contents, and submission count. + +## See also + +- [View template versions]({{< ref "template-versions.md" >}}) +- [Author templates]({{< ref "author-templates.md" >}}) +- [Import templates]({{< ref "import-templates.md" >}}) +- [Submit templates]({{< ref "submit-templates.md" >}}) diff --git a/content/nginx-one-console/nginx-configs/config-templates/template-versions.md b/content/nginx-one-console/nginx-configs/config-templates/template-versions.md new file mode 100644 index 000000000..daf2b3687 --- /dev/null +++ b/content/nginx-one-console/nginx-configs/config-templates/template-versions.md @@ -0,0 +1,70 @@ +--- +f5-content-type: how-to +f5-docs: DOCS-000 +f5-product: NONECO +title: View template versions +toc: true +weight: 120 +--- + +# Overview + +This guide explains how to view and manage the version history of a template using the NGINX One Console. The **Versions** tab on the [Template Detail page]({{< ref "template-detail-view.md" >}}) lists every version created for a template and shows how many active submissions reference each version. + +A new version is created each time the template content changes. Versions progress through two states: + +- **`draft`** — editable; content can still be updated in place. +- **`final`** — immutable; any further content changes create a new draft version. + +## Navigate to the Versions tab + +1. In the NGINX One Console, go to **Manage > Config Templates**. +2. Select a template name from the list. +3. Select the **Versions** tab. + +## Versions data grid + +The **Versions** tab displays the following columns: + +{{}} +| Column | Description | +|--------|-------------| +| **Version** | The sequential version number. Version 1 is the initial version created at import. Each subsequent content change increments this number. | +| **Modified** | The date and time the version was last modified. | +| **Description** | The description associated with the template version, if one was provided. | +| **Submissions** | The total number of template submissions that reference this specific version. | +{{}} + +The list can be sorted by **Version**, **Modified**, or **Description**, and supports text search across all visible columns. + +{{< call-out "note" >}} +The **Submissions** count reflects the number of submissions referencing a specific version, not the latest version overall. A version with a non-zero submission count cannot be deleted. +{{< /call-out >}} + +## Delete a version + +To delete a template version, select the delete action on the version row and confirm the dialog. + +{{< call-out "important" >}} +The following constraints apply when deleting a template version: + +- **The latest version cannot be deleted.** To remove the entire template including the latest version, use [Delete a Template]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/deleteTemplate" >}}) instead. +- **A version with associated submissions cannot be deleted.** The **Submissions** column shows the count. Resolve or delete the associated submissions before attempting to remove the version. +{{< /call-out >}} + +## Refresh + +Select **Refresh** at the top right of the page to reload the version list from the server. + +## API reference + +The **Versions** tab uses the following API operations: + +- [List template versions]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/listTemplateVersions" >}}) — retrieves all versions for a template. +- [Delete a template version]({{< ref "/nginx-one-console/api/api-reference-guide/#operation/deleteTemplateVersion" >}}) — deletes a specific version by its `templateVersionObjectID`. Returns `409 Conflict` if the version has associated submissions. + +## See also + +- [View template details]({{< ref "template-detail-view.md" >}}) +- [Author templates]({{< ref "author-templates.md" >}}) +- [Submit templates]({{< ref "submit-templates.md" >}})