Merge pull request #43 from mbattista/add-turn-server
allow to add password protected turn server
This commit is contained in:
commit
4589f758c6
12
README.md
12
README.md
@ -41,6 +41,7 @@ For n.eko room management software visit https://github.com/m1k1o/neko-rooms.
|
||||
- Added `?usr=<display-name>` that will prefill username. This allows creating auto-join links.
|
||||
- Added `?cast=1` that will hide all control and show only video.
|
||||
- Shake keyboard icon if someone attempted to control when is nobody hosting.
|
||||
- Support for password protected `NEKO_ICESERVERS` (by @mbattista).
|
||||
|
||||
### Bugs
|
||||
- Fixed minor gst pipeline bug.
|
||||
@ -280,7 +281,16 @@ NEKO_CERT:
|
||||
NEKO_KEY:
|
||||
- Path to the SSL-Certificate private key
|
||||
- e.g. '/certs/key.pem'
|
||||
|
||||
NEKO_ICELITE:
|
||||
- Use the ice lite protocol
|
||||
- e.g. false
|
||||
NEKO_ICESERVER:
|
||||
- Describes a single STUN and TURN server that can be used by the ICEAgent to establish a connection with a peer (simple usage for server without authentication)
|
||||
- e.g. 'stun:stun.l.google.com:19302'
|
||||
NEKO_ICESERVERS:
|
||||
- Describes multiple STUN and TURN server that can be used by the ICEAgent to establish a connection with a peer
|
||||
- e.g. '[{"urls": ["turn:turn.example.com:19302", "stun:stun.example.com:19302"], "username": "name", "credential": "password"}, {"urls": ["stun:stun.example2.com:19302"]}]'
|
||||
- [More information](https://developer.mozilla.org/en-US/docs/Web/API/RTCIceServer)
|
||||
```
|
||||
|
||||
# How to contribute?
|
||||
|
@ -183,7 +183,7 @@ export abstract class BaseClient extends EventEmitter<BaseEvents> {
|
||||
this._ws!.send(JSON.stringify({ event, ...payload }))
|
||||
}
|
||||
|
||||
public createPeer(sdp: string, lite: boolean, servers: string[]) {
|
||||
public createPeer(sdp: string, lite: boolean, servers: RTCIceServer[]) {
|
||||
this.emit('debug', `creating peer`)
|
||||
if (!this.socketOpen) {
|
||||
this.emit(
|
||||
@ -202,7 +202,7 @@ export abstract class BaseClient extends EventEmitter<BaseEvents> {
|
||||
this._peer = new RTCPeerConnection()
|
||||
if (lite !== true) {
|
||||
this._peer = new RTCPeerConnection({
|
||||
iceServers: [{ urls: servers }],
|
||||
iceServers: servers,
|
||||
})
|
||||
}
|
||||
|
||||
|
@ -67,7 +67,7 @@ export interface SignalProvideMessage extends WebSocketMessage, SignalProvidePay
|
||||
export interface SignalProvidePayload {
|
||||
id: string
|
||||
lite: boolean
|
||||
ice: string[]
|
||||
ice: RTCIceServer[]
|
||||
sdp: string
|
||||
}
|
||||
|
||||
|
@ -127,7 +127,7 @@ func (session *Session) SignalCandidate(data string) error {
|
||||
return session.socket.Send(&message.SignalCandidate{
|
||||
Event: event.SIGNAL_CANDIDATE,
|
||||
Data: data,
|
||||
});
|
||||
})
|
||||
}
|
||||
|
||||
func (session *Session) destroy() error {
|
||||
|
@ -1,17 +1,20 @@
|
||||
package config
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
||||
"github.com/spf13/cobra"
|
||||
"github.com/spf13/viper"
|
||||
"n.eko.moe/neko/internal/utils"
|
||||
|
||||
"github.com/pion/webrtc/v3"
|
||||
)
|
||||
|
||||
type WebRTC struct {
|
||||
ICELite bool
|
||||
ICEServers []string
|
||||
ICEServers []webrtc.ICEServer
|
||||
EphemeralMin uint16
|
||||
EphemeralMax uint16
|
||||
NAT1To1IPs []string
|
||||
@ -38,13 +41,31 @@ func (WebRTC) Init(cmd *cobra.Command) error {
|
||||
return err
|
||||
}
|
||||
|
||||
cmd.PersistentFlags().String("iceservers", "", "describes a single STUN and TURN server that can be used by the ICEAgent to establish a connection with a peer")
|
||||
if err := viper.BindPFlag("iceservers", cmd.PersistentFlags().Lookup("iceservers")); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *WebRTC) Set() {
|
||||
s.ICELite = viper.GetBool("icelite")
|
||||
s.ICEServers = viper.GetStringSlice("iceserver")
|
||||
s.NAT1To1IPs = viper.GetStringSlice("nat1to1")
|
||||
s.ICELite = viper.GetBool("icelite")
|
||||
s.ICEServers = []webrtc.ICEServer{}
|
||||
|
||||
iceServersJson := viper.GetString("iceservers")
|
||||
if iceServersJson != "" {
|
||||
err := json.Unmarshal([]byte(iceServersJson), &s.ICEServers)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
}
|
||||
|
||||
iceServerSlice := viper.GetStringSlice("iceserver")
|
||||
if len(iceServerSlice) > 0 {
|
||||
s.ICEServers = append(s.ICEServers, webrtc.ICEServer{URLs: iceServerSlice})
|
||||
}
|
||||
|
||||
if len(s.NAT1To1IPs) == 0 {
|
||||
ip, err := utils.GetIP()
|
||||
|
@ -2,6 +2,8 @@ package message
|
||||
|
||||
import (
|
||||
"n.eko.moe/neko/internal/types"
|
||||
|
||||
"github.com/pion/webrtc/v3"
|
||||
)
|
||||
|
||||
type Message struct {
|
||||
@ -18,7 +20,7 @@ type SignalProvide struct {
|
||||
ID string `json:"id"`
|
||||
SDP string `json:"sdp"`
|
||||
Lite bool `json:"lite"`
|
||||
ICE []string `json:"ice"`
|
||||
ICE []webrtc.ICEServer `json:"ice"`
|
||||
}
|
||||
|
||||
type SignalAnswer struct {
|
||||
|
@ -2,6 +2,8 @@ package types
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"github.com/pion/webrtc/v3"
|
||||
)
|
||||
|
||||
type Sample struct {
|
||||
@ -13,7 +15,7 @@ type Sample struct {
|
||||
type WebRTCManager interface {
|
||||
Start()
|
||||
Shutdown() error
|
||||
CreatePeer(id string, session Session) (string, bool, []string, error)
|
||||
CreatePeer(id string, session Session) (string, bool, []webrtc.ICEServer, error)
|
||||
}
|
||||
|
||||
type Peer interface {
|
||||
|
@ -63,7 +63,7 @@ func (manager *WebRTCManager) Start() {
|
||||
|
||||
manager.logger.Info().
|
||||
Str("ice_lite", fmt.Sprintf("%t", manager.config.ICELite)).
|
||||
Str("ice_servers", strings.Join(manager.config.ICEServers, ",")).
|
||||
Str("ice_servers", fmt.Sprintf("%+v", manager.config.ICEServers)).
|
||||
Str("ephemeral_port_range", fmt.Sprintf("%d-%d", manager.config.EphemeralMin, manager.config.EphemeralMax)).
|
||||
Str("nat_ips", strings.Join(manager.config.NAT1To1IPs, ",")).
|
||||
Msgf("webrtc starting")
|
||||
@ -74,13 +74,9 @@ func (manager *WebRTCManager) Shutdown() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (manager *WebRTCManager) CreatePeer(id string, session types.Session) (string, bool, []string, error) {
|
||||
func (manager *WebRTCManager) CreatePeer(id string, session types.Session) (string, bool, []webrtc.ICEServer, error) {
|
||||
configuration := &webrtc.Configuration{
|
||||
ICEServers: []webrtc.ICEServer{
|
||||
{
|
||||
URLs: manager.config.ICEServers,
|
||||
},
|
||||
},
|
||||
ICEServers: manager.config.ICEServers,
|
||||
SDPSemantics: webrtc.SDPSemanticsUnifiedPlanWithFallback,
|
||||
}
|
||||
|
||||
@ -99,7 +95,7 @@ func (manager *WebRTCManager) CreatePeer(id string, session types.Session) (stri
|
||||
|
||||
settings.SetEphemeralUDPPortRange(manager.config.EphemeralMin, manager.config.EphemeralMax)
|
||||
settings.SetNAT1To1IPs(manager.config.NAT1To1IPs, webrtc.ICECandidateTypeHost)
|
||||
settings.SetICETimeouts(6 * time.Second, 6 * time.Second, 3 * time.Second)
|
||||
settings.SetICETimeouts(6*time.Second, 6*time.Second, 3*time.Second)
|
||||
settings.SetSRTPReplayProtectionWindow(512)
|
||||
|
||||
// Create MediaEngine based off sdp
|
||||
@ -146,12 +142,12 @@ func (manager *WebRTCManager) CreatePeer(id string, session types.Session) (stri
|
||||
Msg("connection state has changed")
|
||||
})
|
||||
|
||||
rtpVideo, err := connection.AddTrack(manager.videoTrack);
|
||||
rtpVideo, err := connection.AddTrack(manager.videoTrack)
|
||||
if err != nil {
|
||||
return "", manager.config.ICELite, manager.config.ICEServers, err
|
||||
}
|
||||
|
||||
rtpAudio, err := connection.AddTrack(manager.audioTrack);
|
||||
rtpAudio, err := connection.AddTrack(manager.audioTrack)
|
||||
if err != nil {
|
||||
return "", manager.config.ICELite, manager.config.ICEServers, err
|
||||
}
|
||||
@ -234,7 +230,6 @@ func (manager *WebRTCManager) CreatePeer(id string, session types.Session) (stri
|
||||
}
|
||||
}()
|
||||
|
||||
|
||||
return description.SDP, manager.config.ICELite, manager.config.ICEServers, nil
|
||||
}
|
||||
|
||||
|
@ -90,7 +90,6 @@ func (h *MessageHandler) Message(id string, raw []byte) error {
|
||||
return h.controlKeyboard(id, session, payload)
|
||||
}), "%s failed", header.Event)
|
||||
|
||||
|
||||
// Chat Events
|
||||
case event.CHAT_MESSAGE:
|
||||
payload := &message.ChatReceive{}
|
||||
|
@ -10,10 +10,10 @@ import "C"
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"regexp"
|
||||
"sync"
|
||||
"time"
|
||||
"unsafe"
|
||||
"regexp"
|
||||
|
||||
"n.eko.moe/neko/internal/types"
|
||||
)
|
||||
|
Reference in New Issue
Block a user