Skip to content

Commit

Permalink
启动时获取不到直播间信息也在监控列表中保持直播间 (#466)
Browse files Browse the repository at this point in the history
* Keeping room in live list even failed on launch.
  • Loading branch information
kira1928 authored Jun 3, 2023
1 parent 3c506e8 commit f09da7c
Show file tree
Hide file tree
Showing 9 changed files with 166 additions and 18 deletions.
1 change: 1 addition & 0 deletions src/cmd/bililive/internal/init.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import (
_ "github.com/hr3lxphr6j/bililive-go/src/live/missevan"
_ "github.com/hr3lxphr6j/bililive-go/src/live/openrec"
_ "github.com/hr3lxphr6j/bililive-go/src/live/qq"
_ "github.com/hr3lxphr6j/bililive-go/src/live/system"
_ "github.com/hr3lxphr6j/bililive-go/src/live/twitch"
_ "github.com/hr3lxphr6j/bililive-go/src/live/yizhibo"
_ "github.com/hr3lxphr6j/bililive-go/src/live/zhanqi"
Expand Down
11 changes: 6 additions & 5 deletions src/listeners/event.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,10 @@ import (
)

const (
ListenStart events.EventType = "ListenStart"
ListenStop events.EventType = "ListenStop"
LiveStart events.EventType = "LiveStart"
LiveEnd events.EventType = "LiveEnd"
RoomNameChanged events.EventType = "RoomNameChanged"
ListenStart events.EventType = "ListenStart"
ListenStop events.EventType = "ListenStop"
LiveStart events.EventType = "LiveStart"
LiveEnd events.EventType = "LiveEnd"
RoomNameChanged events.EventType = "RoomNameChanged"
RoomInitializingFinished events.EventType = "RoomInitializingFinished"
)
21 changes: 18 additions & 3 deletions src/listeners/listener.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import (
"github.com/hr3lxphr6j/bililive-go/src/instance"
"github.com/hr3lxphr6j/bililive-go/src/interfaces"
"github.com/hr3lxphr6j/bililive-go/src/live"
"github.com/hr3lxphr6j/bililive-go/src/live/system"
"github.com/hr3lxphr6j/bililive-go/src/pkg/events"
)

Expand Down Expand Up @@ -92,9 +93,10 @@ func (l *listener) refresh() {
}
)
defer func() { l.status = latestStatus }()
isStatusChanged := true
switch l.status.Diff(latestStatus) {
case 0:
return
isStatusChanged = false
case statusToTrueEvt:
l.Live.SetLastStartTime(time.Now())
evtTyp = LiveStart
Expand All @@ -109,9 +111,22 @@ func (l *listener) refresh() {
evtTyp = RoomNameChanged
logInfo = "Room name was changed"
}
if isStatusChanged {
l.ed.DispatchEvent(events.NewEvent(evtTyp, l.Live))
l.logger.WithFields(fields).Info(logInfo)
}

l.ed.DispatchEvent(events.NewEvent(evtTyp, l.Live))
l.logger.WithFields(fields).Info(logInfo)
if info.Initializing {
initializingLive := l.Live.(*live.WrappedLive).Live.(*system.InitializingLive)
info, err = initializingLive.OriginalLive.GetInfo()
if err == nil {
l.ed.DispatchEvent(events.NewEvent(RoomInitializingFinished, live.InitializingFinishedParam{
InitializingLive: l.Live,
Live: initializingLive.OriginalLive,
Info: info,
}))
}
}
}

func (l *listener) run() {
Expand Down
52 changes: 52 additions & 0 deletions src/listeners/manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (
"github.com/hr3lxphr6j/bililive-go/src/instance"
"github.com/hr3lxphr6j/bililive-go/src/interfaces"
"github.com/hr3lxphr6j/bililive-go/src/live"
"github.com/hr3lxphr6j/bililive-go/src/pkg/events"
)

// for test
Expand All @@ -33,11 +34,43 @@ type manager struct {
savers map[live.ID]Listener
}

func (m *manager) registryListener(ctx context.Context, ed events.Dispatcher) {
ed.AddEventListener(RoomInitializingFinished, events.NewEventListener(func(event *events.Event) {
param := event.Object.(live.InitializingFinishedParam)
initializingLive := param.InitializingLive
live := param.Live
info := param.Info
if info.CustomLiveId != "" {
live.SetLiveIdByString(info.CustomLiveId)
}
inst := instance.GetInstance(ctx)
logger := inst.Logger
inst.Lives[live.GetLiveId()] = live

room, err := inst.Config.GetLiveRoomByUrl(live.GetRawUrl())
if err != nil {
logger.WithFields(map[string]interface{}{
"room": live.GetRawUrl(),
}).Error(err)
panic(err)
}
room.LiveId = live.GetLiveId()
if room.IsListening {
if err := m.replaceListener(ctx, initializingLive, live); err != nil {
logger.WithFields(map[string]interface{}{
"url": live.GetRawUrl(),
}).Error(err)
}
}
}))
}

func (m *manager) Start(ctx context.Context) error {
inst := instance.GetInstance(ctx)
if inst.Config.RPC.Enable || len(inst.Lives) > 0 {
inst.WaitGroup.Add(1)
}
m.registryListener(ctx, inst.EventDispatcher.(events.Dispatcher))
return nil
}

Expand Down Expand Up @@ -76,6 +109,25 @@ func (m *manager) RemoveListener(ctx context.Context, liveId live.ID) error {
return nil
}

func (m *manager) replaceListener(ctx context.Context, oldLive live.Live, newLive live.Live) error {
m.lock.Lock()
defer m.lock.Unlock()
oldLiveId := oldLive.GetLiveId()
oldListener, ok := m.savers[oldLiveId]
if !ok {
return ErrListenerNotExist
}
oldListener.Close()
newListener := newListener(ctx, newLive)
if oldLiveId == newLive.GetLiveId() {
m.savers[oldLiveId] = newListener
} else {
delete(m.savers, oldLiveId)
m.savers[newLive.GetLiveId()] = newListener
}
return newListener.Start()
}

func (m *manager) GetListener(ctx context.Context, liveId live.ID) (Listener, error) {
m.lock.RLock()
defer m.lock.RUnlock()
Expand Down
4 changes: 4 additions & 0 deletions src/listeners/manager_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import (
"github.com/hr3lxphr6j/bililive-go/src/instance"
"github.com/hr3lxphr6j/bililive-go/src/live"
livemock "github.com/hr3lxphr6j/bililive-go/src/live/mock"
evtmock "github.com/hr3lxphr6j/bililive-go/src/pkg/events/mock"
)

func TestManagerAddAndRemoveListener(t *testing.T) {
Expand Down Expand Up @@ -46,7 +47,10 @@ func TestManagerAddAndRemoveListener(t *testing.T) {
func TestManagerStartAndClose(t *testing.T) {
ctrl := gomock.NewController(t)
defer ctrl.Finish()
ed := evtmock.NewMockDispatcher(ctrl)
ed.EXPECT().AddEventListener(RoomInitializingFinished, gomock.Any())
ctx := context.WithValue(context.Background(), instance.Key, &instance.Instance{
EventDispatcher: ed,
Config: &configs.Config{
RPC: configs.RPC{Enable: true},
},
Expand Down
12 changes: 8 additions & 4 deletions src/live/info.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,12 @@ import (
)

type Info struct {
Live Live
HostName, RoomName string
Status, Listening, Recording bool
CustomLiveId string
Live Live
HostName, RoomName string
Status bool // means isLiving, maybe better to rename it
Listening, Recording bool
Initializing bool
CustomLiveId string
}

func (i *Info) MarshalJSON() ([]byte, error) {
Expand All @@ -21,6 +23,7 @@ func (i *Info) MarshalJSON() ([]byte, error) {
Status bool `json:"status"`
Listening bool `json:"listening"`
Recording bool `json:"recording"`
Initializing bool `json:"initializing"`
LastStartTime string `json:"last_start_time,omitempty"`
LastStartTimeUnix int64 `json:"last_start_time_unix,omitempty"`
}{
Expand All @@ -32,6 +35,7 @@ func (i *Info) MarshalJSON() ([]byte, error) {
Status: i.Status,
Listening: i.Listening,
Recording: i.Recording,
Initializing: i.Initializing,
}
if !i.Live.GetLastStartTime().IsZero() {
t.LastStartTime = i.Live.GetLastStartTime().Format("2006-01-02 15:04:05")
Expand Down
28 changes: 22 additions & 6 deletions src/live/lives.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@ import (
)

var (
m = make(map[string]Builder)
m = make(map[string]Builder)
InitializingLiveBuilderInstance InitializingLiveBuilder
)

func Register(domain string, b Builder) {
Expand All @@ -29,6 +30,16 @@ type Builder interface {
Build(*url.URL, ...Option) (Live, error)
}

type InitializingLiveBuilder interface {
Build(Live, *url.URL, ...Option) (Live, error)
}

type InitializingFinishedParam struct {
InitializingLive Live
Live Live
Info *Info
}

type Options struct {
Cookies *cookiejar.Jar
Quality int
Expand Down Expand Up @@ -77,7 +88,7 @@ func WithQuality(quality int) Option {
return func(opts *Options) {
opts.Quality = quality
}
}
}

type ID string

Expand All @@ -92,19 +103,19 @@ type Live interface {
SetLastStartTime(time.Time)
}

type wrappedLive struct {
type WrappedLive struct {
Live
cache gcache.Cache
}

func newWrappedLive(live Live, cache gcache.Cache) Live {
return &wrappedLive{
return &WrappedLive{
Live: live,
cache: cache,
}
}

func (w *wrappedLive) GetInfo() (*Info, error) {
func (w *WrappedLive) GetInfo() (*Info, error) {
i, err := w.Live.GetInfo()
if err != nil {
return nil, err
Expand Down Expand Up @@ -135,5 +146,10 @@ func New(url *url.URL, cache gcache.Cache, opts ...Option) (live Live, err error
}
time.Sleep(1 * time.Second)
}
return nil, err

// when room initializaion is failed
live, err = InitializingLiveBuilderInstance.Build(live, url, opts...)
live = newWrappedLive(live, cache)
live.GetInfo() // dummy call to initialize cache inside wrappedLive
return
}
48 changes: 48 additions & 0 deletions src/live/system/initializing_live.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
package system

import (
"net/url"

"github.com/hr3lxphr6j/bililive-go/src/live"
"github.com/hr3lxphr6j/bililive-go/src/live/internal"
)

func init() {
live.InitializingLiveBuilderInstance = new(builder)
}

type builder struct{}

func (b *builder) Build(live live.Live, url *url.URL, opt ...live.Option) (live.Live, error) {
return &InitializingLive{
BaseLive: internal.NewBaseLive(url, opt...),
OriginalLive: live,
}, nil
}

type InitializingLive struct {
internal.BaseLive
OriginalLive live.Live
}

func (l *InitializingLive) GetInfo() (info *live.Info, err error) {
err = nil
info = &live.Info{
Live: l,
HostName: "",
RoomName: l.GetRawUrl(),
Status: false,
Initializing: true,
}
return
}

func (l *InitializingLive) GetStreamUrls() (us []*url.URL, err error) {
us = make([]*url.URL, 0)
err = nil
return
}

func (l *InitializingLive) GetPlatformCNName() string {
return ""
}
7 changes: 7 additions & 0 deletions src/webapp/src/component/live-list/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,9 @@ class LiveList extends React.Component<Props, IState> {
if (tag === '录制中') {
color = 'red';
}
if (tag === '初始化') {
color = 'orange';
}

return (
<Tag color={color} key={tag}>
Expand Down Expand Up @@ -234,6 +237,10 @@ class LiveList extends React.Component<Props, IState> {
tags = ['录制中'];
}

if (item.initializing === true) {
tags.push('初始化')
}

return {
key: index + 1,
name: item.host_name,
Expand Down

0 comments on commit f09da7c

Please sign in to comment.