Why MinIO?
AWS S3 is powerful but expensive and locked to Amazon’s cloud. MinIO gives you the same S3 API — on your own hardware. It’s used by organizations like:
- Development teams who need a local S3 mock that uses the real S3 protocol.
- On-premises enterprises with data sovereignty requirements.
- Homelab enthusiasts who want object storage without cloud bills.
Prerequisites
- Linux server (Ubuntu 22.04 or RHEL 9).
- At least 4 GB RAM and a dedicated data disk.
- Root or sudo access.
Step 1: Install MinIO
Single-Node Setup (Quickest)
# Download the binary
wget https://dl.min.io/server/minio/release/linux-amd64/minio
chmod +x minio
sudo mv minio /usr/local/bin/
# Create data directory
sudo mkdir -p /data/minio
sudo chown $(whoami):$(whoami) /data/minio
# Set root credentials
export MINIO_ROOT_USER=minioadmin
export MINIO_ROOT_PASSWORD=StrongPassword123!
# Start MinIO
minio server /data/minio --console-address ":9001"
- API endpoint:
http://your-server:9000 - Web Console:
http://your-server:9001
Systemd Service (Production)
# /etc/systemd/system/minio.service
[Unit]
Description=MinIO Object Storage
After=network.target
[Service]
User=minio-user
EnvironmentFile=/etc/default/minio
ExecStart=/usr/local/bin/minio server /data/minio --console-address ":9001"
Restart=always
[Install]
WantedBy=multi-user.target
Environment file /etc/default/minio:
MINIO_ROOT_USER=minioadmin
MINIO_ROOT_PASSWORD=StrongPassword123!
MINIO_VOLUMES="/data/minio"
sudo systemctl daemon-reload
sudo systemctl enable --now minio
Step 2: Install the MinIO Client (mc)
wget https://dl.min.io/client/mc/release/linux-amd64/mc
chmod +x mc
sudo mv mc /usr/local/bin/
# Configure an alias pointing to your MinIO instance
mc alias set myminio http://localhost:9000 minioadmin StrongPassword123!
Common mc Commands
| Command | What it does |
|---|---|
mc mb myminio/my-bucket | Create a new bucket |
mc cp file.txt myminio/my-bucket/ | Upload a file |
mc ls myminio/my-bucket | List bucket contents |
mc mirror /local/dir myminio/my-bucket | Sync a local directory to a bucket |
mc anonymous set download myminio/my-bucket | Make a bucket publicly readable |
Step 3: Connect Applications (S3 SDK)
Any S3-compatible SDK works with MinIO. Here’s a Python (boto3) example:
import boto3
s3 = boto3.client(
's3',
endpoint_url='http://minio-server:9000',
aws_access_key_id='minioadmin',
aws_secret_access_key='StrongPassword123!',
config=boto3.session.Config(signature_version='s3v4'),
)
# Upload a file
s3.upload_file('local-file.pdf', 'my-bucket', 'remote-file.pdf')
# List objects
for obj in s3.list_objects_v2(Bucket='my-bucket')['Contents']:
print(obj['Key'])
Key point: Always set force_path_style: true (or equivalent) when using non-AWS S3 endpoints, and use Signature Version 4.
Troubleshooting
| Problem | Solution |
|---|---|
SignatureDoesNotMatch | Verify access/secret keys match; ensure client uses S3v4 signatures |
Connection refused on port 9000 | Check MinIO is running (systemctl status minio); verify firewall allows 9000/9001 |
| Slow uploads/downloads | Use mc mirror with --multi-threaded for parallelism; check disk I/O with iotop |
| ”Bucket already exists” error | Bucket names are global within the instance; choose a unique name |
| TLS certificate errors | Place public.crt + private.key in ~/.minio/certs/; restart MinIO |
Summary
- MinIO is a drop-in S3 replacement you can host yourself.
- Use
mc(MinIO Client) for CLI operations andboto3/aws-clifor application integration. - Always use S3v4 signatures and
force_path_style: true. - Run as a systemd service in production with credentials in
/etc/default/minio.