m3u8d/api.go

115 lines
2.4 KiB
Go
Raw Normal View History

2023-11-18 02:57:49 +00:00
package m3u8d
import (
"context"
"io/ioutil"
"path/filepath"
"sort"
"strings"
"sync"
)
var gMergeStatus SpeedStatus
var gMergeCancel context.CancelFunc
var gMergeCancelLocker sync.Mutex
type MergeTsDir_Resp struct {
ErrMsg string
IsCancel bool
}
2023-11-18 03:06:39 +00:00
var gMergeIsRunning bool
var gMergeIsRunningLocker sync.Mutex
2023-11-18 02:57:49 +00:00
2023-11-19 15:05:24 +00:00
func beginMerge() bool {
gMergeIsRunningLocker.Lock()
defer gMergeIsRunningLocker.Unlock()
2023-11-18 03:06:39 +00:00
2023-11-19 15:05:24 +00:00
if gMergeIsRunning != false {
return false
}
gMergeIsRunning = true
return true
}
func MergeTsDir(InputTsDir string, OutputMp4Name string) (resp MergeTsDir_Resp) {
if !beginMerge() {
return resp
2023-11-18 02:57:49 +00:00
}
2023-11-18 03:06:39 +00:00
defer func() {
gMergeIsRunningLocker.Lock()
gMergeIsRunning = false
gMergeIsRunningLocker.Unlock()
}()
2023-11-18 02:57:49 +00:00
fList, err := ioutil.ReadDir(InputTsDir)
if err != nil {
resp.ErrMsg = "读取目录失败 " + err.Error()
return
}
var tsFileList []string
for _, f := range fList {
if f.Mode().IsRegular() && strings.HasSuffix(strings.ToLower(f.Name()), ".ts") {
tsFileList = append(tsFileList, filepath.Join(InputTsDir, f.Name()))
}
}
if len(tsFileList) == 0 {
resp.ErrMsg = "目录下不存在ts文件: " + InputTsDir
return
}
sort.Strings(tsFileList) // 按照字典顺序排序
if OutputMp4Name == "" {
OutputMp4Name = filepath.Join(InputTsDir, "all.mp4")
2023-11-19 15:46:27 +00:00
} else if !filepath.IsAbs(OutputMp4Name) {
OutputMp4Name = filepath.Join(InputTsDir, OutputMp4Name)
2023-11-18 02:57:49 +00:00
}
ctx, cancelFn := context.WithCancel(context.Background())
defer cancelFn()
gMergeCancelLocker.Lock()
if gMergeCancel != nil {
gMergeCancel()
}
gMergeCancel = cancelFn
gMergeCancelLocker.Unlock()
err = MergeTsFileListToSingleMp4(MergeTsFileListToSingleMp4_Req{
TsFileList: tsFileList,
OutputMp4: OutputMp4Name,
Ctx: ctx,
Status: &gMergeStatus,
})
if err != nil {
resp.ErrMsg = "合并错误: " + err.Error()
resp.IsCancel = isContextCancel(ctx)
return resp
}
return resp
}
type MergeGetProgressPercent_Resp struct {
Percent int
SpeedText string
IsRunning bool
}
func MergeGetProgressPercent() (resp MergeGetProgressPercent_Resp) {
2023-11-18 03:08:58 +00:00
gMergeIsRunningLocker.Lock()
resp.IsRunning = gMergeIsRunning
gMergeIsRunningLocker.Unlock()
2023-11-18 02:57:49 +00:00
if resp.IsRunning {
resp.Percent = gMergeStatus.GetPercent()
resp.SpeedText = gMergeStatus.SpeedRecent5sGetAndUpdate()
}
return resp
}
func MergeStop() {
gMergeCancelLocker.Lock()
if gMergeCancel != nil {
gMergeCancel()
}
gMergeCancelLocker.Unlock()
}