# Artifacts

Artifacts let you save files produced during a workflow run and make them available for download after the run completes. Common uses include test reports, build outputs, compiled binaries, log files, and any other data you want to persist beyond the lifetime of the job that created it.

Artifacts are stored on the Copia server and can be downloaded from the workflow run summary page in the Copia web UI. Each artifact is packaged as an immutable zip archive, so its contents cannot be modified after upload.

## Why Use Artifacts

Artifacts are useful any time you need to keep files that a workflow generates. A few examples:

* Save test results or coverage reports so your team can review them without re-running the workflow.
* Preserve compiled binaries or packaged project exports that were built during CI.
* Pass files between jobs in the same workflow. For instance, one job can build an output and upload it as an artifact, and a later job can download and use it.
* Archive logs or diagnostic data from long-running validation steps.

Without artifacts, any files created during a job are discarded when the job finishes. Artifacts give you a way to hold on to those files.

## Uploading Artifacts

To upload an artifact, use the `actions/upload-artifact` action in your workflow. At minimum, you need to provide a `name` for the artifact and a `path` pointing to the file or directory you want to upload.

### Basic Example

```yaml
name: Build and Save Output
on: [push]

jobs:
  build:
    runs-on: windows10-S5K
    steps:
      - name: Check out repository
        uses: actions/checkout@v3

      - name: Run build script
        run: ./build.sh

      - name: Upload build output
        uses: actions/upload-artifact@v3
        with:
          name: build-output
          path: dist/
```

This uploads everything in the `dist/` directory as an artifact named `build-output`. After the workflow run finishes, you can download `build-output` as a zip file from the run summary page.

### Uploading Individual Files

```yaml
- uses: actions/upload-artifact@v3
  with:
    name: test-report
    path: results/report.xml
```

### Uploading with Wildcard Patterns

You can use glob patterns and exclusions to control exactly which files are included.

```yaml
- uses: actions/upload-artifact@v3
  with:
    name: logs
    path: |
      output/logs/
      !output/logs/*.tmp
```

### Upload Inputs Reference

<table><thead><tr><th width="200.2890625" align="center">Input</th><th width="382.98828125">Description</th><th align="center">Default</th></tr></thead><tbody><tr><td align="center"><code>name</code></td><td>Name of the artifact</td><td align="center"><code>artifact</code></td></tr><tr><td align="center"><code>path</code></td><td>File, directory, or wildcard pattern to upload (required)</td><td align="center">-</td></tr><tr><td align="center"><code>if-no-files-found</code></td><td>Behavior when no files match: <code>warn</code>, <code>error</code>, or <code>ignore</code></td><td align="center"><code>warn</code></td></tr><tr><td align="center"><code>retention-days</code></td><td>Number of days to keep the artifact (1-90)</td><td align="center">Repository default</td></tr><tr><td align="center"><code>compression-level</code></td><td>Zlib compression level, 0 (none) to 9 (max)</td><td align="center"><code>6</code></td></tr><tr><td align="center"><code>overwrite</code></td><td>Delete any existing artifact with the same name before uploading</td><td align="center"><code>false</code></td></tr></tbody></table>

### Upload Outputs

After a successful upload, the step exposes the following outputs:

<table><thead><tr><th width="167.49609375" align="center">Output</th><th>Description</th></tr></thead><tbody><tr><td align="center"><code>artifact-id</code></td><td>Unique ID for the uploaded artifact</td></tr><tr><td align="center"><code>artifact-url</code></td><td>Direct URL to download the artifact (requires login)</td></tr></tbody></table>

You can reference these outputs in later steps or jobs. For example:

```yaml
- name: Upload artifact
  id: upload-step
  uses: actions/upload-artifact@v3
  with:
    name: my-artifact
    path: output/

- name: Print artifact ID
  run: echo "Artifact ID is ${{ steps.upload-step.outputs.artifact-id }}"
```

## Downloading Artifacts

To download an artifact in a later job within the same workflow, use `actions/download-artifact`.

### Download in a Subsequent Job

```yaml
jobs:
  build:
    runs-on: windows10-S5K
    steps:
      - name: Check out repository
        uses: actions/checkout@v3

      - name: Build project
        run: ./build.sh

      - name: Upload build output
        uses: actions/upload-artifact@v3
        with:
          name: build-output
          path: dist/

  deploy:
    runs-on: windows10-S5K
    needs: build
    steps:
      - name: Download build output
        uses: actions/download-artifact@v3
        with:
          name: build-output
          path: dist/

      - name: Deploy
        run: ./deploy.sh dist/
```

The `needs: build` line ensures the `deploy` job waits for `build` to finish before running.

### Download Inputs Reference

<table><thead><tr><th width="175.109375" align="center">Input</th><th width="403.23046875">Description</th><th align="center">Default</th></tr></thead><tbody><tr><td align="center"><code>name</code></td><td>Name of the artifact to download. If omitted, all artifacts are downloaded.</td><td align="center">-</td></tr><tr><td align="center"><code>path</code></td><td>Directory to download into</td><td align="center">Working directory</td></tr><tr><td align="center"><code>pattern</code></td><td>Glob pattern to filter which artifacts to download</td><td align="center">-</td></tr><tr><td align="center"><code>merge-multiple</code></td><td>When downloading multiple artifacts, merge them into the same directory instead of creating subdirectories</td><td align="center"><code>false</code></td></tr></tbody></table>

## Downloading from the Copia Web UI

You do not need to use `actions/download-artifact` to access your artifacts manually. After a workflow run completes, navigate to the run summary page in the **Actions** tab of your repository. A dedicated **Artifacts** section at the bottom of the page lists all artifacts produced by that run. Click on an artifact name to download it as a zip file.

Users with write permissions to the repository can also delete artifacts from this page.

## Important Limitations

There are a few things to keep in mind when working with artifacts:

**Unique names per job.** Each artifact within a workflow run must have a unique name. You cannot upload to the same artifact name twice in the same job. If you need to upload from multiple jobs or matrix runs, include a distinguishing suffix in the name:

```yaml
- uses: actions/upload-artifact@v3
  with:
    name: results-${{ matrix.os }}
    path: output/
```

**Artifact count limit.** Each job can create up to 500 artifacts.

**Retention.** Artifacts are retained for 90 days by default. You can set a shorter retention period using the `retention-days` input. After the retention period expires, artifacts are automatically deleted.

**Zip format only.** Artifacts are always packaged as zip archives. There is no option to download individual files or use a different archive format.

**File permissions are not preserved.** When artifacts are downloaded, any special file permissions\
from the original files (such as executable flags on scripts) are reset to defaults. If you need to\
preserve the original permissions, wrap your files in a tar archive before uploading:

```yaml
- name: Tar files to preserve permissions
  run: tar -cvf my-files.tar path/to/files/

- name: Upload tar archive
  uses: actions/upload-artifact@v3
  with:
    name: my-artifact
    path: my-files.tar
```

**Compression tip.** For large files that do not compress well (like binary data), set `compression-level: 0` to skip compression and significantly speed up the upload.


---

# 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.copia.io/docs/actions/artifacts.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.
