UNPKG

janky

Version:

Janus Interface

111 lines (97 loc) 3.9 kB
import janus, { JanusJS } from "janus-gateway"; import RemoteFeeds from "../repositories/RemoteFeeds"; import { IncomingStreams } from "../types"; interface ReadyToSubscribeStreams { feed: string; mid: string; } class Subscriber { private userID: string = ''; private rfid: string = ''; private streams: IncomingStreams[] = []; constructor( private readonly roomID: number, private readonly handler: JanusJS.PluginHandle) {} public async subscribeToNewFeeds(id: number, streams?: IncomingStreams[]): Promise<JanusJS.PluginHandle> { if (!streams) { streams = RemoteFeeds.getUserFeed(id)[0]?.streams ?? undefined; } const streamsToSubscribeTo = this.prepareStreamsToSubscribe(streams); await this.sendJoinRequest(streamsToSubscribeTo); this.saveNewFeed(); return this.handler as JanusJS.PluginHandle; } private shouldSkipVideo(stream: IncomingStreams): boolean { // If the publisher is VP8/VP9 and this is an older Safari, let's avoid video if(stream.type === "video" && janus.webRTCAdapter.browserDetails.browser === "safari" && (stream.codec === "vp9" || (stream.codec === "vp8" && !janus.safariVp8))) { alert("Publisher is using " + stream.codec.toUpperCase + ", but Safari doesn't support it: disabling video stream #" + stream.mindex); return true; } return false; } private prepareStreamsToSubscribe(streams: IncomingStreams[] | undefined): ReadyToSubscribeStreams[] { this.streams = streams ?? []; const streamsToSubscribeTo = []; for (const stream of streams ?? []) { if (this.shouldSkipVideo(stream)) { continue; } streamsToSubscribeTo.push({ feed: stream.id, mid: stream.mid }); this.rfid = stream.id; this.userID = stream.display; } return streamsToSubscribeTo; } private sendJoinRequest(streamsToSubscribeTo: ReadyToSubscribeStreams[]): Promise<void> { return new Promise<void>((resolve, reject) => { const message = { request: "join", room: this.roomID, ptype: "subscriber", streams: streamsToSubscribeTo, use_msid: this.userID, private_id: parseInt(this.userID) }; this.handler?.send({ message, success: (data) => { if (data && data.error) { reject(data.error); } else { resolve(); } } }); }); } public doAnswer(jsep: JanusJS.JSEP) { this.handler.createAnswer( { jsep: jsep, // We only specify data channels here, as this way in // case they were offered we'll enable them. Since we // don't mention audio or video tracks, we autoaccept them // as recvonly (since we won't capture anything ourselves) success: (jsep) => { console.debug("Got SDP!", jsep); let body = { request: "start", room: this.roomID }; this.handler.send({ message: body, jsep: jsep }); }, error: (error) => { console.error("WebRTC error:", error); } } as JanusJS.PluginCreateAnswerParam); } private saveNewFeed() { RemoteFeeds.setFeed({ id: parseInt(this.rfid), userID: this.userID, handler: this.handler as JanusJS.PluginHandle, streams: this.streams, }); } }; export default Subscriber;