Mikro servis mimarileri modern yazılım geliştirmeyi hâlâ domine ederken, tekil servis yaşam döngülerinin yönetiminin karmaşıklığı katlanarak artıyor. Pek çok ekip orkestrasyon için Kubernetes'e yönelse de, endüstrinin önemli bir kısmı hâlâ sanal makineler, PaaS hizmetleri (AWS Elastic Beanstalk veya Heroku gibi) veya fiziksel sunucular gibi daha basit dağıtım hedeflerine güveniyor. Bu ortamlar için CI/CD hattı yalnızca derlemeleri otomatikleştirmekle kalmamalı, aynı zamanda dağıtım mantığını, ortam yapılandırmasını ve geri alma stratejilerini de hassasiyetle yönetmelidir.
GitHub Actions, sürekli entegrasyon ve sürekli teslimat (CI/CD) için güçlü, kod odaklı bir yaklaşım sunar. Bu yazıda, modülerlik, güvenlik ve güvenilirliğe odaklanarak Kubernetes dışı mikro servisler için sağlam bir hat nasıl oluşturulacağını keşfedeceğiz.
Modüler Hattın Felsefesi
Geliştiricilerin yaptığı en yaygın hatalardan biri, dağıtım sürecinin her adımını tek bir monolitik YAML dosyasına sabit kodlamaktır. Bir mikro servis mimarisi için bu yaklaşım hızla yönetilemez hale gelir. Bunun yerine, GitHub Actions iş akışlarını bileşen birimler olarak ele almalıyız.
Kullanılabilir iş akışlarından ve ortam bazlı yapılandırmadan yararlanarak, derleme mantığımız için tek bir gerçeklik kaynağı korurken dağıtım hedeflerinin değişmesine izin verebiliriz. Bu, altyapı olarak kod (infrastructure-as-code) farklı servisler arasında farklı şekilde yönetildiğinde (örneğin bazıları Terraform, diğerleri basit kabuk betikleri kullanırken) özellikle kritik öneme sahiptir.
Hattın Temel Bileşenleri
Kubernetes dışı servisler için sağlam bir hat genellikle üç ayrı aşamadan oluşur: Derleme, Test ve Dağıtım. Bu aşamaları verimli bir şekilde kapsayan bir GitHub Actions iş akışının nasıl yapılandırılacağına bakalım.
1. Derleme ve Test Aşaması
Herhangi bir CI/CD hattının temeli hız ve güvenilirliktir. Testler bozulursa hızlıca başarısız olmayı (fail fast) hedeflemeliyiz. GitHub Actions kullanarak test yürütmesini paralelleştirebilir ve geri bildirim döngülerini azaltabiliriz.
Bağımlılık kurulumunu, kod incelemesini (linting) ve birim testlerini yöneten bir iş akışı örneği burada verilmiştir:
name: Build and Test
on:
pull_request:
branches: [ main ]
push:
branches: [ main ]
jobs:
build:
runs-on: ubuntu-latest
strategy:
matrix:
node-version: [18.x, 20.x]
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Set up Node.js ${{ matrix.node-version }}
uses: actions/setup-node@v4
with:
node-version: ${{ matrix.node-version }}
cache: 'npm'
- name: Install dependencies
run: npm ci
- name: Run linter
run: npm run lint
- name: Run unit tests
run: npm test -- --coverage
2. Tutarlılık İçin Konteynerleştirme
Kubernetes kullanmıyor olsanız bile, konteynerleştirme geliştirme, önizleme ve üretim ortamları arasındaki tutarlılığı sağlamak için altın standart olmaya devam etmektedir. Docker kullanmak, mikro servisinizin altta yanan ana işletim sisteminden bağımsız olarak öngörülebilir şekilde çalışmasını sağlar.
Docker derleme ve yükleme işlemlerini doğrudan hatta entegre edebiliriz. Bu, dağıtılan aracın (artifact) tüm testlerden geçtiği ile aynı olduğundan emin olmasını sağlar.
- name: Build and Push Docker Image
uses: docker/build-push-action@v5
with:
context: .
push: true
tags: ghcr.io/${{ github.repository }}:${{ github.sha }}
3. Ortam Bazlı Dağıtım
Kubernetes dışı servislerde dağıtım genellikle bir sunucuya SSH ile bağlanmayı veya bir PaaS sağlayıcısının API'sini çağırmayı içerir. Güvenlik burada hayati önem taşır. Kimlik bilgilerini asla sabit kodlamamalıyız. Bunun yerine GitHub Secrets'i ortam koruma kurallarıyla birlikte kullanmalıyız.
SSH aracılığıyla bir Linux sunucusuna dağıtım yaptığımızı varsayalım. Dağıtım betiklerini yürütmek için `appleboy/ssh-action` kullanabiliriz.
deploy-staging:
needs: build
runs-on: ubuntu-latest
environment: staging
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Deploy to Staging Server
uses: appleboy/ssh-action@v1
with:
host: ${{ secrets.STAGING_HOST }}
username: ${{ secrets.SSH_USER }}
key: ${{ secrets.SSH_PRIVATE_KEY }}
script: |
cd /opt/my-service
docker pull ghcr.io/${{ github.repository }}:${{ github.sha }}
docker-compose up -d --no-deps my-service
# Perform health check
curl -f http://localhost:8080/health || exit 1
Dayanıklılık İçin En İyi Uygulamalar
- Tutarlılık (Idempotency): Dağıtım betiklerinizin yan etkiler olmadan birden fazla kez çalıştırılabilmesini sağlayın. Docker bunu kolaylaştırır ancak veritabanı geçişleri için uygulama düzeyinde tutarlılık hala gereklidir.
- Geri Alma Stratejisi: Kubernetes dışı ortamlarda geri alma işlemi manuel olabilir. Docker imajlarını anlamsal sürüm numaralarıyla etiketleyerek ve önceki sürümleri mevcut tutarak bunu otomatikleştirin. Bir sağlık kontrolü başarısız olursa, hat otomatik olarak bir geri alma iş akışını tetiklemelidir.
- Gizli Bilgi Yönetimi: SSH anahtarlarınızı ve API belirteçlerinizi düzenli olarak yenileyin. Üretim ortamına dağıtımları onaylayacak kişileri kısıtlamak için GitHub Ortamlarını kullanın.
Sonuç
Kubernetes dışı mikro servisler için CI/CD hatları oluşturmak bir zihniyet değişikliği gerektirir. Dağıtımları ve geri almaları yönetmek için orkestrasyon motoruna güvenmek yerine, sorumluluk tamamen hatta geçer. GitHub Actions'ın modüler yapısından, konteynerleştirmeden ve güvenli gizli bilgi yönetiminden yararlanarak, Kubernetes karşılıkları kadar sağlam ve ölçeklenebilir bir dağıtım sistemi oluşturabilirsiniz. Otomasyonu benimseyin, güvenliği önceliklendirin ve dağıtımlarınızı her zaman otomatik sağlık kontrolleriyle doğrulayın.