v2 — B2B Odaklı Güncelleme

İşletmeler İçin
Akıllı Müzik Yönetimi

Muzibu = B2B müzik platformu. Her kullanıcı bir işletme sahibi. Sektör + Gün Dilimi + İşletme İhtiyacı odaklı dinamik içerik sistemi.

Soundtrack Your Brand modeli
Bireysel kullanıcı yok

v1'den Ne Değişti?

B2B kararının etkileri

Herkes İçin

v1'de "bireysel kullanıcı da olabilir" varsayımı vardı. Ama Muzibu sadece işletmelere hizmet veriyor. Bu demek oluyor ki: Her kullanıcının bir sektörü VAR, "kişisel müzik zevki" değil "işletmeye en uygun müzik" önemli. Spotify yerine Soundtrack Your Brand bizim asıl referansımız.

Kaldırılan / Değişen

Guest (giriş yapmamış) kullanıcı senaryosu
"Kişisel keşif" bölümü (Discover Weekly tarzı)
"Çünkü X dinledin" bireysel öneri mantığı
visibility_rules → auth_required kontrolü (herkes giriş yapmış)
Sektörsüz kullanıcı fallback'i

Eklenen / Güçlendirilen

Dayparting birincil özellik — her işletmenin gün boyu müzik takvimi
Sektör zorunlu — her kullanıcının sektörü var, filtre her zaman aktif
"İşletmeniz için" odağı — tüm dil ve UX iş odaklı
Çalışma saatleri entegrasyonu — işletme açılış/kapanış saati
Sektör sayfası feed — sektör detayında da dinamik koleksiyonlar

B2B Müzik Platformu Modeli

Muzibu kullanıcısı = İşletme sahibi

Herkes İçin

Muzibu'da kayıt olan herkes bir işletme sahibi. Kafe, restoran, gym, spa, otel veya mağaza çalıştırıyor. Bu kişiler kendi zevkleri için müzik aramıyor — müşterilerine en uygun ambiyansı arıyorlar. Sabah kafeyi açtığında sakin müzik, öğle pik saatinde enerjik müzik, akşam kapanışta ambient müzik istiyor. Biz bu geçişleri otomatik yapacağız.

Cafe / Restoran

Müşteri konforunu artırmak, oturma süresini uzatmak/kısaltmak

Ambiyans odaklı

Gym / Fitness

Motivasyon, enerji, performans artışı

Enerji odaklı

SPA / Otel / Mağaza

Rahatlama, lüks his, alışveriş deneyimi

Deneyim odaklı
Teknik Detay Soundtrack Your Brand vs Muzibu karşılaştırma
Özellik Soundtrack Muzibu (Hedef)
Hedef kitle Global B2B Türkiye B2B
Dayparting 6 dilim, manuel schedule 6 dilim, otomatik koleksiyonlar
Sektör sistemi Şablon bazlı Koleksiyon + sektör kuralları (daha esnek)
İçerik yönetimi 2000+ editör playlist Admin koleksiyonları + mevcut playlist/albüm/radyo
Multi-zone Var (bar, lobi, tuvalet) Şimdilik yok (gelecek faz)
AI Playlist LLM tabanlı generator Şimdilik yok (blog AI'dan adapte edilebilir)
Avantaj Büyük katalog Türk müziği + yerel sektör bilgisi + esneklik

Dayparting: İşletmenin Günlük Ritmi

B2B'nin kalbi — saate göre otomatik içerik

Herkes İçin

Dayparting = Günü dilimlerine bölmek. Bir kafe sabah açıldığında sakin müzik çalar, öğle yoğunluğunda biraz daha enerjik geçer, akşam kapanışta ambient'e döner. Biz bu geçişleri otomatik yapıyoruz. İşletme sahibi hiçbir şeye dokunmadan, siteye girdiğinde o ana uygun müzik koleksiyonlarını görüyor.

Bir Cafe'nin Günü

Sabah Açılış 06 - 09

Akustik, Ambient, Hafif Jazz

Kahve Saati 09 - 11:30

Bossa Nova, Indie Folk, Soft Pop

Öğle Pik 11:30 - 14

Upbeat Pop, Funk, Enerjik Listeler

Öğleden Sonra 14 - 17

Soul, Soft Rock, Chill

Akşam 17 - 21

Jazz, Lounge, Nu-Soul

Kapanış 21 - 06

Lo-fi, Ambient, Deep Chill

Teknik Detay Sektör x Daypart matrisi — her hücre = 1 koleksiyon
Sektör Açılış
06-09
Sabah
09-11:30
Öğle Pik
11:30-14
Öğle Sonra
14-17
Akşam
17-21
Gece
21-06
Cafe Akustik, Ambient Bossa Nova, Jazz Upbeat Pop Soul, Soft Rock Jazz Lounge Lo-fi, Ambient
Restoran Brunch Vibes Lunch Energy Afternoon Tea Fine Dining Romantic Night
Gym Warm-up Cardio Start Beast Mode Steady Workout Cool Down Late Night Gym
SPA Morning Zen Meditation Nature Sounds Deep Relax Massage Therapy Sleep Ambient
Otel Lobby Morning Pool Chill Restaurant Spa & Pool Bar Lounge Night Club
Mağaza Opening Vibes Shopping Pop Trendy Energy Boutique Chill Fashion Lounge

Bu matrisin her hücresi admin panelinden bir "koleksiyon" olarak oluşturulur. Toplam ~36 koleksiyon ile tüm sektörler x tüm zaman dilimleri kaplanır. "—" olan hücreler o sektör için o saatte koleksiyon gerekmediğini gösterir (genel koleksiyon düşer).

Veritabanı & Servis Mimarisi

B2B'ye göre sadeleştirilmiş

Veritabanı v1'den fark: visibility_rules sadeleşti (auth_required kaldırıldı, her zaman giriş yapmış)

muzibu_content_collections

collection_id    BIGINT PK AUTO
title            JSON          -- {"tr": "Sabah Enerjisi"}
slug             JSON
description      JSON
type             ENUM          -- curated, daypart, sector, featured

-- Görsel
icon             VARCHAR(50)   -- fas fa-coffee
color            VARCHAR(20)   -- #f59e0b
media_id         BIGINT NULL   -- Kapak görseli

-- Zaman Kuralları
display_rules    JSON
-- Sektör Kuralları
sector_rules     JSON
-- İş Kuralları (B2B odaklı)
business_rules   JSON          -- YENİ: abonelik, işletme boyutu

priority         INT DEFAULT 0
is_active        BOOLEAN
is_featured      BOOLEAN
cache_ttl        INT DEFAULT 300

created_at, updated_at, deleted_at

muzibu_collection_items

id               BIGINT PK AUTO
collection_id    BIGINT FK

-- Polymorphic
itemable_type    VARCHAR  -- Playlist, Album, Radio, Song
itemable_id      BIGINT

position         INT DEFAULT 0
is_active        BOOLEAN

created_at, updated_at
v1'den Fark
  • visibility_rulesbusiness_rules olarak yeniden adlandırıldı
  • auth_required, is_new_user kaldırıldı
  • subscription_types eklendi (trial, standard, premium, corporate)
display_rules
{
  "time_slots": [
    {"start": "06:00", "end": "09:00",
     "label": "Sabah Açılış"}
  ],
  "days": [1,2,3,4,5],
  "is_always": false
}
sector_rules
{
  "mode": "include",
  "sector_ids": [1, 3],
  "show_to_all": false
}

show_to_all: true = tüm sektörlere göster

business_rules YENİ
{
  "subscription": [
    "standard", "premium",
    "corporate"
  ],
  "min_months": 0
}

trial kullanıcılar bazı koleksiyonları göremez

SmartFeedService B2B mantık: Sektör her zaman var, guest yok
class SmartFeedService
{
    /**
     * İşletme sahibi için kişisel feed oluştur.
     * B2B: Kullanıcı HER ZAMAN giriş yapmış, HER ZAMAN sektörü var.
     */
    public function getFeed(User $user): array
    {
        $now = now();
        $sectorId = $user->primary_sector_id; // Zorunlu alan

        return Cache::remember(
            $this->cacheKey($user->id, $sectorId, $now),
            300,
            fn() => $this->buildFeed($user, $sectorId, $now)
        );
    }

    private function buildFeed(User $user, int $sectorId, Carbon $now): array
    {
        $feed = [];

        // 1. Selamlama
        $feed['greeting'] = $this->getGreeting($user, $now);

        // 2. Featured/Hero (varsa)
        $feed['featured'] = $this->getFeatured($sectorId, $now);

        // 3. Daypart koleksiyonu (saate göre)
        $feed['daypart'] = $this->getDaypartCollections($sectorId, $now);

        // 4. Sektör koleksiyonları (her zaman göster)
        $feed['sector'] = $this->getSectorCollections($sectorId, $now);

        // 5. Genel koleksiyonlar (tüm sektörler)
        $feed['general'] = $this->getGeneralCollections($now);

        return $feed;
    }

    private function getGreeting(User $user, Carbon $now): array
    {
        $hour = (int) $now->format('H');
        $name = $user->name;

        if ($hour >= 6 && $hour < 12)  $text = "Günaydın, {$name}";
        elseif ($hour < 18)            $text = "İyi Günler, {$name}";
        elseif ($hour < 22)            $text = "İyi Akşamlar, {$name}";
        else                           $text = "İyi Geceler, {$name}";

        return [
            'text' => $text,
            'daypart_label' => $this->getDaypartLabel($hour),
            'sector_name' => $user->sector->title,
        ];
    }

    private function getDaypartLabel(int $hour): string
    {
        return match(true) {
            $hour >= 6 && $hour < 9    => 'Sabah Açılış',
            $hour >= 9 && $hour < 12   => 'Sabah',
            $hour >= 12 && $hour < 14  => 'Öğle',
            $hour >= 14 && $hour < 17  => 'Öğleden Sonra',
            $hour >= 17 && $hour < 21  => 'Akşam',
            default                    => 'Gece',
        };
    }

    private function cacheKey($userId, $sectorId, $now): string
    {
        // 30dk blok: 07:00-07:29 = "0700", 07:30-07:59 = "0730"
        $block = $now->format('H') . ($now->minute < 30 ? '00' : '30');
        return "smart_feed:{$userId}:{$sectorId}:{$block}";
    }
}

UX Tasarım: İşletme Sahibi Ne Görür?

B2B odaklı sayfa yapısı

Herkes İçin

Dil ve ton tamamen iş odaklı. "Senin için" yerine "İşletmeniz için", "Keşfet" yerine "Sektörünüze Özel". İşletme sahibi giriş yaptığında hemen kendi sektörüne ve o anki saate uygun müzikleri görüyor.

Anasayfa Mockup — Pzt sabah 09:15, Cafe sektörü

Günaydın, Mehmet

Pazartesi • Cafe • Kahve Saati dilimi

Son çaldığınız: Cafe Jazz
Favorileriniz
Cafe Radyo
Yeni

Bahar Koleksiyonu Yayında!

Cafe'niz için özel seçilmiş 8 yeni playlist

Kahve Saati 09:00 - 11:30

Cafe'niz için şu an ideal müzikler

Tümü
Bossa Nova Cafe 48 şarkı • 2.5 saat
Morning Acoustic 35 şarkı • 2 saat
Indie Coffee Shop 42 şarkı • 2.8 saat
Soft Jazz 55 şarkı • 3 saat

Cafe'niz İçin Seçtiklerimiz

Sektörünüze özel, tüm gün için

Tümü
Cafe Klasikleri 120 şarkı
Retro Cafe 80 şarkı
World Music Cafe 65 şarkı
Lo-fi & Study 90 şarkı

Sırada: Öğle Pik 11:30'da başlayacak

Birazdan işletmenize uygun olacak listeler

Upbeat Pop 11:30'dan itibaren
Enerjik Cafe 11:30'dan itibaren

Tüm Sektörler İçin

Bu Haftanın Yenileri
En Popüler Radyolar
Mevsim Seçmeleri
Sayfa Bölüm Sırası (Yukarıdan aşağı)
1
Selamlama +
Hızlı Erişim
2
Featured
Hero Kart
3
Daypart
Şu anki dilim
4
Sektör
Koleksiyonları
5
Sıradaki
Zaman Dilimi
6
Genel
Koleksiyonlar

B2B Dil & Ton Rehberi

Durum Bireysel (KULLANMA) B2B (KULLAN)
Başlık "Senin İçin" "İşletmeniz İçin Seçtiklerimiz"
Daypart "Sabah Enerjisi" "Kahve Saati — Cafe'niz için ideal müzikler"
Keşif "Yeni müzikler keşfet" "Sektörünüze yeni eklenen listeler"
Sırada "Akşam için öneriler" "Sırada: Öğle Pik — 11:30'da başlayacak"
Boş durum "Henüz bir şey dinlemedin" "İşletmeniz için bir playlist seçin"

B2B Senaryoları

Farklı işletmeler, farklı saatler

Pazartesi 08:30 — Cafe

Mehmet, premium abonelik

"Günaydın, Mehmet" • Cafe • Sabah Açılış
Sabah Açılış: Akustik, Ambient Jazz, Morning Acoustic
Cafe İçin: Bossa Nova, Cafe Klasikleri, Retro Cafe
Sırada 09:00: Kahve Saati dilimi playlistleri
Genel: Bu Haftanın Yenileri, Mevsim Seçmeleri

Cuma 18:00 — Gym

Ayşe, standard abonelik

"İyi Akşamlar, Ayşe" • Gym • Akşam
Akşam: Cool Down, Yoga Flow, Stretching
Gym İçin: Beast Mode, Cardio Power, Running Beats
Sırada 21:00: Late Night Gym dilimi
Cuma Özel: Weekend Workout (Cuma-Pazar aktif)

Pazar 14:30 — SPA

Zeynep, corporate abonelik

"İyi Günler, Zeynep" • SPA • Öğleden Sonra
Öğleden Sonra: Deep Relax, Nature Sounds, Crystal Bowls
SPA İçin: Meditation, Massage Therapy, Zen Garden
Corporate Özel: Premium SPA Seçkisi (sadece corporate)
Hafta Sonu: Weekend Wellness koleksiyonu

Cumartesi 20:00 — Restoran

Ali, premium abonelik

"İyi Akşamlar, Ali" • Restoran • Akşam
Akşam: Fine Dining, Romantic Night, Wine & Dine
Restoran İçin: Italian Night, Gourmet Jazz, Piano Bar
Featured: Sevgililer Günü Koleksiyonu (kampanya)
C.tesi Özel: Weekend Dinner (Cmt-Paz aktif)

Uygulama Fazları (B2B Güncel)

4 faz, aynı yapı, B2B odaklı

F1

Veritabanı & Modeller

2 yeni tablo + 2 model

Temel
  • muzibu_content_collections migration (central + tenant)
  • muzibu_collection_items migration (central + tenant)
  • ContentCollection model (JSON cast, ilişkiler, scope'lar)
  • CollectionItem model (polymorphic morph map)
F2

SmartFeedService

B2B filtre motoru + cache + HomeController entegrasyonu

Akıl
  • SmartFeedService: zaman + sektör + abonelik filtresi
  • Greeting sistemi (saat + isim + sektör)
  • "Sıradaki dilim" özelliği
  • Cache: user:sector:30dk-blok key stratejisi
  • HomeController güncelleme
F3

Admin Panel (Livewire)

Koleksiyon CRUD + kural oluşturucu + sortable

Yönetim
  • Koleksiyon listesi (Tabler grid, aktif/pasif toggle)
  • 5 sekmeli form: Temel, Zaman, Sektör, İş Kuralları, İçerik
  • Saat/gün picker (görsel zaman dilimi seçici)
  • Sektör seçici (checkbox grid)
  • Sortable.js ile sürükle-bırak içerik seçimi
F4

Frontend & Blade

İşletme sahibinin gördüğü sayfa

Görsel
  • Selamlama + hızlı erişim grid
  • Featured hero kartı (kampanya)
  • Daypart koleksiyonu (şu anki + sıradaki)
  • Sektör koleksiyonları carousel
  • Genel koleksiyonlar
  • Sektör detay sayfasına entegrasyon

Sonraki Adım

B2B modeli netleşti. Onayınızla Faz 1'den (migration & modeller) başlayabiliriz. Her faz bağımsız çalışır ve test edilebilir. Migration için 3 aşamalı onay süreci uygulanacak.

Mevcut tablolara dokunulmuyor, risk düşük