Managed Garage hosting

Workflow and dataOn-prem or sovereign site

S3-compatible object storage that keeps every object in three zones, on your own hardware or in the Pilae regions you choose. Pilae runs it on your own servers, or in Zurich, Switzerland, and eleven other Pilae Cloud regions.

Talk to us about Garage

Licence
AGPL-3.0
Runs on
Your own hardware, or any of twelve Pilae regions — six of them in Switzerland and the EU
Upgrades
Pinned, tested against your configuration, applied in your window
Upstream
garagehq.deuxfleurs.fr

Running Garage in production: what it takes

  1. Place three zones

    One node per zone, placed where the data is allowed to live: Pilae regions, your own sites, or both. Zones get similar capacity, because the smallest one sets how much the cluster can hold.

  2. Metadata on SSD, with snapshots

    The object index lives on SSD under a checksumming filesystem, and data blocks on large disks under XFS. Metadata is snapshotted every six hours, because an unclean shutdown can corrupt the default LMDB engine, and the snapshots go to the data disks rather than the SSD.

  3. A key per application, private by default

    Every app gets its own key on its own buckets. Garage answers only on the private network, and anything you publish, such as a static site or a presigned download link, goes through the gate on port 443.

  4. Back up beyond the replicas

    Three copies survive a lost disk or a lost zone, not a delete. Buckets go offsite daily, encrypted, to a location in your chosen country. Once a month we restore one into a scratch environment and read it back.

  5. Upgrade one major release at a time

    Minor releases roll through node by node with no downtime. Major releases go one at a time, never skipped, and the whole cluster switches together after a metadata snapshot. The Pilae Agent rehearses each upgrade on a copy of the cluster and applies it in your window once you approve, recording it in the console.

What Garage is, and who runs it

Self-hosted Garage for S3-compatible object storage

Garage is an object store that speaks the Amazon S3 API. It ships as a single binary with no external database or coordination service, and it was designed to keep every object in three zones: separate sites joined over ordinary networks, so that a whole site can go dark while the applications carry on. It is developed by Deuxfleurs, a French non-profit that has run it in production since 2020, with public funding from the EU Next Generation Internet programme.

Most of the apps we operate want a bucket somewhere: Nextcloud for primary storage, Harbor for container images, backup tools for their repositories. Garage is that bucket, spread across three of our 12 Pilae Cloud regions, across three of your own sites, or across a mix of both. The bucket is often where most of an organisation’s data ends up, which makes it the place where residency is decided.

Garage in production: zones, metadata and backups

Most of the work is in the layout. We place one node per zone and prefer fewer, bigger nodes over many small ones, because Garage spreads data most evenly over those. Metadata sits on SSD and is snapshotted every six hours. Nodes answer only on the private network, whose encrypted tunnels carry the S3 traffic Garage serves without TLS of its own. A bucket reaches the internet only through the gate, and only if you publish it.

A delete reaches all three replicas at once, and Garage has no versioning to undo it, so the replicas are not the backup. Buckets are also backed up daily, encrypted, to an offsite location in your chosen country, and once a month we restore one into a scratch environment and read it back. Our monitoring probes every node every 60 seconds, and upgrades go through the Pilae Agent one major release at a time.

Garage licence and S3 compatibility

Garage is AGPL-3.0 and has no paid edition. If you want to fund the project directly, the Garage team at Deuxfleurs takes donations and support contracts. What a small system gives up is S3 API coverage: no versioning, no object lock, no bucket policies or ACLs, and no server-side encryption with managed keys. Customer-provided keys (SSE-C) work, and the disks underneath are encrypted. We check what your applications call before we recommend Garage, and say when another store fits better. Pricing is on request. Talk to us about the buckets you want to move off S3.

Garage system requirements

Before anything is deployed, this is what has to exist. We size it with you in the first session, and we say so when your own hardware is already enough.

Nodes
3 nodes · 3 zonesThree-way replication keeps one copy in each zone. The smallest zone sets how much the cluster can hold, so zones are sized alike.
CPU and memory
2 vCPU · 4 GB per nodeUpstream asks for 1 GB. The headroom lets the kernel cache the metadata database, which upstream recommends for performance.
Metadata disk
SSD · ZFS or BtrfsHolds the index of every object. Garage does not checksum its metadata, so the filesystem should, and the default LMDB engine needs snapshots in case an unclean shutdown corrupts it.
Data disks
HDD or SSD · XFSGarage checksums and scrubs data blocks itself and uses several disks per node without RAID. Ext4 is avoided because its inode limits bite on large object counts.
Network between zones
≤200 ms · ≥50 MbpsUpstream figures. Nodes talk to each other on port 3901, always encrypted, over the private network. The S3 endpoint has no TLS of its own, so it stays on the private network too, and reaches the gate only if you publish it.

Migrating from Amazon S3 to Garage

Applications keep speaking S3, so for most of them the move is a new endpoint, a region name and a new pair of keys, and the objects copy across with rclone or any S3 client. What does not come across is what Amazon keeps beside the objects. Garage has no versioning, so only the current version of each object moves. It has no object lock, bucket policies, ACLs or storage classes. IAM policies become one key per application with read, write or owner rights on named buckets, and lifecycle rules survive only as expiry and the cleanup of abandoned uploads. The work is in finding which of those features an application quietly relies on, and in the copy itself, which AWS bills as data transfer out unless AWS Support approves a credit for leaving.

  1. List what each bucket relies on

    We read the AWS configuration of every bucket for the features Garage lacks. A bucket that needs object lock stays on a store that has it, and we name those buckets before anything moves.

  2. Create buckets and keys

    Each application gets one Garage key, limited to its own buckets. Keys can carry an expiry date, so a contractor's key ends when the contract does.

  3. Copy, then copy the difference

    A bulk copy with rclone runs while the applications still write to S3, and a second pass on the night of the switch takes what changed. Object counts and sizes are compared per bucket before anything is repointed.

  4. Repoint, then freeze the old bucket

    Each application gets the new endpoint, region and keys, with path-style or virtual-host addressing set to what it expects. It is tested against Garage first, so a call Garage does not implement returns 501 there and not in production. The S3 bucket stays read-only until its owner signs off.

One Garage node of three, as configured

# /etc/garage.toml on acme-s3-fra1. The nodes in gra1 and ams1 differ only in their addresses.
replication_factor = 3
consistency_mode = "consistent"

metadata_dir = "/var/lib/garage/meta"              # NVMe, ZFS
metadata_snapshots_dir = "/srv/garage/hdd1/snapshots"  # on the data disks, not the SSD
metadata_auto_snapshot_interval = "6h"
db_engine = "lmdb"

data_dir = [
  { path = "/srv/garage/hdd1", capacity = "8T" },
  { path = "/srv/garage/hdd2", capacity = "8T" },
]

rpc_bind_addr = "[::]:3901"
rpc_public_addr = "10.40.1.11:3901"                # private network only
rpc_secret_file = "/run/secrets/garage_rpc_secret"

[s3_api]
api_bind_addr = "[::]:3900"                        # plain HTTP, private network only
s3_region = "garage"

[admin]
api_bind_addr = "10.40.1.11:3903"
admin_token_file = "/run/secrets/garage_admin_token"
metrics_token_file = "/run/secrets/garage_metrics_token"
metrics_require_token = true

# Layout, staged and applied once, from one node:
#   garage layout assign 3f1a -z fra1 -c 16T -t acme-s3-fra1
#   garage layout assign 9c07 -z gra1 -c 16T -t acme-s3-gra1
#   garage layout assign d24e -z ams1 -c 16T -t acme-s3-ams1
#   garage layout apply --version 1
An example cluster for acme with one node each in Frankfurt, Gravelines and Amsterdam, so every object has a copy in three EU countries and a whole region can fail while reads and writes carry on. Secrets are read from files rather than written into the config, metadata is snapshotted every six hours, and the S3 port speaks plain HTTP only inside the encrypted private network.

What Pilae is responsible for

A pinned version

A version we have run, not whatever latest resolves to that day.

A runbook

What it depends on, how it fails, what to do about it. In your repository.

A restore drill

Backups restored on a schedule. A backup nobody has restored is a file.

A patch window

Security updates in a window you agreed, with a rollback ready.

Someone watching

Every endpoint probed on the minute. An alert reaches a person, not a dashboard nobody opens.

Where it runs
zur1, fra1, fal1, gra1, ams1, hel1, lon1, ash1, hil1, sin1, tok1, syd1, on-premZurich, Frankfurt, Falkenstein, Gravelines, Amsterdam, Helsinki, London, Ashburn, Hillsboro, Singapore, Tokyo, Sydney, Your own hardware
Who holds the credentials
You do. Ours are separate, named, logged and revocable with one command. We ask before anything changes outside an agreed window.
If you leave
The machine, the data, the compose files and the runbook are already yours. Nothing stops when our access does.

What drives the price of running Garage

Pricing is on request: a fixed price for onboarding, then a monthly price for Garage, quoted in writing within five business days. The plans set what every deployment includes; these are the inputs the quote is built from.

Instance size
The CPU, memory and, where a model runs, the GPUs the app needs for your users and your data.
High availability
One machine with tested restores, or a replicated setup that keeps serving when a node fails.
Storage and backups
How much data it holds, how long backups are kept, and point-in-time recovery for its database.
Plan and support
Essential, Business or Enterprise: support hours, response times in the contract and how often we review the service with you.
Region
Your own hardware, where the infrastructure is already yours, or a Pilae Cloud region, where it is passed through at cost plus a fixed margin.
Sign-on and integrations
Single sign-on, directory sync, mail relays and the other systems the app has to reach.

Garage: common questions

Is Garage open source?

Yes. Garage is AGPL-3.0 throughout, with no paid edition and no features held back for a commercial licence. It is developed by Deuxfleurs, a French non-profit association, and has had public funding from the EU Next Generation Internet programme through NGI POINTER and NLnet. We run it unmodified, so the AGPL asks nothing extra of you in the normal case.

Where do the objects actually live?

In all three zones of the layout, since each object has a copy in each. That makes residency the first thing the zones are chosen for: three Pilae regions inside the EU, such as Frankfurt, Gravelines and Amsterdam, your own sites, or a mix. If the data must stay in Switzerland, the zones are Zurich and two of your own Swiss sites, or three of your own.

Can a Garage bucket hold our backups?

Yes, as a target for backup tools such as restic that keep their own snapshots and retention. Garage itself has no versioning or object lock, and the project states that a safe object lock cannot be built on its design, which has no consensus protocol. If your backup policy requires write-once, immutable storage, that copy needs another store, and we say so before you choose Garage for it.

How does Garage compare with MinIO or Ceph?

Garage is the small option: a single binary on three nodes, with a narrower S3 API, and it fits when that API is enough for your applications. Ceph covers far more of the S3 API, versioning and object lock included, and is a much larger system to run. The MinIO community repository is archived and states that it is no longer maintained, its community edition ships as source code only, and the vendor points to its AIStor editions instead.

What happens when a node or a whole zone fails?

With three zones, the cluster keeps reading and writing while the failures stay within one zone, and loses no data while they stay within two. A replaced disk refills from the other copies with one repair command, and a replacement node takes over the old one in the layout. Our probes check every node every 60 seconds and alert an engineer when one drops out.

Also in workflow and data

Back to apps

Bring us your Garage. We will tell you what it takes.

Thirty minutes on the deployment you already have, or the one you are about to start.