# S3-compatible storage

> Use Zaryn as S3 storage with aws-cli, rclone, restic and any S3 SDK. Make a key, point the tool at the endpoint, and every object is checked on every read and counted once on your storage plan.

Source: https://zaryn.xyz/docs/en/s3-storage

Zaryn speaks S3, the language almost every backup tool, sync tool and cloud SDK already knows. Make a key, point your tool at Zaryn's endpoint, and it works the way it does with Amazon S3: buckets, objects, folders, big files in parts.

```diagram
type: flow
title: From nothing to your first backup
---
Make a key | Storage → S3 access → Create key. Copy the secret: it is shown once | accent | 🔑
~ endpoint + key
Point the tool | aws-cli, rclone, restic, Kopia, your SDK: endpoint https://s3.zaryn.xyz | | 🔧
~ PUT
Store | Every object is hashed as it arrives and kept in Zaryn Vault | | 📦
~ GET
Read back | Checked against its hash before a byte is sent | | ✓
```

## Make an S3 key

1. Open [Storage](/storage#s3) and find **S3 access** (it is in [Settings](/settings) too).
2. Write what the key is for (say *laptop backup*) and press **Create key**.
3. Copy the **access key** and the **secret**. The secret is shown only now; Zaryn keeps it encrypted and can't show it again. Lost it? Revoke the key and make a new one.

An account has up to 10 keys. Give each tool or machine its own, so you can revoke one without touching the others.

## Connect aws-cli, rclone, restic or an SDK

The endpoint is `https://s3.zaryn.xyz` and the region `zaryn`. Both path-style (`s3.zaryn.xyz/bucket/key`) and virtual-hosted style (`bucket.s3.zaryn.xyz/key`) work.

**aws-cli**

```bash
aws configure set aws_access_key_id ZK...
aws configure set aws_secret_access_key ...
aws configure set region zaryn
aws --endpoint-url https://s3.zaryn.xyz s3 mb s3://my-files
aws --endpoint-url https://s3.zaryn.xyz s3 sync ~/Pictures s3://my-files/pictures
```

**rclone** (in `~/.config/rclone/rclone.conf`)

```ini
[zaryn]
type = s3
provider = Other
endpoint = https://s3.zaryn.xyz
region = zaryn
access_key_id = ZK...
secret_access_key = ...
```

Then `rclone sync ~/Documents zaryn:my-files/documents`.

**restic** (encrypted, deduplicated backups)

```bash
export AWS_ACCESS_KEY_ID=ZK...
export AWS_SECRET_ACCESS_KEY=...
restic -r s3:https://s3.zaryn.xyz/my-backups init
restic -r s3:https://s3.zaryn.xyz/my-backups backup ~/Documents
```

Veeam, Synology, Kopia and more, step by step: [Connect your tools in 60 seconds](/docs/en/connect-storage).

Or let zev do it all: [`zev backup`](/docs/en/backups) makes the key and the bucket, encrypts, deduplicates and schedules, and restores any day with one command.

**Any SDK** (Python's boto3 here; the others take the same three settings)

```python
import boto3
s3 = boto3.client("s3", endpoint_url="https://s3.zaryn.xyz", region_name="zaryn",
                  aws_access_key_id="ZK...", aws_secret_access_key="...")
s3.upload_file("report.pdf", "my-files", "2026/report.pdf")
```

## How it is counted

S3 shares your [storage plan](/storage#plans) with the files you share by link. An object kept twice in a bucket (a copy, the same photo synced from two folders) is stored once and counts once.

```diagram
type: stats
title: What counts
---
Once | an object kept twice in a bucket | the same bytes, one copy | | accent
Whole | an upload still in parts | until it completes or is aborted | |
7 days | parts of an upload never finished | then removed for you | |
```

When the plan is full, a new upload gets `QuotaExceeded`. Nothing already stored is touched: reads, lists and deletes keep working.

## What makes it different

- **Checked on every read.** Each object is named by its BLAKE3 hash. Before a byte is sent, what's on disk is checked against it (in 8 MiB windows for big objects). A damaged object is refused, never served, and the daily check repairs it from its second copy.
- **Checked on every write.** An upload is refused unless it matches what your tool says it sent: its SHA-256, its Content-MD5 and its `x-amz-checksum`.
- **Signed like AWS.** Every request is signed with SigV4: by the header, a presigned URL, or `aws-chunked` uploads with a signature per chunk.

## What works

| | |
|---|---|
| Buckets | create, list, delete (when empty), head, location |
| Objects | put, get (with ranges), head, delete, delete many, copy |
| Listing | v1 and v2, with prefix, delimiter (folders) and pages |
| Big files | multipart: start, upload parts (up to 10,000), complete, abort, list |
| Object lock | retention (governance, compliance), legal holds, bucket defaults: see [Ransomware protection](/docs/en/ransomware-protection) |
| Limits | 5 GB per object, 100 buckets and 10 keys per account |

Versioning is off; instead a bucket can have a [trash](/docs/en/ransomware-protection#the-trash) that keeps deleted and overwritten objects. Bucket policies, ACLs and lifecycle rules aren't there yet: every bucket belongs to your account and only your keys can use it.

Related: [Storing and sharing files](/docs/en/storing-files), [Verified storage](/docs/en/verified-storage).
