From a878c05d9d995226ea19fb7aff01bb8753b853e3 Mon Sep 17 00:00:00 2001 From: Jessica Stokes Date: Tue, 11 Aug 2020 16:28:20 -0700 Subject: [PATCH] Allow additional youtube-dl arguments This allows inserting arbitrary extra arguments into the youtube-dl command-line within each podcast feed entry. This allows, for example, requesting that youtube-dl embed subtitles and captions into the video file, or configuring additional postprocessor arguments. No effort has been made to make sure no incompatible arguments are provided, with the expectation that the end-user will understand what's possible, and that this is an option expressly for advanced users. This would fix #162,and theoretically also #136! --- README.md | 1 + pkg/config/config.go | 2 ++ pkg/ytdl/ytdl.go | 3 +++ pkg/ytdl/ytdl_test.go | 17 ++++++++++++++--- 4 files changed, 20 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 90177d0..9eb4194 100644 --- a/README.md +++ b/README.md @@ -80,6 +80,7 @@ vimeo = [ # Multiple keys will be rotated. # filters = { title = "regex for title here", not_title = "regex for negative title match", description = "...", not_description = "..." } # Optional Golang regexp format. If set, then only download matching episodes. # opml = true|false # Optional inclusion of the feed in the OPML file (default value: false) # clean = { keep_last = 10 } # Keep last 10 episodes (order desc by PubDate) + # youtube_dl_args = [ "--write-sub", "--embed-subs", "--sub-lang", "en,en-US,en-GB" ] # Optional extra arguments passed to youtube-dl when downloading videos from this feed. This example would embed available English closed captions in the videos. Note that setting '--audio-format' for audio format feeds, or '--format' or '--output' for any format may cause unexpected behaviour. You should only use this if you know what you are doing, and have read up on youtube-dl's options! [database] badger = { truncate = true, file_io = true } # See https://github.com/dgraph-io/badger#memory-usage diff --git a/pkg/config/config.go b/pkg/config/config.go index 0496d85..2c8ccd3 100644 --- a/pkg/config/config.go +++ b/pkg/config/config.go @@ -40,6 +40,8 @@ type Feed struct { Clean Cleanup `toml:"clean"` // Custom is a list of feed customizations Custom Custom `toml:"custom"` + // List of additional youtube-dl arguments passed at download time + YouTubeDLArgs []string `toml:"youtube_dl_args"` // Included in OPML file OPML bool `toml:"opml"` } diff --git a/pkg/ytdl/ytdl.go b/pkg/ytdl/ytdl.go index f74277d..ae291f7 100644 --- a/pkg/ytdl/ytdl.go +++ b/pkg/ytdl/ytdl.go @@ -214,6 +214,9 @@ func buildArgs(feedConfig *config.Feed, episode *model.Episode, outputFilePath s args = append(args, "--extract-audio", "--audio-format", "mp3", "--format", format) } + // Insert additional per-feed youtube-dl arguments + args = append(args, feedConfig.YouTubeDLArgs...) + args = append(args, "--output", outputFilePath, episode.VideoURL) return args } diff --git a/pkg/ytdl/ytdl_test.go b/pkg/ytdl/ytdl_test.go index 8b2581c..09ca031 100644 --- a/pkg/ytdl/ytdl_test.go +++ b/pkg/ytdl/ytdl_test.go @@ -17,6 +17,7 @@ func TestBuildArgs(t *testing.T) { maxHeight int output string videoURL string + ytdlArgs []string expect []string }{ { @@ -91,14 +92,24 @@ func TestBuildArgs(t *testing.T) { videoURL: "http://url1", expect: []string{"--format", "bestvideo[height<=1024][ext=mp4]+bestaudio[ext=m4a]/best[ext=mp4]/best", "--output", "/tmp/2", "http://url1"}, }, + { + name: "Video high quality with custom youtube-dl arguments", + format: model.FormatVideo, + quality: model.QualityHigh, + output: "/tmp/2", + videoURL: "http://url1", + ytdlArgs: []string{"--write-sub", "--embed-subs", "--sub-lang", "en,en-US,en-GB"}, + expect: []string{"--format", "bestvideo[ext=mp4]+bestaudio[ext=m4a]/best[ext=mp4]/best", "--write-sub", "--embed-subs", "--sub-lang", "en,en-US,en-GB", "--output", "/tmp/2", "http://url1"}, + }, } for _, tst := range tests { t.Run(tst.name, func(t *testing.T) { result := buildArgs(&config.Feed{ - Format: tst.format, - Quality: tst.quality, - MaxHeight: tst.maxHeight, + Format: tst.format, + Quality: tst.quality, + MaxHeight: tst.maxHeight, + YouTubeDLArgs: tst.ytdlArgs, }, &model.Episode{ VideoURL: tst.videoURL, }, tst.output)