Skip to content
Snippets Groups Projects
Commit 919b52d9 authored by Travis Ralston's avatar Travis Ralston
Browse files

Add preliminary support for MP4 files

This needs to be expanded to cover more of what ffmpeg covers. This does not support animation for a few reasons:
* Most clients which will be using a video thumbnail will be using it in such a way where even a GIF isn't supported.
* Clients rely on the thumbnail endpoint returning images, which can lead to resource inefficiencies if we return GIFs.
* Returning more optimized thumbnails is not feasible for compatibility with most clients.
parent 92530fbd
No related branches found
No related tags found
No related merge requests found
......@@ -13,6 +13,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
* After running this tool, use the `gdpr_import` tool to bring the export into the media repo.
* Added thumbnailing support for some audio waveforms (MP3, WAV, OGG, and FLAC).
* Added audio metadata (duration, etc) to the unstable `/info` endpoint. Aligns with [MSC2380](https://github.com/matrix-org/matrix-doc/pull/2380).
* Added simple thumbnailing for MP4 videos.
### Fixed
......
......@@ -397,6 +397,7 @@ thumbnails:
- "audio/ogg"
- "audio/wav"
- "audio/flac"
#- "video/mp4" # Be sure to have ffmpeg installed to thumbnail video files
# Animated thumbnails can be CPU intensive to generate. To disable the generation of animated
# thumbnails, set this to false. If disabled, regular thumbnails will be returned.
......
package i
import (
"errors"
_ "image/jpeg"
"io/ioutil"
"os"
"os/exec"
"path"
"github.com/turt2live/matrix-media-repo/common/rcontext"
"github.com/turt2live/matrix-media-repo/thumbnailing/m"
"github.com/turt2live/matrix-media-repo/util"
"github.com/turt2live/matrix-media-repo/util/cleanup"
)
type mp4Generator struct {
}
func (d mp4Generator) supportedContentTypes() []string {
return []string{"video/mp4"}
}
func (d mp4Generator) supportsAnimation() bool {
return false
}
func (d mp4Generator) matches(img []byte, contentType string) bool {
return util.ArrayContains(d.supportedContentTypes(), contentType)
}
func (d mp4Generator) GenerateThumbnail(b []byte, contentType string, width int, height int, method string, animated bool, ctx rcontext.RequestContext) (*m.Thumbnail, error) {
key, err := util.GenerateRandomString(16)
if err != nil {
return nil, errors.New("mp4: error generating temp key: " + err.Error())
}
tempFile1 := path.Join(os.TempDir(), "media_repo."+key+".1.mp4")
tempFile2 := path.Join(os.TempDir(), "media_repo."+key+".2.png")
defer os.Remove(tempFile1)
defer os.Remove(tempFile2)
f, err := os.OpenFile(tempFile1, os.O_RDWR|os.O_CREATE, 0640)
if err != nil {
return nil, errors.New("mp4: error writing temp video file: " + err.Error())
}
_, _ = f.Write(b)
cleanup.DumpAndCloseStream(f)
err = exec.Command("ffmpeg", "-i", tempFile1, "-vf", "select=eq(n\\,0)", tempFile2).Run()
if err != nil {
return nil, errors.New("mp4: error converting video file: " + err.Error())
}
b, err = ioutil.ReadFile(tempFile2)
if err != nil {
return nil, errors.New("mp4: error reading temp png file: " + err.Error())
}
return pngGenerator{}.GenerateThumbnail(b, "image/png", width, height, method, false, ctx)
}
func init() {
generators = append(generators, mp4Generator{})
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment