1
0
mirror of https://github.com/Mrs4s/go-cqhttp.git synced 2025-05-05 19:43:49 +08:00

Merge pull request #549 from wdvxdr1123/patch-2

fix file close
This commit is contained in:
Mrs4s 2021-01-09 17:56:11 +08:00 committed by GitHub
commit 56da9adeab
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 58 additions and 25 deletions

View File

@ -5,7 +5,6 @@ import (
"encoding/gob"
"fmt"
"hash/crc32"
"math/rand"
"os"
"path"
"runtime/debug"
@ -126,6 +125,21 @@ func (bot *CQBot) UploadLocalImageAsGroup(groupCode int64, img *LocalImageElemen
return bot.Client.UploadGroupImageByFile(groupCode, img.File)
}
func (bot *CQBot) UploadLocalVideo(target int64, v *LocalVideoElement) (*message.ShortVideoElement, error) {
if v.File != "" {
video, err := os.Open(v.File)
if err != nil {
return nil, err
}
defer video.Close()
// todo 多线程上传失败: 短视频上传失败: resp is empty (upload video file error: upload failed: 70
//hash, _ := utils.ComputeMd5AndLength(io.MultiReader(video, v.thumb))
//cacheFile := path.Join(global.CACHE_PATH, hex.EncodeToString(hash[:])+".cache")
return bot.Client.UploadGroupShortVideo(target, video, v.thumb)
}
return &v.ShortVideoElement, nil
}
func (bot *CQBot) UploadLocalImageAsPrivate(userId int64, img *LocalImageElement) (*message.FriendImageElement, error) {
if img.Stream != nil {
return bot.Client.UploadPrivateImage(userId, img.Stream)
@ -160,8 +174,8 @@ func (bot *CQBot) SendGroupMessage(groupId int64, m *message.SendingMessage) int
newElem = append(newElem, gv)
continue
}
if i, ok := elem.(*LocalVideoElement); ok { // todo:cache & multiThread
gv, err := bot.Client.UploadGroupShortVideo(groupId, i.video, i.thumb)
if i, ok := elem.(*LocalVideoElement); ok {
gv, err := bot.UploadLocalVideo(groupId, i)
if err != nil {
log.Warnf("警告: 群 %v 消息短视频上传失败: %v", groupId, err)
continue
@ -289,10 +303,10 @@ func (bot *CQBot) SendPrivateMessage(target int64, m *message.SendingMessage) in
newElem = append(newElem, fv)
continue
}
if i, ok := elem.(*LocalVideoElement); ok { // todo:cache & multiThread
gv, err := bot.Client.UploadGroupShortVideo(target, i.video, i.thumb)
if i, ok := elem.(*LocalVideoElement); ok {
gv, err := bot.UploadLocalVideo(target, i)
if err != nil {
log.Warnf("警告: 私聊 %v 消息短视频上传失败: %v", int64(rand.Uint32()), err)
log.Warnf("警告: 私聊 %v 消息短视频上传失败: %v", target, err)
continue
}
newElem = append(newElem, gv)

View File

@ -82,7 +82,6 @@ type LocalVoiceElement struct {
type LocalVideoElement struct {
message.ShortVideoElement
File string
video io.ReadSeeker
thumb io.ReadSeeker
}
@ -793,26 +792,30 @@ func (bot *CQBot) ToElement(t string, d map[string]string, group bool) (m interf
return nil, err
}
v := file.(*LocalVideoElement)
if v.File == "" {
return v, nil
}
var data []byte
if cover, ok := d["cover"]; ok {
data, _ := global.FindFile(cover, cache, global.IMAGE_PATH)
v.thumb = bytes.NewReader(data)
}
if v.thumb == nil {
data, _ = global.FindFile(cover, cache, global.IMAGE_PATH)
} else {
_ = global.ExtractCover(v.File, v.File+".jpg")
v.thumb, _ = os.Open(v.File + ".jpg")
data, _ = ioutil.ReadFile(v.File + ".jpg")
}
v.video, _ = os.Open(v.File)
_, err = v.video.Seek(4, io.SeekStart)
v.thumb = bytes.NewReader(data)
video, _ := os.Open(v.File)
defer video.Close()
_, err = video.Seek(4, io.SeekStart)
if err != nil {
return nil, err
}
var header = make([]byte, 4)
_, err = v.video.Read(header)
if !bytes.Equal(header, []byte{0x66, 0x74, 0x79, 0x70}) { // ftyp
_, _ = v.video.Seek(0, io.SeekStart)
hash, _ := utils.ComputeMd5AndLength(v.video)
_, err = video.Read(header)
if !bytes.Equal(header, []byte{0x66, 0x74, 0x79, 0x70}) { // check file header ftyp
_, _ = video.Seek(0, io.SeekStart)
hash, _ := utils.ComputeMd5AndLength(video)
cacheFile := path.Join(global.CACHE_PATH, hex.EncodeToString(hash[:])+".mp4")
if global.PathExists(cacheFile) {
if global.PathExists(cacheFile) && cache == "1" {
goto ok
}
err = global.EncodeMP4(v.File, cacheFile)
@ -820,9 +823,8 @@ func (bot *CQBot) ToElement(t string, d map[string]string, group bool) (m interf
return nil, err
}
ok:
v.video, _ = os.Open(cacheFile)
v.File = cacheFile
}
_, _ = v.video.Seek(0, io.SeekStart)
return v, nil
default:
return nil, errors.New("unsupported cq code: " + t)
@ -924,8 +926,9 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video, group bool) (
}
return &LocalVideoElement{File: fu.Path}, nil
}
if video { // 短视频视频只支持以上两种
return nil, errors.New("invalid video")
rawPath := path.Join(global.IMAGE_PATH, f)
if video {
goto video
}
if strings.HasPrefix(f, "base64") {
b, err := base64.StdEncoding.DecodeString(strings.ReplaceAll(f, "base64://", ""))
@ -934,7 +937,6 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video, group bool) (
}
return &LocalImageElement{Stream: bytes.NewReader(b)}, nil
}
rawPath := path.Join(global.IMAGE_PATH, f)
if !global.PathExists(rawPath) && global.PathExists(path.Join(global.IMAGE_PATH_OLD, f)) {
rawPath = path.Join(global.IMAGE_PATH_OLD, f)
}
@ -1007,6 +1009,23 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video, group bool) (
return rsp, nil
}
return nil, errors.New("invalid image")
video:
rawPath = path.Join(global.VIDEO_PATH, f)
if !global.PathExists(rawPath) {
return nil, errors.New("invalid video")
}
if path.Ext(rawPath) == ".video" {
b, _ := ioutil.ReadFile(rawPath)
r := binary.NewReader(b)
return &LocalVideoElement{ShortVideoElement: message.ShortVideoElement{// todo 检查缓存是否有效
Md5: r.ReadBytes(16),
Size: r.ReadInt32(),
Name: r.ReadString(),
Uuid: r.ReadAvailable(),
}}, nil
} else {
return &LocalVideoElement{File: rawPath}, nil
}
}
//makeShowPic 一种xml 方式发送的群消息图片

View File

@ -39,7 +39,7 @@ func EncoderSilk(data []byte) ([]byte, error) {
return slk, nil
}
func EncodeMP4(src string, dst string) error {
func EncodeMP4(src string, dst string) error { // -y 覆盖文件
cmd := exec.Command("ffmpeg", "-i", src, "-y", "-c", "copy", "-map", "0", dst)
return cmd.Run()
}