Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/deuxfleurs-org/garage/llms.txt

Use this file to discover all available pages before exploring further.

This guide shows how to run Garage as a systemd service on Linux, providing automatic startup, process management, and system integration.

Prerequisites

Before configuring systemd:
  • Garage binary installed at /usr/local/bin/garage
  • Configuration file at /etc/garage.toml
  • Understanding of systemd service management

Configuration Requirements

For systemd’s security features to work correctly, your /etc/garage.toml must use specific paths:
metadata_dir = "/var/lib/garage/meta"
data_dir = "/var/lib/garage/data"
These paths are mandatory for the DynamicUser hardening feature. If /var/lib/garage exists before first start, the service might not start correctly.
On the host filesystem, Garage data will actually be stored in /var/lib/private/garage due to systemd’s dynamic user mapping.

Creating the Service File

1

Create Service Unit

Create a file at /etc/systemd/system/garage.service:
[Unit]
Description=Garage Data Store
After=network-online.target
Wants=network-online.target

[Service]
Environment='RUST_LOG=garage=info' 'RUST_BACKTRACE=1'
ExecStart=/usr/local/bin/garage server
StateDirectory=garage
DynamicUser=true
ProtectHome=true
NoNewPrivileges=true
LimitNOFILE=42000

[Install]
WantedBy=multi-user.target
2

Reload systemd

Reload systemd to recognize the new service:
sudo systemctl daemon-reload

Service Hardening Features

The systemd service file includes several security hardening features:
  • Garage runs as a dynamically-allocated non-privileged user
  • User ID is allocated at service start
  • Provides isolation between services
  • Blocks access to /home, /root, and /run/user directories
  • Prevents accidental or malicious access to user data
  • Prevents the process from gaining new privileges
  • Blocks privilege escalation attempts
  • Automatically creates /var/lib/garage directory
  • Sets correct permissions for the dynamic user
  • Maps to /var/lib/private/garage on the host
  • Increases the file descriptor limit
  • Necessary for handling many simultaneous connections

Starting the Service

1

Start Garage

Start the Garage service:
sudo systemctl start garage
2

Enable Auto-Start

Enable Garage to start automatically at boot:
sudo systemctl enable garage
3

Verify Status

Check that the service is running:
sudo systemctl status garage
You should see output indicating the service is active:
● garage.service - Garage Data Store
   Loaded: loaded (/etc/systemd/system/garage.service; enabled; vendor preset: enabled)
   Active: active (running) since Mon 2024-01-15 10:30:00 UTC; 5s ago
 Main PID: 1234 (garage)
    Tasks: 10 (limit: 4915)
   Memory: 45.2M
   CGroup: /system.slice/garage.service
           └─1234 /usr/local/bin/garage server

Managing the Service

Basic Commands

# Start the service
sudo systemctl start garage

# Stop the service
sudo systemctl stop garage

# Restart the service
sudo systemctl restart garage

# Reload configuration (if supported)
sudo systemctl reload garage

# Check service status
sudo systemctl status garage

# Enable auto-start at boot
sudo systemctl enable garage

# Disable auto-start at boot
sudo systemctl disable garage

Viewing Logs

Use journalctl to view Garage logs:
# View all logs
sudo journalctl -u garage

# Follow logs in real-time
sudo journalctl -u garage -f

# View logs since last boot
sudo journalctl -u garage -b

# View logs from the last hour
sudo journalctl -u garage --since "1 hour ago"

# View logs with specific priority (error, warning, info, debug)
sudo journalctl -u garage -p err

Customizing the Service

Changing Log Level

Edit the service file to adjust the RUST_LOG environment variable:
[Service]
Environment='RUST_LOG=garage=debug' 'RUST_BACKTRACE=1'
Available log levels:
  • error: Only errors
  • warn: Warnings and errors
  • info: Normal operations (default)
  • debug: Detailed debugging information
  • trace: Very verbose debugging
After modifying, reload and restart:
sudo systemctl daemon-reload
sudo systemctl restart garage

Custom Binary Location

If your Garage binary is in a different location:
[Service]
ExecStart=/path/to/garage server

Custom Configuration File

To use a non-default configuration file:
[Service]
Environment='GARAGE_CONFIG_FILE=/path/to/garage.toml' 'RUST_LOG=garage=info' 'RUST_BACKTRACE=1'

Resource Limits

Add additional resource limits:
[Service]
# Limit memory usage to 4GB
MemoryMax=4G

# Limit CPU usage to 200% (2 cores)
CPUQuota=200%

# Increase file descriptor limit
LimitNOFILE=65536

Using with Multiple Nodes

For multi-node deployments, install and configure the systemd service on each node:
1

Install on Each Node

# Copy binary
sudo cp garage /usr/local/bin/
sudo chmod +x /usr/local/bin/garage

# Copy configuration (customize per node)
sudo cp garage.toml /etc/garage.toml

# Copy service file
sudo cp garage.service /etc/systemd/system/
2

Configure Each Node

Ensure each node’s /etc/garage.toml has:
  • Unique rpc_public_addr
  • Same rpc_secret across all nodes
  • Appropriate metadata_dir and data_dir
3

Start Services

# On each node
sudo systemctl daemon-reload
sudo systemctl enable --now garage
4

Connect Nodes

After all services are running, connect the nodes using the Garage CLI.

Troubleshooting

Service Fails to Start

Check the service status and logs:
# View detailed status
sudo systemctl status garage

# View recent error logs
sudo journalctl -u garage -p err --since "10 minutes ago"
Common issues:
  • Configuration file syntax errors
  • Permission issues with data directories
  • Port already in use
  • Invalid paths in configuration

Permission Denied Errors

If you see permission errors:
  1. Verify paths in /etc/garage.toml use /var/lib/garage/
  2. Remove any existing /var/lib/garage directory:
    sudo rm -rf /var/lib/garage
    
  3. Restart the service:
    sudo systemctl restart garage
    

Configuration Changes Not Applied

After modifying the service file:
sudo systemctl daemon-reload
sudo systemctl restart garage

Port Conflicts

If ports are already in use, check what’s using them:
# Check port 3900 (S3 API)
sudo netstat -tulpn | grep 3900

# Check port 3901 (RPC)
sudo netstat -tulpn | grep 3901

Alternative: Using with Socket Activation

For advanced use cases, you can configure socket activation:
# /etc/systemd/system/garage.socket
[Unit]
Description=Garage Socket

[Socket]
ListenStream=3900
ListenStream=3901

[Install]
WantedBy=sockets.target
Modify the service file:
[Unit]
Requires=garage.socket
After=garage.socket
Enable and start:
sudo systemctl enable garage.socket
sudo systemctl start garage.socket

Next Steps

Build docs developers (and LLMs) love