[.net] 如何使用Youtube API 下載播放清單內的所有影片

因為想下載youtube播放清單內的所有影片,又找不到有相關免費的下載器可以用

就自己來寫一個

首先必需先到google申請一個youtube的api key ,這個部份網路上有許多教學,這裡就不說明了

再來就是寫一個下載的程式

private static async Task<YoutubePlaylistModel> GetYoutubePlaylist(string pageToken)
        {
            var client = new HttpClient();

            string url = "https://www.googleapis.com/youtube/v3/playlistItems?";

            var querystring = HttpUtility.ParseQueryString("");
            querystring.Add("part", "snippet,contentDetails");
            querystring.Add("playlistId", PLAYLIST_ID);
            querystring.Add("maxResults", "50");
            querystring.Add("key", YOUTUBE_API_KEY);

            if (!string.IsNullOrEmpty(pageToken))
                querystring.Add("pageToken", pageToken);

            url += querystring.ToString();

            var response = await client.GetAsync(url);

            if (!response.IsSuccessStatusCode)
            {
                Console.ForegroundColor = ConsoleColor.Red;
                Console.WriteLine("取得下載清單失敗");
                Console.ResetColor();

                return null;
            }

            var data = await response.Content.ReadAsStringAsync();

            return JsonConvert.DeserializeObject<YoutubePlaylistModel>(data);
        }
       

url : 這段是固定的,取得播放清單內的影片資訊

querystring:

"part" => 資料格式要包含哪些東西,我要的資訊需要包含 snippet, contentDetails ,實際可以參考 ( https://developers.google.com/youtube/v3/docs/playlistItems/list )  

"playlistId" => 哪一個播放清單,例如我的播放清單網址為:https://www.youtube.com/playlist?list=PLhMsqKJtHaLoXU2ewdjwvUi6OafG16ERn ,playlistId = PLhMsqKJtHaLoXU2ewdjwvUi6OafG16ERn

"maxResults" => 一次要取得幾筆,這裡最大只能下載50筆

"key" => 這是你申請的api key

"pageToken" => 如果你的播放清單有下一頁,在打API時會多一個pageToken的Response,你要下載下一頁的資料就必需把這個代入 

目前就是取得播放清單內的資料回來

再來要開始下載影片並轉檔為mp3

下載的部份要加入參考 <PackageReference Include="VideoLibrary" Version="3.0.9" />

private static string DownloadFile(string dir, string url)
        {
            //url = "https://www.youtube.com/playlist?list=PLsyOSbh5bs14MzRNG0FuuN7OFt914H-Nz";

            try
            {
                Console.WriteLine("下載中...");

                var youtube = YouTube.Default;

                var vid = youtube.GetVideo(url);

                var oriFilePath = Path.Combine(dir, vid.FullName).Replace("\"", "'");

                File.WriteAllBytes(oriFilePath, vid.GetBytes());

                Console.WriteLine("下載完成...");

                return oriFilePath;
            }
            catch (Exception e)
            {
                Console.WriteLine($"下載發生錯誤:{e.Message}");

                return string.Empty;
            }
        }

 

轉檔的部份使用ffmpeg

private static void Translate(string oriFilePath, string desFileName)
        {
            try
            {
                Console.WriteLine("轉檔中...");

                var sh = "./convert.sh";

                var cmd = $"ffmpeg -y -i \"{oriFilePath}\" \"{desFileName}\"";

                File.WriteAllText(sh, cmd);

                using var p = Process.Start(new ProcessStartInfo
                                            {
                                                FileName = "/bin/sh",
                                                Arguments = sh,
                                                UseShellExecute = false,
                                                RedirectStandardOutput = true,
                                                RedirectStandardError = true,
                                                CreateNoWindow = true
                                            });

                p.WaitForExit();

                Console.WriteLine("轉檔完成...");

                if (p.ExitCode > 0)
                {
                    throw new Exception($"Failed");
                }

                File.Delete(oriFilePath);
            }
            catch (Exception e)
            {
                Console.WriteLine($"轉檔發生錯誤:{e.Message}");
            }
        }