Add enable loopback candidate option (#1185)

This commit is contained in:
cnderrauber
2022-11-23 16:01:36 +08:00
committed by GitHub
parent 491a15e49e
commit 6711060cdb
7 changed files with 37 additions and 74 deletions
+2
View File
@@ -80,6 +80,8 @@ rtc:
# low_quality: 500ms
# mid_quality: 1s
# high_quality: 1s
# # when set, Livekit will collect loopback candidates, it is useful for some VM have public address mapped to its loopback interface.
# enable_loopback_candidate: true
# # network interface filter. If the machine has more than one network interface and you'd like it to use or skip specific interfaces
# # both inclusion and exclusion filters can be used together. If neither is defined (default), all interfaces on the machine will be used.
# # If both of them are set, then only include takes effect.
+1 -1
View File
@@ -34,7 +34,7 @@ require (
github.com/pion/stun v0.3.5
github.com/pion/transport v0.13.1
github.com/pion/turn/v2 v2.0.8
github.com/pion/webrtc/v3 v3.1.48
github.com/pion/webrtc/v3 v3.1.49
github.com/pkg/errors v0.9.1
github.com/prometheus/client_golang v1.14.0
github.com/rs/cors v1.8.2
+2 -5
View File
@@ -308,7 +308,6 @@ github.com/pion/dtls/v2 v2.1.3/go.mod h1:o6+WvyLDAlXF7YiPB/RlskRoeK+/JtuaZa5emwQ
github.com/pion/dtls/v2 v2.1.5 h1:jlh2vtIyUBShchoTDqpCCqiYCyRFJ/lvf/gQ8TALs+c=
github.com/pion/dtls/v2 v2.1.5/go.mod h1:BqCE7xPZbPSubGasRoDFJeTsyJtdD1FanJYL0JGheqY=
github.com/pion/ice/v2 v2.2.6/go.mod h1:SWuHiOGP17lGromHTFadUe1EuPgFh/oCU6FCMZHooVE=
github.com/pion/ice/v2 v2.2.11/go.mod h1:NqUDUao6SjSs1+4jrqpexDmFlptlVhGxQjcymXLaVvE=
github.com/pion/ice/v2 v2.2.12 h1:n3M3lUMKQM5IoofhJo73D3qVla+mJN2nVvbSPq32Nig=
github.com/pion/ice/v2 v2.2.12/go.mod h1:z2KXVFyRkmjetRlaVRgjO9U3ShKwzhlUylvxKfHfd5A=
github.com/pion/interceptor v0.1.11/go.mod h1:tbtKjZY14awXd7Bq0mmWvgtHB5MDaRN7HV3OZ/uy7s8=
@@ -346,8 +345,8 @@ github.com/pion/turn/v2 v2.0.8/go.mod h1:+y7xl719J8bAEVpSXBXvTxStjJv3hbz9YFflvkp
github.com/pion/udp v0.1.1 h1:8UAPvyqmsxK8oOjloDk4wUt63TzFe9WEJkg5lChlj7o=
github.com/pion/udp v0.1.1/go.mod h1:6AFo+CMdKQm7UiA0eUPA8/eVCTx8jBIITLZHc9DWX5M=
github.com/pion/webrtc/v3 v3.1.44/go.mod h1:G/J8k0+grVsjC/rjCZ24AKoCCxcFFODgh7zThNZGs0M=
github.com/pion/webrtc/v3 v3.1.48 h1:lRAdRAewrcQTlj2n7pDUbJcuiQpHwwMq61edwhTkVq4=
github.com/pion/webrtc/v3 v3.1.48/go.mod h1:JOk9h4pOtogTAWM1SCoEG2opDQmEOR0QZcbEo9vy0Xc=
github.com/pion/webrtc/v3 v3.1.49 h1:rbsNGxK9jMYts+xE6zYAJMUQHnGwmk/JYze8yttW+to=
github.com/pion/webrtc/v3 v3.1.49/go.mod h1:kHf/o47QW4No1rgpsFux/h7lUhtUnwFnSFDZOXeLapw=
github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
@@ -547,7 +546,6 @@ golang.org/x/net v0.0.0-20220425223048-2871e0cb64e4/go.mod h1:CfG3xpIq0wQ8r1q4Su
golang.org/x/net v0.0.0-20220531201128-c960675eff93/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
golang.org/x/net v0.0.0-20220630215102-69896b714898/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
golang.org/x/net v0.0.0-20221002022538-bcab6841153b/go.mod h1:YDH+HFinaLZZlnHAfSS6ZXJJ9M9t4Dl22yv3iI2vPwk=
golang.org/x/net v0.1.0/go.mod h1:Cx3nUiGt4eDBEyega/BKRp+/AlGL8hYe7U9odMt2Cco=
golang.org/x/net v0.2.0 h1:sZfSu1wtKLGlWI4ZZayP0ck9Y73K1ynO6gqzTdBVdPU=
golang.org/x/net v0.2.0/go.mod h1:KqCZLdyyvdV855qA2rE3GC2aiw5xGR5TEjj8smXukLY=
@@ -642,7 +640,6 @@ golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBc
golang.org/x/sys v0.0.0-20220608164250-635b8c9b7f68/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220622161953-175b2fd9d664/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.1.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.2.0 h1:ljd4t30dBnAvMZaQCevtY0xLLD0A+bRZXbgLMLU1F/A=
golang.org/x/sys v0.2.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+13 -12
View File
@@ -58,18 +58,19 @@ type Config struct {
}
type RTCConfig struct {
UDPPort uint32 `yaml:"udp_port,omitempty"`
TCPPort uint32 `yaml:"tcp_port,omitempty"`
ICEPortRangeStart uint32 `yaml:"port_range_start,omitempty"`
ICEPortRangeEnd uint32 `yaml:"port_range_end,omitempty"`
NodeIP string `yaml:"node_ip,omitempty"`
NodeIPAutoGenerated bool `yaml:"-"`
STUNServers []string `yaml:"stun_servers,omitempty"`
TURNServers []TURNServer `yaml:"turn_servers,omitempty"`
UseExternalIP bool `yaml:"use_external_ip"`
UseICELite bool `yaml:"use_ice_lite,omitempty"`
Interfaces InterfacesConfig `yaml:"interfaces"`
IPs IPsConfig `yaml:"ips"`
UDPPort uint32 `yaml:"udp_port,omitempty"`
TCPPort uint32 `yaml:"tcp_port,omitempty"`
ICEPortRangeStart uint32 `yaml:"port_range_start,omitempty"`
ICEPortRangeEnd uint32 `yaml:"port_range_end,omitempty"`
NodeIP string `yaml:"node_ip,omitempty"`
NodeIPAutoGenerated bool `yaml:"-"`
STUNServers []string `yaml:"stun_servers,omitempty"`
TURNServers []TURNServer `yaml:"turn_servers,omitempty"`
UseExternalIP bool `yaml:"use_external_ip"`
UseICELite bool `yaml:"use_ice_lite,omitempty"`
Interfaces InterfacesConfig `yaml:"interfaces"`
IPs IPsConfig `yaml:"ips"`
EnableLoopbackCandidate bool `yaml:"enable_loopback_candidate"`
// Number of packets to buffer for NACK
PacketBufferSize int `yaml:"packet_buffer_size,omitempty"`
+6 -2
View File
@@ -30,14 +30,14 @@ func (conf *Config) determineIP() (string, error) {
}
// use local ip instead
addresses, err := GetLocalIPAddresses()
addresses, err := GetLocalIPAddresses(false)
if len(addresses) > 0 {
return addresses[0], err
}
return "", err
}
func GetLocalIPAddresses() ([]string, error) {
func GetLocalIPAddresses(includeLoopback bool) ([]string, error) {
ifaces, err := net.Interfaces()
if err != nil {
return nil, err
@@ -70,6 +70,10 @@ func GetLocalIPAddresses() ([]string, error) {
}
}
if includeLoopback {
addresses = append(addresses, loopBacks...)
}
if len(addresses) > 0 {
return addresses, nil
}
+11 -4
View File
@@ -114,12 +114,15 @@ func NewWebRTCConfig(conf *config.Config, externalIP string) (*WebRTCConfig, err
return nil, err
}
} else if rtcConf.UDPPort != 0 {
udpMux, err := ice.NewMultiUDPMuxFromPort(
int(rtcConf.UDPPort),
opts := []ice.UDPMuxFromPortOption{
ice.UDPMuxFromPortWithReadBufferSize(defaultUDPBufferSize),
ice.UDPMuxFromPortWithWriteBufferSize(defaultUDPBufferSize),
ice.UDPMuxFromPortWithLogger(s.LoggerFactory.NewLogger("udp_mux")),
)
}
if rtcConf.EnableLoopbackCandidate {
opts = append(opts, ice.UDPMuxFromPortWithLoopback())
}
udpMux, err := ice.NewMultiUDPMuxFromPort(int(rtcConf.UDPPort), opts...)
if err != nil {
return nil, err
}
@@ -159,6 +162,10 @@ func NewWebRTCConfig(conf *config.Config, externalIP string) (*WebRTCConfig, err
}
s.SetNetworkTypes(networkTypes)
if rtcConf.EnableLoopbackCandidate {
s.SetIncludeLoopbackCandidate(true)
}
// publisher configuration
publisherConfig := DirectionConfig{
RTPHeaderExtension: RTPHeaderExtensionConfig{
@@ -251,7 +258,7 @@ func getNAT1to1IPsForConf(conf *config.Config, ipFilter func(net.IP) bool) ([]st
if len(stunServers) == 0 {
stunServers = config.DefaultStunServers
}
localIPs, err := config.GetLocalIPAddresses()
localIPs, err := config.GetLocalIPAddresses(conf.RTC.EnableLoopbackCandidate)
if err != nil {
return nil, err
}
+2 -50
View File
@@ -7,8 +7,6 @@
package service
import (
"context"
"crypto/tls"
"fmt"
"github.com/go-redis/redis/v8"
"github.com/livekit/livekit-server/pkg/clientconfiguration"
@@ -19,7 +17,7 @@ import (
"github.com/livekit/protocol/egress"
"github.com/livekit/protocol/ingress"
"github.com/livekit/protocol/livekit"
"github.com/livekit/protocol/logger"
redis2 "github.com/livekit/protocol/redis"
"github.com/livekit/protocol/webhook"
"github.com/pion/turn/v2"
"github.com/pkg/errors"
@@ -144,53 +142,7 @@ func createWebhookNotifier(conf *config.Config, provider auth.KeyProvider) (webh
}
func createRedisClient(conf *config.Config) (redis.UniversalClient, error) {
if !conf.HasRedis() {
return nil, nil
}
var rc redis.UniversalClient
var tlsConfig *tls.Config
if conf.Redis.UseTLS {
tlsConfig = &tls.Config{
MinVersion: tls.VersionTLS12,
}
}
values := make([]interface{}, 0)
values = append(values, "sentinel", conf.UseSentinel())
if conf.UseSentinel() {
values = append(values, "addr", conf.Redis.SentinelAddresses, "masterName", conf.Redis.MasterName)
rcOptions := &redis.FailoverOptions{
SentinelAddrs: conf.Redis.SentinelAddresses,
SentinelUsername: conf.Redis.SentinelUsername,
SentinelPassword: conf.Redis.SentinelPassword,
MasterName: conf.Redis.MasterName,
Username: conf.Redis.Username,
Password: conf.Redis.Password,
DB: conf.Redis.DB,
TLSConfig: tlsConfig,
}
rc = redis.NewFailoverClient(rcOptions)
} else {
values = append(values, "addr", conf.Redis.Address)
rcOptions := &redis.Options{
Addr: conf.Redis.Address,
Username: conf.Redis.Username,
Password: conf.Redis.Password,
DB: conf.Redis.DB,
TLSConfig: tlsConfig,
}
rc = redis.NewClient(rcOptions)
}
logger.Infow("using multi-node routing via redis", values...)
if err := rc.Ping(context.Background()).Err(); err != nil {
err = errors.Wrap(err, "unable to connect to redis")
return nil, err
}
return rc, nil
return redis2.GetRedisClient(&conf.Redis)
}
func createStore(rc redis.UniversalClient) ObjectStore {