Live Stream Join Flow
Host, guest ve audience için canlı yayına katılma sırası
Live Stream Join Flow
Canlı yayına katılım üç ayrı client rolüyle düşünülmelidir: host, guest ve audience. HTTP join endpoint'i Agora RTC/RTM token'larını üretir; Socket.IO joinStream eventi ise yayın odası event'lerini ve viewer count güncellemelerini almak içindir.
Rol seçimi
| Kullanıcı | Endpoint | Rol |
|---|---|---|
| Yayını oluşturan kullanıcı | POST /api/v1/live-stream/join-as-creator | host |
| Yayına davet edilmiş guest | POST /api/v1/live-stream/join-as-guest | guest |
| Normal izleyici | POST /api/v1/live-stream/join | audience |
Creator veya guest kullanıcının POST /api/v1/live-stream/join endpoint'ine role=audience ile girmesine izin verilmez. Client rolü kullanıcı ilişkisinden belirlemeli ve doğru endpoint'i çağırmalıdır.
Genel sıra
- Yayın listesi veya detay endpoint'i ile
liveStreamIdalınır. - Kullanıcı rolüne göre HTTP join endpoint'i çağrılır.
- Response'taki
data.agoraile Agora RTC channel'a girilir. - Response'taki
data.rtmile Agora RTM login/channel join yapılır. /live-streamSocket.IO namespace'ine bağlanılır vejoinStreameventi gönderilir.- Ekran kapanırken
leaveStream, RTM leave/logout ve RTC leave sırasıyla çalıştırılır.
Audience join
POST /api/v1/live-stream/join
Authorization: Bearer <accessToken>
Content-Type: application/json
{
"liveStreamId": "65f000000000000000000001",
"role": "audience",
"deviceType": "iOS",
"appVersion": "1.4.2"
}Audience join sadece aktif yayınlarda beklenmelidir. Ücretli yayınlarda backend ilk ücreti join sırasında keser ve periyodik billing scheduler'ını başlatabilir. Yetersiz bakiye gibi durumlar 400 ile döner.
Creator join
POST /api/v1/live-stream/join-as-creator
Authorization: Bearer <accessToken>
Content-Type: application/json
{
"liveStreamId": "65f000000000000000000001"
}Creator join sadece yayını oluşturan kullanıcı için geçerlidir. Response içinde host rolüne uygun RTC token ve RTM token döner. POST /api/v1/live-stream/create canlı yayın kaydını oluşturur; Agora RTM token almak için creator ayrıca join-as-creator çağırmalıdır.
Guest join
POST /api/v1/live-stream/join-as-guest
Authorization: Bearer <accessToken>
Content-Type: application/json
{
"liveStreamId": "65f000000000000000000001"
}Guest join kullanıcının o yayına davet edilmiş olmasını gerektirir. DuoCrowd yayınlarda funding tamamlanmadan host/guest join bloklanabilir. Guest join bazı duo yayınlarda yayını active duruma taşıyabilir ve ilgili liveStreamStarted event'lerini tetikleyebilir.
Join response
{
"isSuccess": true,
"statusCode": 201,
"data": {
"liveStream": {
"_id": "65f000000000000000000001",
"status": "active"
},
"agora": {
"appId": "agora-app-id",
"channelName": "stream-channel",
"token": "rtc-token",
"uid": 123456,
"role": "audience",
"expiresAt": "2026-05-21T11:00:00.000Z"
},
"rtm": {
"appId": "agora-app-id",
"channelName": "stream-channel",
"userId": "65f000000000000000000abc",
"token": "rtm-token",
"expiresAt": "2026-05-21T11:00:00.000Z"
}
},
"errors": [],
"timestamp": "2026-05-21T10:00:00.000Z"
}Socket room'a katılma
const socket = io(`${SOCKET_BASE_URL}/live-stream`, {
transports: ["websocket"],
});
socket.emit("joinStream", { streamId: liveStreamId });
socket.on("joinedStream", (payload) => {
// payload.viewerCount
});Socket room'a girmek HTTP join yerine geçmez. Agora token almak, participant kaydı oluşturmak, paid stream ücretlendirmesini başlatmak ve ban kontrollerini çalıştırmak için HTTP join endpoint'i çağrılmalıdır.
Ayrılma ve cleanup
socket.emit("leaveStream", { streamId: liveStreamId });
await rtmChannel.leave();
await rtmClient.logout();
await rtcClient.leave();Client ekran kapanışı, app background ve bağlantı kaybı durumlarında cleanup'i idempotent yazmalıdır. Aynı leave işlemi birden fazla kez çağrılsa bile UI state bozulmamalıdır.