n8n Backup ve Workflow Dışa Aktarma Rehberi
Prodüksiyonda çalışan bir n8n instance’ı kaybetmek, üzerine haftalarca emek harcadığın workflow’ları sıfırdan yazmak zorunda kalmak demek. Bunu bir kez yaşayan bir daha “backup almayı unuttum” demez. Bu yazıda n8n’de backup alma, workflow dışa aktarma ve otomatik yedekleme stratejilerini ele alacağız. Hem Docker ortamı hem de bare metal kurulum için pratik senaryolarla gidelim.
n8n’in Veri Yapısını Anlamak
Backup almadan önce neyi yedeklediğimizi bilmek gerekiyor. n8n verilerini iki farklı yerde tutuyor:
Veritabanı: Workflow’lar, credential’lar, execution history, kullanıcı bilgileri. Varsayılan olarak SQLite kullanılır, production ortamda PostgreSQL veya MySQL tercih edilmeli.
Dosya Sistemi: Encryption key (.n8n/config), binary veri dosyaları, custom node’lar.
SQLite kullananlar için tek bir .db dosyası tüm şeyi barındırıyor. PostgreSQL’e geçtiyseniz iş biraz daha karmaşıklaşıyor ama yönetimi çok daha kolay hale geliyor. Özellikle büyük takımlarda SQLite’ı kesinlikle tavsiye etmiyorum, bir süre sonra locking sorunları başlıyor.
Workflow’ları CLI ile Dışa Aktarma
n8n, n8n export komutunu sunuyor ve bu komut oldukça güçlü. Docker kullanıyorsan container içinde, bare metal kurulumda doğrudan çalıştırabilirsin.
Tek Bir Workflow’u Dışa Aktarma
# Workflow ID'sini önce listele
n8n list:workflow
# Belirli bir workflow'u JSON olarak dışa aktar
n8n export:workflow --id=5 --output=/backup/workflow-5.json
Buradan çıkan JSON dosyası, tüm node yapılandırmasını, bağlantıları ve ayarları içeriyor. Credential değerlerini içermediğini not düş, bu güvenlik açısından iyi bir şey aslında.
Tüm Workflow’ları Toplu Dışa Aktarma
# Tüm workflow'ları tek bir dizine aktar
n8n export:workflow --all --output=/backup/workflows/
# Credentials'ları da dışa aktar (dikkatli kullan!)
n8n export:credentials --all --output=/backup/credentials/
# Backup dizini tarihli olsun
BACKUP_DATE=$(date +%Y%m%d_%H%M%S)
mkdir -p /backup/n8n/$BACKUP_DATE
n8n export:workflow --all --output=/backup/n8n/$BACKUP_DATE/
Credential backup’ı almak istiyorsun ama bunu düz metin olarak saklamak felaket olur. Şifrelenmiş arşiv içinde sakla, buna aşağıda döneceğiz.
Docker Ortamında Dışa Aktarma
Docker ile çalışıyorsan komutları container içinde çalıştırman gerekiyor:
# Container adını bul
docker ps | grep n8n
# Container içinde export komutu çalıştır
docker exec -it n8n_container n8n export:workflow --all --output=/home/node/.n8n/backups/
# Host'a kopyala
docker cp n8n_container:/home/node/.n8n/backups/ /opt/backups/n8n/
# Docker Compose ile
docker compose exec n8n n8n export:workflow --all --output=/home/node/.n8n/backups/
Otomatik Backup Script’i
Manuel export yapmak güzel bir başlangıç ama gerçek dünyada buna zaman ayıramazsın. Bir bash script yazalım, bunu cron’a verelim:
#!/bin/bash
# /opt/scripts/n8n-backup.sh
set -euo pipefail
# Yapılandırma
N8N_CONTAINER="n8n"
BACKUP_ROOT="/opt/backups/n8n"
RETENTION_DAYS=30
BACKUP_DATE=$(date +%Y%m%d_%H%M%S)
BACKUP_DIR="${BACKUP_ROOT}/${BACKUP_DATE}"
LOG_FILE="/var/log/n8n-backup.log"
# Bildirim için (opsiyonel)
WEBHOOK_URL="${N8N_BACKUP_WEBHOOK:-}"
log() {
echo "[$(date '+%Y-%m-%d %H:%M:%S')] $*" | tee -a "$LOG_FILE"
}
# Backup dizini oluştur
mkdir -p "$BACKUP_DIR"
log "n8n backup başlıyor: $BACKUP_DIR"
# Workflow'ları dışa aktar
if docker exec "$N8N_CONTAINER" n8n export:workflow --all
--output=/home/node/.n8n/backups/; then
docker cp "${N8N_CONTAINER}:/home/node/.n8n/backups/"
"${BACKUP_DIR}/workflows/"
log "Workflow'lar başarıyla dışa aktarıldı"
else
log "HATA: Workflow export başarısız!"
exit 1
fi
# SQLite veritabanını kopyala (eğer SQLite kullanıyorsan)
if docker exec "$N8N_CONTAINER" test -f /home/node/.n8n/database.sqlite; then
docker cp "${N8N_CONTAINER}:/home/node/.n8n/database.sqlite"
"${BACKUP_DIR}/database.sqlite"
log "SQLite veritabanı kopyalandı"
fi
# Encryption key'i yedekle
docker cp "${N8N_CONTAINER}:/home/node/.n8n/config"
"${BACKUP_DIR}/config" 2>/dev/null ||
log "Uyarı: Config dosyası kopyalanamadı, encryption key kontrol et"
# Arşivle ve şifrele
ARCHIVE_FILE="${BACKUP_ROOT}/n8n-backup-${BACKUP_DATE}.tar.gz.enc"
tar -czf - -C "$BACKUP_ROOT" "$BACKUP_DATE" |
openssl enc -aes-256-cbc -pbkdf2
-pass env:BACKUP_ENCRYPTION_KEY
-out "$ARCHIVE_FILE"
# Ham dizini temizle (şifreli arşiv kaldı)
rm -rf "$BACKUP_DIR"
log "Şifreli arşiv oluşturuldu: $ARCHIVE_FILE"
# Eski backup'ları temizle
find "$BACKUP_ROOT" -name "n8n-backup-*.tar.gz.enc"
-mtime +$RETENTION_DAYS -delete
log "${RETENTION_DAYS} günden eski backup'lar temizlendi"
# Boyut raporu
BACKUP_SIZE=$(du -sh "$ARCHIVE_FILE" | cut -f1)
log "Backup tamamlandı. Boyut: $BACKUP_SIZE"
# Başarı bildirimi gönder (n8n webhook varsa)
if [ -n "$WEBHOOK_URL" ]; then
curl -s -X POST "$WEBHOOK_URL"
-H "Content-Type: application/json"
-d "{"status": "success", "size": "${BACKUP_SIZE}",
"date": "${BACKUP_DATE}"}" || true
fi
Şimdi bunu çalıştırılabilir yap ve cron’a ekle:
chmod +x /opt/scripts/n8n-backup.sh
# Ortam değişkenlerini ayarla
echo "BACKUP_ENCRYPTION_KEY=cok-gizli-bir-sifre-buraya" >> /etc/environment
# Crontab'a ekle - her gece 02:00'de
crontab -e
# 0 2 * * * BACKUP_ENCRYPTION_KEY=sifren /opt/scripts/n8n-backup.sh
PostgreSQL ile Backup
Eğer n8n’i PostgreSQL ile kullanıyorsan (ki production için kesinlikle kullanmalısın), backup stratejin farklı olacak:
#!/bin/bash
# PostgreSQL backup eklentisi
PG_HOST="${N8N_DB_HOST:-localhost}"
PG_PORT="${N8N_DB_PORT:-5432}"
PG_DB="${N8N_DB_DATABASE:-n8n}"
PG_USER="${N8N_DB_USER:-n8n}"
BACKUP_DIR="/opt/backups/n8n/db"
DATE=$(date +%Y%m%d_%H%M%S)
mkdir -p "$BACKUP_DIR"
# pg_dump ile yedekle
PGPASSWORD="$N8N_DB_PASSWORD" pg_dump
-h "$PG_HOST"
-p "$PG_PORT"
-U "$PG_USER"
-d "$PG_DB"
--format=custom
--compress=9
--file="${BACKUP_DIR}/n8n-db-${DATE}.dump"
echo "PostgreSQL backup tamamlandı: n8n-db-${DATE}.dump"
# Eski dump'ları temizle (14 günden eski)
find "$BACKUP_DIR" -name "n8n-db-*.dump" -mtime +14 -delete
Docker Compose ortamında PostgreSQL container’ına bağlanmak için:
# Docker Compose ile PostgreSQL backup
docker compose exec postgres pg_dump
-U n8n
-d n8n
--format=custom
--compress=9
> /opt/backups/n8n/n8n-db-$(date +%Y%m%d).dump
Workflow’ları Git ile Versiyonlama
Bu benim favori yaklaşımım. Workflow’ları JSON olarak dışa aktarıp Git reposuna commit etmek, hem backup sağlıyor hem de versiyon geçmişini tutuyor. Bir workflow’da ne zaman ne değiştiğini görebilmek çok değerli.
#!/bin/bash
# /opt/scripts/n8n-git-sync.sh
# Workflow'ları Git reposuna senkronize eder
REPO_DIR="/opt/n8n-workflows-repo"
N8N_CONTAINER="n8n"
GIT_USER="n8n-backup-bot"
GIT_EMAIL="[email protected]"
# Repo yoksa klonla
if [ ! -d "$REPO_DIR/.git" ]; then
git clone [email protected]:ops/n8n-workflows.git "$REPO_DIR"
fi
# n8n'den güncel workflow'ları çek
docker exec "$N8N_CONTAINER" n8n export:workflow --all
--output=/home/node/.n8n/git-export/
docker cp "${N8N_CONTAINER}:/home/node/.n8n/git-export/"
"${REPO_DIR}/workflows/"
cd "$REPO_DIR"
# Git config
git config user.name "$GIT_USER"
git config user.email "$GIT_EMAIL"
# Değişiklikleri kontrol et
if git diff --quiet && git diff --staged --quiet; then
echo "Değişiklik yok, commit atlanıyor"
exit 0
fi
# Commit ve push
git add -A
git commit -m "Auto-backup: $(date '+%Y-%m-%d %H:%M:%S')"
git push origin main
echo "Workflow'lar Git'e push edildi"
n8n’in [Community Edition] 1.x sürümünden itibaren gelen Source Control özelliği de bunu kutudan çıkar çıkmaz yapabiliyorsun. Ama bu özellik Enterprise lisansında daha gelişmiş, Community’de temel seviyede kalıyor. Script yaklaşımı daha fazla esneklik veriyor.
Backup’tan Geri Yükleme
Backup almak güzel, ama geri yüklemeyi test etmeden backup almak eksik. En az üç ayda bir disaster recovery tatbikatı yapılması gerekiyor.
# Şifreli arşivi çöz ve aç
openssl enc -d -aes-256-cbc -pbkdf2
-pass env:BACKUP_ENCRYPTION_KEY
-in n8n-backup-20240115_020000.tar.gz.enc |
tar -xzf - -C /tmp/n8n-restore/
# Workflow'ları içe aktar
docker exec -it n8n_container n8n import:workflow
--input=/home/node/.n8n/restore/workflows/
# Tüm workflow'ları içe aktar (üzerine yazar)
docker exec n8n_container n8n import:workflow
--separate
--input=/home/node/.n8n/restore/workflows/
# Credentials'ları içe aktar
docker exec n8n_container n8n import:credentials
--input=/home/node/.n8n/restore/credentials/
PostgreSQL’den geri yükleme:
# Dump'tan geri yükle
PGPASSWORD="$N8N_DB_PASSWORD" pg_restore
-h localhost
-p 5432
-U n8n
-d n8n
--clean
--if-exists
/opt/backups/n8n/db/n8n-db-20240115.dump
# Container yeniden başlat
docker compose restart n8n
Geri yükleme sonrası her zaman şunu kontrol et: workflow’ların aktif/pasif durumu, credential bağlantıları ve bir kaç test execution. Credential’lar içe aktarıldığında doğru encryption key olmadan şifresi çözülemiyor, bu yüzden .n8n/config dosyasını da mutlaka yedeklemen kritik.
Uzak Depolama’ya Gönderme
Yerel backup yeterli değil. Sunucu yanarsa lokal backup işe yaramıyor. S3 veya benzeri bir nesne depolama alanına göndermek şart:
#!/bin/bash
# AWS S3'e backup gönder
# rclone veya aws-cli kullanabilirsin
BACKUP_FILE="$1"
S3_BUCKET="s3://sirketim-n8n-backups"
DATE_PATH=$(date +%Y/%m/%d)
# aws-cli ile
aws s3 cp "$BACKUP_FILE"
"${S3_BUCKET}/${DATE_PATH}/$(basename $BACKUP_FILE)"
--storage-class STANDARD_IA
--sse AES256
# rclone ile (Backblaze B2, MinIO, Google Cloud Storage için de çalışır)
rclone copy "$BACKUP_FILE"
"remote:n8n-backups/${DATE_PATH}/"
--progress
# Başarılı mı kontrol et
if [ $? -eq 0 ]; then
echo "Backup uzak depolamaya başarıyla gönderildi"
# Yerel dosyayı sil (opsiyonel, disk alanı için)
# rm "$BACKUP_FILE"
else
echo "HATA: Uzak depolamaya gönderim başarısız!"
exit 1
fi
n8n’in Kendi Workflow’u ile Backup
n8n’i backup almak için yine n8n kullanabilirsin. Bu biraz inception gibi ama çalışıyor. Bir “Maintenance” workflow’u oluşturun, Schedule trigger ile her gece çalışsın, Execute Command node’u ile export komutunu çalıştırsın, HTTP Request node’u ile Telegram veya Slack’e bildirim göndersin.
Tek dezavantajı: n8n kendisi çöktüğünde bu backup workflow’u da çalışmıyor. Bu yüzden harici bir cron job ile kombine kullanmak en sağlıklısı. n8n workflow’u birincil, sistem cron’u fallback olarak kurgula.
İzleme ve Alarm
Backup’ın başarıyla çalıştığını doğrulamak için basit bir monitoring eklemek iyi fikir:
#!/bin/bash
# Backup yaşını kontrol et ve alarm ver
BACKUP_DIR="/opt/backups/n8n"
MAX_AGE_HOURS=25 # 24 saatten yeni backup olmalı
ALERT_EMAIL="[email protected]"
# En son backup dosyasını bul
LATEST_BACKUP=$(find "$BACKUP_DIR" -name "n8n-backup-*.tar.gz.enc"
-printf '%T@ %pn' | sort -n | tail -1 | awk '{print $2}')
if [ -z "$LATEST_BACKUP" ]; then
echo "KRITIK: Hiç backup bulunamadi!" |
mail -s "[ALARM] n8n Backup Yok" "$ALERT_EMAIL"
exit 1
fi
# Dosya yaşını hesapla (saat cinsinden)
FILE_AGE_HOURS=$(( ($(date +%s) - $(stat -c %Y "$LATEST_BACKUP")) / 3600 ))
if [ "$FILE_AGE_HOURS" -gt "$MAX_AGE_HOURS" ]; then
echo "UYARI: Son n8n backup ${FILE_AGE_HOURS} saat önce alınmış!" |
mail -s "[ALARM] n8n Backup Eski" "$ALERT_EMAIL"
exit 1
fi
echo "OK: Son backup ${FILE_AGE_HOURS} saat önce alınmış: $LATEST_BACKUP"
Bu scripti ayrı bir cron job olarak koy, her gün öğlen 12’de çalışsın. Gece 02:00’de backup alınıyorsa 10 saat geçmiş olur, eğer backup hiç çalışmamışsa alarm verir.
Pratik Kontrol Listesi
Bir production n8n kurulumu için şu unsurları mutlaka ele alman gerekiyor:
- Günlük otomatik export: Tüm workflow’lar JSON olarak dışa aktarılıyor mu?
- Veritabanı yedekleme: SQLite için dosya kopyası, PostgreSQL için pg_dump çalışıyor mu?
- Encryption key yedegi:
.n8n/configdosyası güvenli yerde saklanıyor mu? - Şifreli arşiv: Backup dosyaları şifrelendi mi?
- Uzak depolama: Backup’lar farklı lokasyona gönderiliyor mu?
- Geri yükleme testi: En son ne zaman test restore yaptın?
- Backup yaşı izleme: Alarm mekanizması kurulu mu?
- Git versiyonlama: Workflow değişikliklerini takip edebiliyor musun?
Sonuç
n8n backup konusu çoğu zaman “sonra yaparım” kategorisine giriyor. Ama production’da workflow’larını kaybettiğinde veya yanlışlıkla bir şeyleri silip geri almak istediğinde, bu yazıya geri döneceksin ve keşke daha önce kurmuş olsaydım diyeceksin.
Minimum geçerli backup stratejisi şu üç şeyi içermeli: günlük otomatik workflow export, şifreli arşiv olarak uzak depolamaya gönderim ve üç ayda bir geri yükleme testi. Buna Git entegrasyonunu ekleyebilirsen workflow geçmişini de kazanmış olursun, bu özellikle birden fazla kişinin aynı instance’ı kullandığı ortamlarda çok değerli.
Encryption key’e özellikle dikkat et. Bütün workflow’larını yedekledin ama key’i yedeklemediysen credential’larını geri alamazsın. Bu dosyayı bir password manager’a veya şifreli bir vault’a atmayı unutma.
