Production Deployment Rehberi + Claude Prompt
Muzibu'daki sarkilar dinlenirken kucuk parcalar halinde (segment) yukleniyor. Onceden bu parcalar 6 saniyeydi, simdi tum kalite seviyelerinde 4 saniye olarak standardize edildi.
Neden Onemli? 4 saniye segment, Apple HLS standardina uygun ve tum varyantlar arasinda tutarlilik sagliyor. Bu sayede adaptive bitrate (otomatik kalite gecisi) daha yumusak calisiyor.
Kod degisiklikleri yapilip cache temizlendikten sonra, yeni eklenen 83 sarki hala eski formatla uretildi:
Eski Format (Horizon eski kodu kullanmis)
Dogru Format (opcache temizlendikten sonra)
Cozum: curl -s -k https://domain.com/opcache-reset.php calistir. Horizon worker'lari yeni kodu gorecek. Production'da ADIM 1'deki opcache-reset adimini ATLAMA!
| # | Dosya | Degisiklik |
|---|---|---|
| 1 | ConvertToHLSJob.php |
FFmpeg'e -profile:a aac_low -ar 48000 -ac 2 eklendi |
| 2a | HLSService.php:125 |
$targetBitrate undefined bug fix |
| 2b | HLSService.php:158 |
buildFFmpegCommand() internal helper olarak isaretlendi |
| 3 | AddHlsVariantsCommand.php |
--re-encode-high flag'i eklendi (high'i 4sn ile yeniden olusturur) |
| 4 | ConvertSongToHLS.php |
Silindi (olu kod) |
| 5 | routes/web.php |
/stream/key/ eski route kaldirildi |
| 6 | hls-streaming.blade.php |
Dokumantasyon guncellendi |
storage/tenant{id}/app/public/muzibu/hls/{song_id}/
├── enc.bin ← 16 byte AES-128 key (binary)
├── enc.keyinfo ← 3 satir: URI + path + IV
├── master.m3u8 ← 4 varyant referansi
├── playlist.m3u8 ← high kalite (4sn, VOD, encrypted)
├── segment-*.ts ← high segment'ler
├── ultralow/ ← 32kbps, mono, 22050Hz
├── low/ ← 64kbps, mono, 22050Hz
└── mid/ ← 128kbps, stereo, 44100Hz
storage/tenant{id}/app/public/muzibu/songs/mp3_128/
└── {song_id}.mp3 ← 128kbps MP3 fallback
Ana sunucuda adim adim yapilacaklar. Sirasini BOZMA!
cd /var/www/vhosts/muzibu.com/httpdocs
# Kodu cek
git pull origin main
# Cache temizle (route degisti, eski /stream/key/ kaldirildi)
php artisan cache:clear
php artisan route:clear
php artisan config:clear
php artisan view:clear
composer dump-autoload
# KRITIK: OPcache temizle (yoksa Horizon eski kodu calistirir!)
curl -s -k https://muzibu.com/opcache-reset.php
# Route ve config yeniden cache'le
php artisan config:cache
php artisan route:cache
KRITIK UYARI: opcache-reset.php MUTLAKA calistirilmali! mztest'te bu adim atlaninca Horizon eski ConvertToHLSJob kodunu kullanmaya devam etti ve yeni eklenen 83 sarki 10sn segment + VOD'suz + varyant'siz olarak uretildi. Opcache temizlenmezse ayni hata production'da da olur.
Neden? PHP OPcache, dosya degisse bile eski bytecode'u RAM'de tutar. Horizon worker'lari surekli calisan process'ler oldugu icin yeni kodu ancak opcache temizlenince gorur.
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" \
--option="mp3-128=1" \
--option="refresh-master=1" \
--option="re-encode-high=1" \
--option="dry-run=1"
Beklenen cikti: "Toplam HLS: ~30000, Islenecek: ~30000". Hicbir dosyaya dokunmaz, sadece sayar.
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" \
--option="mp3-128=1" \
--option="refresh-master=1" \
--option="re-encode-high=1" \
--option="limit=10"
Beklenen: "10 basarili, 0 basarisiz". ~3-5 dakika surer.
HLS_BASE="storage/tenant1001/app/public/muzibu/hls"
# Ilk 10 sarkinin hepsini kontrol et
GOOD=0; BAD=0; COUNT=0
for DIR in $(ls -d $HLS_BASE/*/ | head -10); do
[ ! -f "$DIR/master.m3u8" ] && continue
COUNT=$((COUNT + 1))
# Segment suresi (4.xxx olmali, 6.xxx olmamali)
MAX=$(grep '#EXTINF:' "$DIR/playlist.m3u8" | sed 's/#EXTINF://' | sed 's/,.*//' | sort -rn | head -1)
INT=$(echo "$MAX" | cut -d. -f1)
# 4 varyant olmali
HAS_ALL=1
for V in ultralow low mid; do
[ ! -f "$DIR/$V/playlist.m3u8" ] && HAS_ALL=0
done
# VOD olmali
HAS_VOD=0
grep -q '#EXT-X-PLAYLIST-TYPE:VOD' "$DIR/playlist.m3u8" && HAS_VOD=1
if [ "$INT" -le 4 ] && [ "$HAS_ALL" -eq 1 ] && [ "$HAS_VOD" -eq 1 ]; then
GOOD=$((GOOD + 1))
else
BAD=$((BAD + 1))
echo "SORUN: $(basename $DIR) max=$MAX varyant=$HAS_ALL vod=$HAS_VOD"
fi
done
echo "Kontrol: $COUNT sarki, $GOOD OK, $BAD SORUNLU"
Beklenen: "10 OK, 0 SORUNLU". Sorun varsa DURMA, once analiz et.
3 ayri terminal ac. Her birinde farkli offset ile calistir. screen veya tmux kullan ki terminal kapansa da devam etsin!
TERMINAL 1 — Sarki 1 - 10.000
screen -S hls-batch1
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" \
--option="mp3-128=1" \
--option="refresh-master=1" \
--option="re-encode-high=1" \
--option="limit=10000" \
--option="offset=0"
TERMINAL 2 — Sarki 10.001 - 20.000
screen -S hls-batch2
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" \
--option="mp3-128=1" \
--option="refresh-master=1" \
--option="re-encode-high=1" \
--option="limit=10000" \
--option="offset=10000"
TERMINAL 3 — Sarki 20.001 - 30.000
screen -S hls-batch3
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" \
--option="mp3-128=1" \
--option="refresh-master=1" \
--option="re-encode-high=1" \
--option="limit=10000" \
--option="offset=20000"
Tahmini Sure: ~30K sarki x ~20sn/sarki = ~7 saat (3 paralel). mztest'te 66 sarki 22 dakikada bitti.
screen kullanimi: Ctrl+A D = ayir (arka planda calisir), screen -r hls-batch1 = geri baglan
HLS_BASE="storage/tenant1001/app/public/muzibu/hls"
echo "=== GENEL DURUM ==="
echo "Toplam HLS klasoru: $(ls -d $HLS_BASE/*/ 2>/dev/null | wc -l)"
echo "master.m3u8 olan: $(ls $HLS_BASE/*/master.m3u8 2>/dev/null | wc -l)"
echo "MP3 128k: $(ls storage/tenant1001/app/public/muzibu/songs/mp3_128/*.mp3 2>/dev/null | wc -l)"
echo ""
echo "=== RASTGELE 20 SARKI KONTROL ==="
GOOD=0; BAD=0
for DIR in $(ls -d $HLS_BASE/*/ | shuf | head -20); do
[ ! -f "$DIR/master.m3u8" ] && continue
MAX=$(grep '#EXTINF:' "$DIR/playlist.m3u8" | sed 's/#EXTINF://' | sed 's/,.*//' | sort -rn | head -1)
INT=$(echo "$MAX" | cut -d. -f1)
HAS_ALL=1
for V in ultralow low mid; do
[ ! -f "$DIR/$V/playlist.m3u8" ] && HAS_ALL=0
done
if [ "$INT" -le 4 ] && [ "$HAS_ALL" -eq 1 ]; then
GOOD=$((GOOD + 1))
else
BAD=$((BAD + 1))
echo "SORUN: $(basename $DIR)"
fi
done
echo "Sonuc: $GOOD OK, $BAD SORUNLU"
php artisan cache:clear
php artisan view:clear
php artisan responsecache:clear
| Kontrol | Beklenen | Nasil Kontrol? |
|---|---|---|
| High segment suresi | ~4.0xx sn | grep '#EXTINF:' playlist.m3u8 | head -3 |
| master.m3u8 varyant sayisi | 4 (ultralow + low + mid + original) | cat master.m3u8 |
| Varyant klasorleri | ultralow/ + low/ + mid/ mevcut | ls -d */ |
| enc.keyinfo URI | /hls-key/muzibu/songs/{id} | head -1 enc.keyinfo |
| Playlist tipi | #EXT-X-PLAYLIST-TYPE:VOD | grep PLAYLIST-TYPE playlist.m3u8 |
| MP3 128k dosyasi | mp3_128/{song_id}.mp3 mevcut | ls songs/mp3_128/ | wc -l |
| Durum | Ne Olur? | Risk |
|---|---|---|
| MP3 dosyasi yok | Atlar, failed sayar, devam eder |
Yok |
| HLS klasoru yok | Atlar | Yok |
| FFmpeg hata | Log'lar, failed sayar, devam eder |
Yok |
| enc.keyinfo yok | re-encode atlar, variant eklemeye devam | Yok |
| Zaten variant var | Atlar (uzerine yazmaz) | Yok |
| Disk dolu | FFmpeg hata verir, log'lanir, devam eder | Orta |
| Terminal kapanirsa | screen kullan! |
Orta |
| Islem ortasinda durur | Ayni komutu tekrar calistir, mevcut olanlari atlar | Yok |
En kotu senaryoda geri almak icin:
git checkout -- .--option="song=12345" ile belirli sarki test etAsagidaki prompt'u production sunucudaki Claude'a ver. Tum islemleri otomatik yapacak.
Muzibu HLS sisteminde 4-saniye standardizasyon yapildi. Test sunucusunda (mztest) 66 sarki basariyla tamamlandi. Simdi production sunucuda (~30K sarki) ayni islemi yapman gerekiyor.
## Ne Yapildi (mztest'te)?
1. ConvertToHLSJob.php: FFmpeg'e -profile:a aac_low -ar 48000 -ac 2 eklendi
2. HLSService.php: $targetBitrate undefined bug fix
3. AddHlsVariantsCommand.php: --re-encode-high flag'i eklendi
4. ConvertSongToHLS.php silindi (olu kod)
5. /stream/key/ eski route kaldirildi
6. hls-streaming.blade.php dokumantasyonu guncellendi
## Senin Yapacaklarin (SIRAYLA!)
### 1. Kodu cek + opcache temizle
```bash
cd /var/www/vhosts/muzibu.com/httpdocs
git pull origin main
# Cache temizle
php artisan cache:clear && php artisan route:clear && php artisan config:clear && php artisan view:clear
composer dump-autoload
# KRITIK: OPcache temizle (Horizon eski kodu calistirmasin!)
curl -s -k https://muzibu.com/opcache-reset.php
# Route ve config yeniden cache'le
php artisan config:cache && php artisan route:cache
```
UYARI: opcache-reset ATLANIRSA Horizon eski kodu kullanmaya devam eder ve yeni sarkilar 10sn segment ile uretilir!
### 2. Dry-run (sadece say, hicbir seye dokunma)
```bash
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" \
--option="mp3-128=1" \
--option="refresh-master=1" \
--option="re-encode-high=1" \
--option="dry-run=1"
```
Beklenen: "Toplam HLS: ~30000, Islenecek: ~30000"
### 3. 10 sarki ile test
```bash
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" \
--option="mp3-128=1" \
--option="refresh-master=1" \
--option="re-encode-high=1" \
--option="limit=10"
```
Beklenen: "10 basarili, 0 basarisiz" (~3-5 dk)
### 4. Test sonucunu dogrula
Ilk 10 sarkiyi kontrol et:
- playlist.m3u8'deki #EXTINF degerleri ~4.0xx olmali (6.xxx OLMAMALI)
- master.m3u8'de 4 varyant olmali (ultralow + low + mid + original)
- enc.keyinfo URI /hls-key/ ile baslamali
- VOD tipi olmali
- Sorun varsa DURMA, analiz et
### 5. Tam re-encode (3 paralel terminal, screen kullan!)
```bash
# Terminal 1
screen -S hls-batch1
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" --option="mp3-128=1" \
--option="refresh-master=1" --option="re-encode-high=1" \
--option="limit=10000" --option="offset=0"
# Terminal 2
screen -S hls-batch2
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" --option="mp3-128=1" \
--option="refresh-master=1" --option="re-encode-high=1" \
--option="limit=10000" --option="offset=10000"
# Terminal 3
screen -S hls-batch3
php artisan tenants:run hls:add-variants --tenants=1001 \
--option="quality=all" --option="mp3-128=1" \
--option="refresh-master=1" --option="re-encode-high=1" \
--option="limit=10000" --option="offset=20000"
```
Tahmini sure: ~7 saat (3 paralel). screen -r hls-batch1 ile takip et.
### 6. Tamamlaninca dogrulama
Rastgele 20 sarki kontrol et:
- High segment suresi 4sn mi?
- 4 varyant var mi?
- enc.keyinfo URI dogru mu?
- MP3 128k var mi?
Sonucu bana raporla.
### 7. Final cache temizligi
```bash
php artisan cache:clear && php artisan view:clear && php artisan responsecache:clear
```
## ONEMLI NOTLAR
- OPCACHE-RESET MUTLAKA CALISTIR! (Adim 1) Yoksa Horizon eski kodu kullanir
- Orijinal MP3'ler HICBIR ZAMAN silinmez/degistirilmez
- Hata olursa komut durmaz, sayar ve devam eder
- Islem ortasinda kesilirse, ayni komutu tekrar calistir (mevcut olanlari atlar)
- screen kullan ki terminal kapansa da islem devam etsin
- SERVIS RESTART YAPMA (apache, nginx, redis vs.)
- Migration YOK, sadece dosya islemi
- Re-encode sirasinda sarkilar calismaya devam eder
- Yeni eklenen sarkilar da otomatik dogru formatla uretilir (opcache temiz olduktan sonra)
149 sarki (66 eski + 83 yeni), 0 hata
| Kontrol | Sonuc |
|---|---|
| High segment suresi | 149/149 = 4sn |
| 6sn eski segment | 0 (tamamen temizlendi) |
| master.m3u8 (4 varyant) | 149/149 |
| enc.keyinfo URI (/hls-key/) | 149/149 |
| VOD tipi | 149/149 |
| MP3 128k | 66 |
| Basarisiz | 0 |
php artisan tenants:run hls:add-variants --tenants=1001
Secenekler:
--option="quality=all" Tum varyantlar (ultralow + low + mid)
--option="quality=low" Sadece low varyant
--option="mp3-128=1" 128kbps MP3 de uret
--option="refresh-master=1" master.m3u8'i yeniden olustur
--option="re-encode-high=1" High playlist'i 4sn segment ile yeniden olustur
--option="song=123" Belirli bir sarki ID
--option="limit=100" Maksimum islenecek sarki
--option="offset=0" Atlanacak sarki (paralel batch icin)
--option="dry-run=1" Sadece sayilari goster, islem yapma