# Support Files

## Overview

When uploading a workflow version, you can include **support files** alongside your WDL files. Support files let you configure transformations, defaults, and dependencies as part of a single upload — no additional API calls or UI steps required.

Workbench recognizes support files by their filename extension:

| Extension             | Creates                  |
| --------------------- | ------------------------ |
| `*.defaults.json`     | Default parameter values |
| `*.transformation.js` | Input transformations    |
| `*.dependencies.json` | Workflow dependencies    |

Any file that does not match one of these patterns is treated as a regular workflow file (e.g., WDL descriptors, imported tasks).

{% hint style="info" %}
Support files work identically whether you upload through the **UI** (drag and drop or file picker) or the **CLI** (`workflows create` / `workflows versions create`).
{% endhint %}

## Example

A typical workflow upload with support files might look like this:

```
my-variant-pipeline/
├── main.wdl
├── tasks/
│   └── align.wdl
├── production.defaults.json
├── production.provider-AWS.region-us-east-1.defaults.json
├── normalize.transformation.js
└── upstream.dependencies.json
```

When you upload this directory, Workbench will:

1. Store `main.wdl` and `tasks/align.wdl` as workflow descriptor files
2. Create a **defaults** entry named `production` with default parameter values
3. Create a second **defaults** entry named `production` scoped to AWS in `us-east-1`
4. Create a **transformation** named `normalize`
5. Create a **dependency** set named `upstream`

All of this happens in a single upload. If any support file fails validation, the entire upload is rolled back — no partial state is created.

***

## Defaults

Defaults files provide pre-configured parameter values for a workflow version. They are useful for setting environment-specific values (such as reference genome paths, thread counts, or cloud provider settings) so users don't have to fill them in manually for every run.

### Basic usage

Any file ending in `.defaults.json` is recognized as a defaults file. The portion before `.defaults.json` becomes the name.

**Filename:** `production.defaults.json`

```json
{
  "threads": 8,
  "memory": "16GB",
  "reference_genome": "gs://my-bucket/references/hg38.fa"
}
```

This creates a defaults entry named `production` with the specified parameter values.

You can also wrap parameters in a `values` object — both formats are accepted:

```json
{
  "values": {
    "threads": 8,
    "memory": "16GB"
  }
}
```

### Selectors

Selectors let you scope defaults to specific execution environments. Add selector segments between the name and `.defaults.json`, using the format `key-value`:

```
<name>.<key-value>.<key-value>.defaults.json
```

The supported selector keys are:

| Key        | Description      | Example                                   |
| ---------- | ---------------- | ----------------------------------------- |
| `provider` | Cloud provider   | `provider-AWS`, `provider-GCP`            |
| `region`   | Cloud region     | `region-us-east-1`, `region-europe-west1` |
| `engine`   | Execution engine | `engine-omics`, `engine-cromwell`         |

**Examples:**

| Filename                                                        | Name   | Selector                                           |
| --------------------------------------------------------------- | ------ | -------------------------------------------------- |
| `prod.defaults.json`                                            | `prod` | *(none — applies broadly)*                         |
| `prod.provider-AWS.defaults.json`                               | `prod` | provider = AWS                                     |
| `prod.engine-omics.provider-AWS.region-us-east-1.defaults.json` | `prod` | provider = AWS, region = us-east-1, engine = omics |

Selector segments can appear in any order. Unknown selector keys are silently ignored, so existing uploads remain compatible as new keys are introduced.

{% hint style="warning" %}
Two defaults files with the same name **and** identical selectors will cause the upload to fail. Different selectors for the same name are allowed — this is how you create environment-specific overrides.
{% endhint %}

***

## Transformations

Transformations are JavaScript functions that modify workflow inputs before execution. They are useful for normalizing user-provided values, injecting computed parameters, or adapting inputs for specific execution environments.

### Basic usage

Any file ending in `.transformation.js` is recognized as a transformation. The portion before `.transformation.js` becomes the name.

**Filename:** `normalize.transformation.js`

```javascript
function transform(params) {
  if (params.sample_id) {
    params.sample_id = params.sample_id.trim().toUpperCase();
  }
  return params;
}
```

This creates a transformation named `normalize`.

{% hint style="info" %}
Transformation scripts are stored as-is. Workbench does not validate JavaScript syntax at upload time.
{% endhint %}

### Ordered chains

When you need transformations to run in a specific sequence, prefix the filename with a number and a dash:

```
<order>-<name>.transformation.js
```

**Examples:**

| Filename                        | Name        | Order         |
| ------------------------------- | ----------- | ------------- |
| `normalize.transformation.js`   | `normalize` | *(unordered)* |
| `1-validate.transformation.js`  | `validate`  | 1             |
| `2-normalize.transformation.js` | `normalize` | 2             |
| `03-enrich.transformation.js`   | `enrich`    | 3             |

Ordered transformations form a chain that executes in ascending numeric order. Unordered transformations are appended after any ordered chain.

{% hint style="warning" %}
Two transformations with the same name, or two transformations with the same order number, will cause the upload to fail.
{% endhint %}

***

## Dependencies

Dependencies define prerequisite workflows that must complete before this workflow can run. They are useful for building multi-step analysis pipelines where one workflow's output feeds into another.

### Basic usage

Any file ending in `.dependencies.json` is recognized as a dependencies file. The portion before `.dependencies.json` becomes the name.

**Filename:** `upstream.dependencies.json`

```json
{
  "dependencies": [
    {
      "workflow_id": "alignment-pipeline",
      "workflow_version_id": "v2_0_0"
    }
  ]
}
```

This creates a dependency set named `upstream` that references the `alignment-pipeline` workflow.

{% hint style="warning" %}
Only **one** set of dependencies can exist for any given workflow version. Include a single `.dependencies.json` file per upload.
{% endhint %}

***

## Version updates and copy-forward

When you upload a new workflow version, support file behavior depends on what you include in the upload:

* **No support files of a given type included:** The previous version's entries for that type are automatically carried forward. For example, uploading only a new `main.wdl` will preserve all defaults, transformations, and dependencies from the prior version.
* **Any support file of a given type included:** Copy-forward is disabled for that type, and only the files you upload are used. For example, including a single `prod.defaults.json` replaces **all** defaults from the prior version — not just the one named `prod`.

{% hint style="info" %}
Copy-forward is all-or-nothing **per type**. You cannot selectively update one defaults entry while keeping others from a previous version — either include all the defaults files you want, or include none to carry everything forward.
{% endhint %}

This does not affect WDL descriptor files. Each version's WDL files are an immutable snapshot and are never copied from prior versions.

***

## Troubleshooting

| Error message                                                          | Cause                                                              |
| ---------------------------------------------------------------------- | ------------------------------------------------------------------ |
| `Multiple transformations named '<name>'`                              | Two transformation files resolve to the same name                  |
| `Multiple transformations with order '<n>'`                            | Two transformation files share the same numeric order prefix       |
| `Multiple defaults with name '<name>' and identical selectors`         | Two defaults files have the same name and matching selector values |
| `Multiple dependencies named '<name>'`                                 | Two dependencies files share the same name                         |
| `Failed to parse defaults file '<filename>': ...`                      | The JSON content of a defaults file is malformed                   |
| `Failed to parse dependencies file '<filename>': ...`                  | The JSON content of a dependencies file is malformed               |
| `Dependencies file '<filename>' missing required 'dependencies' field` | The JSON is valid but missing the top-level `dependencies` array   |


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.omics.ai/products/workbench/workflows/support-files.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
