Skip to content

Commit

Permalink
Add example images
Browse files Browse the repository at this point in the history
  • Loading branch information
Sean-Der committed Aug 23, 2024
1 parent b2af40b commit bd837fb
Show file tree
Hide file tree
Showing 5 changed files with 89 additions and 16 deletions.
Binary file added .github/img/consoleOutput.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added .github/img/outputPage.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added .github/img/streamSettings.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
61 changes: 57 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,21 @@
[![Discord][discord-image]][discord-invite-url]

- [What is OBS Into Discord](#what-is-obs-into-discord)
- [Building](#building)
- [Setup](#setup)
- [Using](#using)
- [TODO](#todo)
- [More](#more)

## What is OBS Into Discord

This project allows you to send video from OBS directly into Discord.
The video is not transcoded or modified in any way. You should see
little to no CPU usage and latency should be minimal.
The video is not transcoded or modified in any way. What you send is
then sent directly to discord.

As a user this gives you
* Higher quality video. Tune your encoding settings!
* Better platform support. Get audio for Linux screenshares.
* More customization. Custom layouts/capture multiple windows....

This projects accepts WebRTC (WHIP) clients using [werift-webrtc](https://github.com/shinyoshiaki/werift-webrtc). It then bridges this
into Discord using [dank074/Discord-video-stream](https://github.com/dank074/Discord-video-stream). This project also supports more then
Expand All @@ -25,14 +30,62 @@ just OBS. You can also use any client that support WHIP.
* [Web Browser](https://github.com/Eyevinn/whip)


## Building
## Setup

### Download

`git clone https://github.com/Sean-Der/obs-into-discord.git`

### Install Dependencies

`cd obs-into-discord && npm install`

### Set `userToken` in `config.json`

Getting the `userToken` is the hardest step. I found these guides the most useful

* https://gist.github.com/MarvNC/e601f3603df22f36ebd3102c501116c6
* https://www.geeksforgeeks.org/how-to-get-discord-token/

### Set `serverIdNumber` and `channelIdNumber`

Follow the official documentation [here](https://support.discord.com/hc/en-us/articles/206346498-Where-can-I-find-my-User-Server-Message-ID)

### Change `httpPort` if 4321 isn't available

In most cases you will not to change this. Only ff port 4321 is already used by another service.

## Using

Run `node index.js`. If it starts without errors you have configured everything correctly. You now have a WHIP -> Discord bridge
running on port 4321. Publish from OBS via WHIP to `http://localhost:4321`. Currently you can do any streamKey (this may change in the future)

![OBS Stream settings example](./.github/img/streamSettings.png)

The following encoding settings are recommended. You can try tuning these, but may
see inconsistent playbcak behavior

![OBS Output settings example](./.github/img/outputPage.png)

If everything worked you should see the following output in the console.

![Console output](./.github/img/consoleOutput.png)

## TODO

* [ ] Allow configuration via Web UI
* [ ] Creater Docker Image
* [ ] Upload to Dockerhub
* [ ] Create [executable](https://nodejs.org/api/single-executable-applications.html) for easier install
* [ ] Support H265
* [ ] Support AV1
* [ ] Lower Latency

## More

For self hosting see [Broadcast Box](https://github.com/glimesh/broadcast-box). With Broadcast Box you can broadcast
with 150Ms of latency and push any video quality you want. No bitrate or codec restrictions!

[Join the Discord][discord-invite-url] and we are ready to help!

[license-image]: https://img.shields.io/badge/License-MIT-yellow.svg
Expand Down
44 changes: 32 additions & 12 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,18 +4,35 @@ const { RTCPeerConnection, RTCRtpCodecParameters, H264RtpPayload } = require('we
const { Client } = require('discord.js-selfbot-v13')
const { Streamer, H264NalSplitter } = require('@dank074/discord-video-stream')

const redText = '\x1b[31m'
const greenText = '\x1b[32m'

const config = require('./config.json')
checkConfig()

http.createServer(async (req, res) => {
if (req.method !== 'POST') {
res.end()
return
return res.end()
}

console.log(`${greenText}New WHIP Session`)

const streamer = new Streamer(new Client())
await streamer.client.login(config.userToken)
await streamer.joinVoice(config.serverIdNumber, config.channelIdNumber, {})

try {
await streamer.client.login(config.userToken)
} catch (err) {
console.log(`${redText}Failed to login, check userToken: ${err.toString()}`)
return res.end()
}

try {
await streamer.joinVoice(config.serverIdNumber, config.channelIdNumber, {})
} catch (err) {
console.log(`${redText}Failed to joinVoice, check serverIdNumber and channelIdNumber: ${err.toString()}`)
return res.end()
}

const udp = await streamer.createStream({})

udp.mediaConnection.setSpeaking(true)
Expand All @@ -29,6 +46,8 @@ http.createServer(async (req, res) => {
let h264Res = new H264RtpPayload()
handleWHIPRequest(req, res,
connectionState => {
console.log(`${greenText}WHIP Session state change ${connectionState}`)

if (connectionState === 'disconnected') {
streamer.stopStream()
streamer.leaveVoice()
Expand All @@ -43,7 +62,11 @@ http.createServer(async (req, res) => {
nalSplitter._transform(h264Res.payload, null, () => {})
}
})
}).listen(config.httpPort)
})
.on('error', err => {
console.log(`${redText}Failed to start HTTP server: ${err.toString()}`)
})
.listen(config.httpPort)

function handleWHIPRequest (req, res, onConnectionState, onAudio, onVideo) {
let body = ''
Expand Down Expand Up @@ -120,21 +143,18 @@ function handleWHIPRequest (req, res, onConnectionState, onAudio, onVideo) {
}

function checkConfig () {
const redText = '\x1b[31m'
const resetText = '\x1b[0m'

const startupErrors = []
if (config.userToken === '') {
startupErrors.push(redText + 'Config is missing userToken' + resetText)
startupErrors.push(`${redText}Config is missing userToken`)
}
if (config.serverIdNumber === '') {
startupErrors.push(redText + 'Config is missing serverIdNumber' + resetText)
startupErrors.push(`${redText}Config is missing serverIdNumber`)
}
if (config.channelIdNumber === '') {
startupErrors.push(redText + 'Config is missing channelIdNumber' + resetText)
startupErrors.push(`${redText}Config is missing channelIdNumber`)
}
if (!config.httpPort) {
startupErrors.push(redText + 'Config is missing httpPort' + resetText)
startupErrors.push(`${redText}Config is missing httpPort`)
}

startupErrors.forEach((e, i) => {
Expand Down

0 comments on commit bd837fb

Please sign in to comment.