From 1d636120ccc93424ac45cf903a3999e79035921e Mon Sep 17 00:00:00 2001 From: Michael Gordeev Date: Sun, 10 May 2020 13:47:42 +0300 Subject: [PATCH] Indetation formatting and unnecessary usings cleanup --- YouTube.API.Test/ClosedCaptionsTest.cs | 26 +- YouTube.API.Test/DashManifestTest.cs | 32 +- YouTube.API.Test/VideoPlaybackTest.cs | 27 +- YouTube.API.Test/WatchLaterTest.cs | 77 ++-- YouTube.API/Assets/DashManifestTemplate.xml | 24 +- YouTube.API/Extensions.cs | 36 +- YouTube.API/Generators/ManifestGenerator.cs | 334 +++++++++--------- YouTube.API/Models/ClosedCaptionInfo.cs | 16 +- YouTube.API/Models/ClosedCaptionTrack.cs | 24 +- YouTube.API/Models/DashManifest.cs | 36 +- YouTube.API/Models/PlaybackUrl.cs | 90 +++-- YouTube.API/Models/VideoPlayback.cs | 28 +- YouTube.API/Resources/CaptionsResource.cs | 86 ++--- .../Resources/DashManifestsResource.cs | 60 ++-- YouTube.API/Resources/HistoryResource.cs | 48 +-- .../Resources/VideoPlaybackResource.cs | 174 ++++----- YouTube.API/Resources/WatchLaterResource.cs | 164 ++++----- YouTube.API/VideoQuality.cs | 76 ++-- YouTube.API/YouTube.API.csproj | 2 +- YouTube.API/YouTubeService.cs | 26 +- 20 files changed, 684 insertions(+), 702 deletions(-) diff --git a/YouTube.API.Test/ClosedCaptionsTest.cs b/YouTube.API.Test/ClosedCaptionsTest.cs index 5e0edfa..cb27a02 100644 --- a/YouTube.API.Test/ClosedCaptionsTest.cs +++ b/YouTube.API.Test/ClosedCaptionsTest.cs @@ -4,16 +4,16 @@ using YouTube.Models; namespace YouTube.API.Test { - public class ClosedCaptionsTest - { - [Test] - public void ValidCaptionsTest() - { - ExtendedYouTubeService service = new ExtendedYouTubeService(); - ClosedCaptionInfo info = service.VideoPlayback.List("VC5-YkjMHuw").Execute().ClosedCaptions.FirstOrDefault(); - ClosedCaptionTrack track = service.Captions.Load(info).Execute(); - Assert.IsNotNull(track); - Assert.IsNotEmpty(track.Captions); - } - } -} + public class ClosedCaptionsTest + { + [Test] + public void ValidCaptionsTest() + { + ExtendedYouTubeService service = new ExtendedYouTubeService(); + ClosedCaptionInfo info = service.VideoPlayback.List("VC5-YkjMHuw").Execute().ClosedCaptions.FirstOrDefault(); + ClosedCaptionTrack track = service.Captions.Load(info).Execute(); + Assert.IsNotNull(track); + Assert.IsNotEmpty(track.Captions); + } + } +} \ No newline at end of file diff --git a/YouTube.API.Test/DashManifestTest.cs b/YouTube.API.Test/DashManifestTest.cs index 2f70f98..8969659 100644 --- a/YouTube.API.Test/DashManifestTest.cs +++ b/YouTube.API.Test/DashManifestTest.cs @@ -5,23 +5,17 @@ using YouTube.Models; namespace YouTube.API.Test { - public class DashManifestTest - { - [SetUp] - public void Setup() - { - - } - - [Test] - public void ValidManifestTest() - { - ExtendedYouTubeService service = new ExtendedYouTubeService(); - IReadOnlyList manifests = service.DashManifests.List("NkGbcQwWxqk").Execute(); - foreach (var i in manifests) - Console.WriteLine(i.Label); - Assert.IsNotNull(manifests); - Assert.IsNotEmpty(manifests); - } - } + public class DashManifestTest + { + [Test] + public void ValidManifestTest() + { + ExtendedYouTubeService service = new ExtendedYouTubeService(); + IReadOnlyList manifests = service.DashManifests.List("NkGbcQwWxqk").Execute(); + foreach (var i in manifests) + Console.WriteLine(i.Label); + Assert.IsNotNull(manifests); + Assert.IsNotEmpty(manifests); + } + } } \ No newline at end of file diff --git a/YouTube.API.Test/VideoPlaybackTest.cs b/YouTube.API.Test/VideoPlaybackTest.cs index 2717e6e..9293b73 100644 --- a/YouTube.API.Test/VideoPlaybackTest.cs +++ b/YouTube.API.Test/VideoPlaybackTest.cs @@ -1,19 +1,16 @@ -using System; -using System.Collections.Generic; -using System.Text; -using NUnit.Framework; +using NUnit.Framework; using YouTube.Models; namespace YouTube.API.Test { - public class VideoPlaybackTest - { - [Test] - public void ValidVideoPlaybackTest() - { - ExtendedYouTubeService service = new ExtendedYouTubeService(); - VideoPlayback info = service.VideoPlayback.List("VC5-YkjMHuw").Execute(); - Assert.NotNull(info); - } - } -} + public class VideoPlaybackTest + { + [Test] + public void ValidVideoPlaybackTest() + { + ExtendedYouTubeService service = new ExtendedYouTubeService(); + VideoPlayback info = service.VideoPlayback.List("VC5-YkjMHuw").Execute(); + Assert.NotNull(info); + } + } +} \ No newline at end of file diff --git a/YouTube.API.Test/WatchLaterTest.cs b/YouTube.API.Test/WatchLaterTest.cs index df810c0..37516a7 100644 --- a/YouTube.API.Test/WatchLaterTest.cs +++ b/YouTube.API.Test/WatchLaterTest.cs @@ -1,7 +1,4 @@ using System; -using System.Collections.Generic; -using System.Text; -using Google.Apis.Auth.OAuth2; using Google.Apis.Services; using Google.Apis.YouTube.v3.Data; using Newtonsoft.Json; @@ -11,44 +8,44 @@ using YouTube.Resources; namespace YouTube.API.Test { - public class WatchLaterTest - { - const string testVideoId = "NkGbcQwWxqk"; - ExtendedYouTubeService service; + public class WatchLaterTest + { + const string testVideoId = "NkGbcQwWxqk"; + ExtendedYouTubeService service; - [SetUp] - public void Setup() - { - var task = AuthorizationHelpers.ExchangeToken(new ClientSecrets - { - ClientId = "CLIENT_ID", - ClientSecret = "CLIENT_SECRET" - }, "SUCCESS_CODE"); - task.Wait(); + [SetUp] + public void Setup() + { + var task = AuthorizationHelpers.ExchangeToken(new Google.Apis.Auth.OAuth2.ClientSecrets + { + ClientId = "CLIENT_ID", + ClientSecret = "CLIENT_SECRET" + }, "SUCCESS_CODE"); + task.Wait(); - UserCredential credential = task.Result; - service = new ExtendedYouTubeService(new BaseClientService.Initializer - { - HttpClientInitializer = credential, - ApplicationName = "FoxTube" - }); - } + UserCredential credential = task.Result; + service = new ExtendedYouTubeService(new BaseClientService.Initializer + { + HttpClientInitializer = credential, + ApplicationName = "FoxTube" + }); + } - [Test] - public void AddVideoTest() - { - WatchLaterResource.InsertRequest request = service.WatchLater.Insert(testVideoId, "snippet"); - PlaylistItem item = request.Execute(); - Console.WriteLine(JsonConvert.SerializeObject(item)); - Assert.IsNotNull(item); - } + [Test] + public void AddVideoTest() + { + WatchLaterResource.InsertRequest request = service.WatchLater.Insert(testVideoId, "snippet"); + PlaylistItem item = request.Execute(); + Console.WriteLine(JsonConvert.SerializeObject(item)); + Assert.IsNotNull(item); + } - [Test] - public void DeleteVideoTest() - { - WatchLaterResource.DeleteRequest request = service.WatchLater.Delete(testVideoId); - request.Execute(); - Assert.Pass(); - } - } -} + [Test] + public void DeleteVideoTest() + { + WatchLaterResource.DeleteRequest request = service.WatchLater.Delete(testVideoId); + request.Execute(); + Assert.Pass(); + } + } +} \ No newline at end of file diff --git a/YouTube.API/Assets/DashManifestTemplate.xml b/YouTube.API/Assets/DashManifestTemplate.xml index 3900b6f..120c43c 100644 --- a/YouTube.API/Assets/DashManifestTemplate.xml +++ b/YouTube.API/Assets/DashManifestTemplate.xml @@ -1,15 +1,15 @@  - - - - - - - - - - - - + + + + + + + + + + + + \ No newline at end of file diff --git a/YouTube.API/Extensions.cs b/YouTube.API/Extensions.cs index 991fc65..431cbcb 100644 --- a/YouTube.API/Extensions.cs +++ b/YouTube.API/Extensions.cs @@ -2,22 +2,22 @@ namespace YouTube { - internal static class Extensions - { - internal static Uri ToUri(this string str) - { - try { return new Uri(str); } - catch { return null; } - } + internal static class Extensions + { + internal static Uri ToUri(this string str) + { + try { return new Uri(str); } + catch { return null; } + } - internal static int RangeOffset(int value, int min, int max) - { - if (value < min) - return -1; - else if (value > max) - return 1; - else - return 0; - } - } -} + internal static int RangeOffset(int value, int min, int max) + { + if (value < min) + return -1; + else if (value > max) + return 1; + else + return 0; + } + } +} \ No newline at end of file diff --git a/YouTube.API/Generators/ManifestGenerator.cs b/YouTube.API/Generators/ManifestGenerator.cs index 11b830f..c624edf 100644 --- a/YouTube.API/Generators/ManifestGenerator.cs +++ b/YouTube.API/Generators/ManifestGenerator.cs @@ -17,210 +17,210 @@ using YoutubeExplode.Models.MediaStreams; namespace YouTube.Generators { - internal class ManifestGenerator - { - IClientService ClientService { get; } - YoutubeClient Client { get; } - string Id { get; } - Video Meta { get; set; } - MediaStreamInfoSet UrlsSet { get; set; } + internal class ManifestGenerator + { + IClientService ClientService { get; } + YoutubeClient Client { get; } + string Id { get; } + Video Meta { get; set; } + MediaStreamInfoSet UrlsSet { get; set; } - public ManifestGenerator(IClientService service, string id) - { - ClientService = service; - Id = id; - Client = new YoutubeClient(service.HttpClient); - } + public ManifestGenerator(IClientService service, string id) + { + ClientService = service; + Id = id; + Client = new YoutubeClient(service.HttpClient); + } - public async Task> GenerateManifestsAsync() - { - Meta = await Client.GetVideoAsync(Id); + public async Task> GenerateManifestsAsync() + { + Meta = await Client.GetVideoAsync(Id); - if (Meta == null) - throw new FileNotFoundException("Video not found. Check video ID and visibility preferences"); + if (Meta == null) + throw new FileNotFoundException("Video not found. Check video ID and visibility preferences"); - UrlsSet = await Client.GetVideoMediaStreamInfosAsync(Id); + UrlsSet = await Client.GetVideoMediaStreamInfosAsync(Id); - if (!string.IsNullOrWhiteSpace(UrlsSet.HlsLiveStreamUrl)) - throw new NotSupportedException("This is livestream. Use 'YouTubeClient.VideoPlayback.List()' to get playback URLs"); + if (!string.IsNullOrWhiteSpace(UrlsSet.HlsLiveStreamUrl)) + throw new NotSupportedException("This is livestream. Use 'YouTubeClient.VideoPlayback.List()' to get playback URLs"); - List list = new List - { - await GenerateManifest("Auto") - }; - foreach (string i in UrlsSet.GetAllVideoQualityLabels()) - list.Add(await GenerateManifest(i)); - - return list.AsReadOnly(); - } + List list = new List + { + await GenerateManifest("Auto") + }; + foreach (string i in UrlsSet.GetAllVideoQualityLabels()) + list.Add(await GenerateManifest(i)); - async Task GenerateManifest(string quality) - { - XmlDocument manifest = new XmlDocument(); - manifest.LoadXml(Properties.Resources.DashManifestTemplate); + return list.AsReadOnly(); + } - manifest["MPD"].SetAttribute("mediaPresentationDuration", XmlConvert.ToString(Meta.Duration)); + async Task GenerateManifest(string quality) + { + XmlDocument manifest = new XmlDocument(); + manifest.LoadXml(Properties.Resources.DashManifestTemplate); - StreamInfo streamInfo = await GetInfoAsync(quality); + manifest["MPD"].SetAttribute("mediaPresentationDuration", XmlConvert.ToString(Meta.Duration)); - foreach (var i in streamInfo.Video) - { - string rep = GetVideoRepresentation(i); - manifest.GetElementsByTagName("ContentComponent")[0].InnerXml += rep; - } + StreamInfo streamInfo = await GetInfoAsync(quality); - foreach (var i in streamInfo.Audio) - manifest.GetElementsByTagName("ContentComponent")[1].InnerXml += GetAudioRepresentation(i); + foreach (var i in streamInfo.Video) + { + string rep = GetVideoRepresentation(i); + manifest.GetElementsByTagName("ContentComponent")[0].InnerXml += rep; + } - return new DashManifest(quality, manifest); - } + foreach (var i in streamInfo.Audio) + manifest.GetElementsByTagName("ContentComponent")[1].InnerXml += GetAudioRepresentation(i); - string GetVideoRepresentation(StreamInfo.VideoInfo info) => - $@" + return new DashManifest(quality, manifest); + } + + string GetVideoRepresentation(StreamInfo.VideoInfo info) => + $@" {WebUtility.UrlEncode(info.Url)} "; - string GetAudioRepresentation(StreamInfo.AudioInfo info) => - $@" + string GetAudioRepresentation(StreamInfo.AudioInfo info) => + $@" {WebUtility.UrlEncode(info.Url)} "; - async Task GetInfoAsync(string quality) - { - StreamInfo info = new StreamInfo(); + async Task GetInfoAsync(string quality) + { + StreamInfo info = new StreamInfo(); - string response = await ClientService.HttpClient.GetStringAsync($"https://youtube.com/watch?v={Id}&disable_polymer=true&bpctr=9999999999&hl=en"); - IHtmlDocument videoEmbedPageHtml = new HtmlParser().ParseDocument(response); + string response = await ClientService.HttpClient.GetStringAsync($"https://youtube.com/watch?v={Id}&disable_polymer=true&bpctr=9999999999&hl=en"); + IHtmlDocument videoEmbedPageHtml = new HtmlParser().ParseDocument(response); - #region I don't know what the fuck is this - string playerConfigRaw = Regex.Match(videoEmbedPageHtml.Source.Text, - @"ytplayer\.config = (?\{[^\{\}]*(((?\{)[^\{\}]*)+((?\})[^\{\}]*)+)*(?(Open)(?!))\})") - .Groups["Json"].Value; - JToken playerConfigJson = JToken.Parse(playerConfigRaw); + #region I don't know what the fuck is this + string playerConfigRaw = Regex.Match(videoEmbedPageHtml.Source.Text, + @"ytplayer\.config = (?\{[^\{\}]*(((?\{)[^\{\}]*)+((?\})[^\{\}]*)+)*(?(Open)(?!))\})") + .Groups["Json"].Value; + JToken playerConfigJson = JToken.Parse(playerConfigRaw); - var playerResponseRaw = playerConfigJson.SelectToken("args.player_response").Value(); - JToken playerResponseJson = JToken.Parse(playerResponseRaw); - string errorReason = playerResponseJson.SelectToken("playabilityStatus.reason")?.Value(); - if (!string.IsNullOrWhiteSpace(errorReason)) - throw new InvalidDataException($"Video [{Id}] is unplayable. Reason: {errorReason}"); + var playerResponseRaw = playerConfigJson.SelectToken("args.player_response").Value(); + JToken playerResponseJson = JToken.Parse(playerResponseRaw); + string errorReason = playerResponseJson.SelectToken("playabilityStatus.reason")?.Value(); + if (!string.IsNullOrWhiteSpace(errorReason)) + throw new InvalidDataException($"Video [{Id}] is unplayable. Reason: {errorReason}"); - List> adaptiveStreamInfosUrl = playerConfigJson.SelectToken("args.adaptive_fmts")?.Value().Split(',').Select(SplitQuery).ToList(); - List> video = - quality == "Auto" ? - adaptiveStreamInfosUrl.FindAll(i => i.ContainsKey("quality_label")) : - adaptiveStreamInfosUrl.FindAll(i => i.ContainsValue(quality.Substring(0, quality.IndexOf('p')))); - List> audio = adaptiveStreamInfosUrl.FindAll(i => i.ContainsKey("audio_sample_rate")); - #endregion + List> adaptiveStreamInfosUrl = playerConfigJson.SelectToken("args.adaptive_fmts")?.Value().Split(',').Select(SplitQuery).ToList(); + List> video = + quality == "Auto" ? + adaptiveStreamInfosUrl.FindAll(i => i.ContainsKey("quality_label")) : + adaptiveStreamInfosUrl.FindAll(i => i.ContainsValue(quality.Substring(0, quality.IndexOf('p')))); + List> audio = adaptiveStreamInfosUrl.FindAll(i => i.ContainsKey("audio_sample_rate")); + #endregion - foreach (var i in video) - info.Video.Add(new StreamInfo.VideoInfo - { - IndexRange = i["index"], - Url = i["url"], - Itag = i["itag"], - Fps = i["fps"], - Height = i["size"].Split('x')[1], - Width = i["size"].Split('x')[0], - Codecs = i["type"].Split('"')[1], - MimeType = i["type"].Split(';')[0], - Label = i["quality_label"] - }); + foreach (var i in video) + info.Video.Add(new StreamInfo.VideoInfo + { + IndexRange = i["index"], + Url = i["url"], + Itag = i["itag"], + Fps = i["fps"], + Height = i["size"].Split('x')[1], + Width = i["size"].Split('x')[0], + Codecs = i["type"].Split('"')[1], + MimeType = i["type"].Split(';')[0], + Label = i["quality_label"] + }); - foreach (var i in audio) - info.Audio.Add(new StreamInfo.AudioInfo - { - ChannelsCount = i["audio_channels"], - IndexRange = i["index"], - SampleRate = i["audio_sample_rate"], - Codecs = i["type"].Split('"')[1], - MimeType = i["type"].Split(';')[0], - Url = i["url"], - Itag = i["itag"] - }); + foreach (var i in audio) + info.Audio.Add(new StreamInfo.AudioInfo + { + ChannelsCount = i["audio_channels"], + IndexRange = i["index"], + SampleRate = i["audio_sample_rate"], + Codecs = i["type"].Split('"')[1], + MimeType = i["type"].Split(';')[0], + Url = i["url"], + Itag = i["itag"] + }); - return info; - } + return info; + } - /// - /// I don't know what the fuck is this either - /// - public Dictionary SplitQuery(string query) - { - Dictionary dic = new Dictionary(StringComparer.OrdinalIgnoreCase); - string[] paramsEncoded = query.TrimStart('?').Split('&'); - foreach (string paramEncoded in paramsEncoded) - { - string param = WebUtility.UrlDecode(paramEncoded); + /// + /// I don't know what the fuck is this either + /// + public Dictionary SplitQuery(string query) + { + Dictionary dic = new Dictionary(StringComparer.OrdinalIgnoreCase); + string[] paramsEncoded = query.TrimStart('?').Split('&'); + foreach (string paramEncoded in paramsEncoded) + { + string param = WebUtility.UrlDecode(paramEncoded); - // Look for the equals sign - int equalsPos = param.IndexOf('='); - if (equalsPos <= 0) - continue; + // Look for the equals sign + int equalsPos = param.IndexOf('='); + if (equalsPos <= 0) + continue; - // Get the key and value - string key = param.Substring(0, equalsPos); - string value = equalsPos < param.Length - ? param.Substring(equalsPos + 1) - : string.Empty; + // Get the key and value + string key = param.Substring(0, equalsPos); + string value = equalsPos < param.Length + ? param.Substring(equalsPos + 1) + : string.Empty; - // Add to dictionary - dic[key] = value; - } + // Add to dictionary + dic[key] = value; + } - return dic; - } + return dic; + } - string GetBandwidth(string quality) => - quality.Split('p')[0] switch - { - "4320" => "16763040‬", - "3072" => "11920384", - "2880" => "11175360", - "2160" => "8381520", - "1440" => "5587680‬", - "1080" => "4190760", - "720" => "2073921", - "480" => "869460", - "360" => "686521", - "240" => "264835", - _ => "100000", - }; + string GetBandwidth(string quality) => + quality.Split('p')[0] switch + { + "4320" => "16763040‬", + "3072" => "11920384", + "2880" => "11175360", + "2160" => "8381520", + "1440" => "5587680‬", + "1080" => "4190760", + "720" => "2073921", + "480" => "869460", + "360" => "686521", + "240" => "264835", + _ => "100000", + }; - class StreamInfo - { - public class VideoInfo - { - public string IndexRange { get; set; } - public string InitRange => $"0-{int.Parse(IndexRange.Split('-')[0]) - 1}"; - public string Itag { get; set; } - public string Fps { get; set; } - public string Url { get; set; } - public string Codecs { get; set; } - public string MimeType { get; set; } - public string Height { get; set; } - public string Width { get; set; } - public string Label { get; set; } - } - public class AudioInfo - { - public string IndexRange { get; set; } - public string InitRange => $"0-{int.Parse(IndexRange.Split('-')[0]) - 1}"; - public string SampleRate { get; set; } - public string ChannelsCount { get; set; } - public string Codecs { get; set; } - public string MimeType { get; set; } - public string Url { get; set; } - public string Itag { get; set; } - } + class StreamInfo + { + public class VideoInfo + { + public string IndexRange { get; set; } + public string InitRange => $"0-{int.Parse(IndexRange.Split('-')[0]) - 1}"; + public string Itag { get; set; } + public string Fps { get; set; } + public string Url { get; set; } + public string Codecs { get; set; } + public string MimeType { get; set; } + public string Height { get; set; } + public string Width { get; set; } + public string Label { get; set; } + } + public class AudioInfo + { + public string IndexRange { get; set; } + public string InitRange => $"0-{int.Parse(IndexRange.Split('-')[0]) - 1}"; + public string SampleRate { get; set; } + public string ChannelsCount { get; set; } + public string Codecs { get; set; } + public string MimeType { get; set; } + public string Url { get; set; } + public string Itag { get; set; } + } - public List Video { get; } = new List(); - public List Audio { get; } = new List(); - } - } -} + public List Video { get; } = new List(); + public List Audio { get; } = new List(); + } + } +} \ No newline at end of file diff --git a/YouTube.API/Models/ClosedCaptionInfo.cs b/YouTube.API/Models/ClosedCaptionInfo.cs index 9eb4fc3..d3af9f0 100644 --- a/YouTube.API/Models/ClosedCaptionInfo.cs +++ b/YouTube.API/Models/ClosedCaptionInfo.cs @@ -3,12 +3,12 @@ using YoutubeExplode.Models.ClosedCaptions; namespace YouTube.Models { - public class ClosedCaptionInfo - { - public CultureInfo Language { get; set; } - public string Url { get; set; } - public bool AutoGenerated { get; set; } + public class ClosedCaptionInfo + { + public CultureInfo Language { get; set; } + public string Url { get; set; } + public bool AutoGenerated { get; set; } - internal ClosedCaptionTrackInfo TrackInfo { get; set; } - } -} + internal ClosedCaptionTrackInfo TrackInfo { get; set; } + } +} \ No newline at end of file diff --git a/YouTube.API/Models/ClosedCaptionTrack.cs b/YouTube.API/Models/ClosedCaptionTrack.cs index 418aa20..ae55b7a 100644 --- a/YouTube.API/Models/ClosedCaptionTrack.cs +++ b/YouTube.API/Models/ClosedCaptionTrack.cs @@ -4,16 +4,16 @@ using System.Text; namespace YouTube.Models { - public class ClosedCaptionTrack - { - public ClosedCaptionInfo Info { get; set; } - public IReadOnlyList Captions { get; set; } + public class ClosedCaptionTrack + { + public ClosedCaptionInfo Info { get; set; } + public IReadOnlyList Captions { get; set; } - public class ClosedCaption - { - public TimeSpan Offset { get; set; } - public TimeSpan Duration { get; set; } - public string Content { get; set; } - } - } -} + public class ClosedCaption + { + public TimeSpan Offset { get; set; } + public TimeSpan Duration { get; set; } + public string Content { get; set; } + } + } +} \ No newline at end of file diff --git a/YouTube.API/Models/DashManifest.cs b/YouTube.API/Models/DashManifest.cs index f09654d..5e235d6 100644 --- a/YouTube.API/Models/DashManifest.cs +++ b/YouTube.API/Models/DashManifest.cs @@ -4,22 +4,22 @@ using System.Xml; namespace YouTube.Models { - public class DashManifest - { - public string Label { get; } - public DateTime ValidUntil { get; } - public DashManifest(string label, XmlDocument doc) - { - Label = label; - Xml = doc; - } + public class DashManifest + { + public string Label { get; } + public DateTime ValidUntil { get; } + public DashManifest(string label, XmlDocument doc) + { + Label = label; + Xml = doc; + } - public string ManifestContent => Xml.OuterXml; - public XmlDocument Xml { get; } - public Uri WriteManifest(FileStream outStream) - { - Xml.Save(outStream); - return new Uri(outStream.Name); - } - } -} + public string ManifestContent => Xml.OuterXml; + public XmlDocument Xml { get; } + public Uri WriteManifest(FileStream outStream) + { + Xml.Save(outStream); + return new Uri(outStream.Name); + } + } +} \ No newline at end of file diff --git a/YouTube.API/Models/PlaybackUrl.cs b/YouTube.API/Models/PlaybackUrl.cs index e740d6b..d31a0da 100644 --- a/YouTube.API/Models/PlaybackUrl.cs +++ b/YouTube.API/Models/PlaybackUrl.cs @@ -1,48 +1,46 @@ -using System.Drawing; - -namespace YouTube.Models +namespace YouTube.Models { - public enum VideoFormat - { - /// - /// MPEG-4 Part 2. - /// - Mp4V = 0, - H263 = 1, - /// - /// MPEG-4 Part 10, H264, Advanced Video Coding (AVC). - /// - H264 = 2, - Vp8 = 3, - Vp9 = 4, - Av1 = 5 - } - public enum AudioFormat - { - /// - /// MPEG-4 Part 3, Advanced Audio Coding (AAC). - /// - Aac = 0, - Vorbis = 1, - Opus = 2 - } - public enum AudioQuality { Low, Medium, High } + public enum VideoFormat + { + /// + /// MPEG-4 Part 2. + /// + Mp4V = 0, + H263 = 1, + /// + /// MPEG-4 Part 10, H264, Advanced Video Coding (AVC). + /// + H264 = 2, + Vp8 = 3, + Vp9 = 4, + Av1 = 5 + } + public enum AudioFormat + { + /// + /// MPEG-4 Part 3, Advanced Audio Coding (AAC). + /// + Aac = 0, + Vorbis = 1, + Opus = 2 + } + public enum AudioQuality { Low, Medium, High } - public class VideoPlaybackUrl - { - public string Quality { get; set; } - public VideoFormat Format { get; set; } - public string Url { get; set; } - public Size Resolution { get; set; } - public bool HasAudio { get; set; } - public int Bitrate { get; set; } - } - - public class AudioPlaybackUrl - { - public AudioQuality Quality { get; set; } - public AudioFormat Format { get; set; } - public string Url { get; set; } - public int Bitrate { get; set; } - } -} + public class VideoPlaybackUrl + { + public string Quality { get; set; } + public VideoFormat Format { get; set; } + public string Url { get; set; } + public System.Drawing.Size Resolution { get; set; } + public bool HasAudio { get; set; } + public int Bitrate { get; set; } + } + + public class AudioPlaybackUrl + { + public AudioQuality Quality { get; set; } + public AudioFormat Format { get; set; } + public string Url { get; set; } + public int Bitrate { get; set; } + } +} \ No newline at end of file diff --git a/YouTube.API/Models/VideoPlayback.cs b/YouTube.API/Models/VideoPlayback.cs index 5aec033..8e94953 100644 --- a/YouTube.API/Models/VideoPlayback.cs +++ b/YouTube.API/Models/VideoPlayback.cs @@ -3,18 +3,18 @@ using System.Collections.Generic; namespace YouTube.Models { - public class VideoPlayback - { - public string Id { get; set; } - public PlaybackUrlsData PlaybackUrls { get; set; } = new PlaybackUrlsData(); - public IReadOnlyList ClosedCaptions { get; set; } + public class VideoPlayback + { + public string Id { get; set; } + public PlaybackUrlsData PlaybackUrls { get; set; } = new PlaybackUrlsData(); + public IReadOnlyList ClosedCaptions { get; set; } - public class PlaybackUrlsData - { - public IReadOnlyList Video { get; set; } - public IReadOnlyList Audio { get; set; } - public string LiveStreamUrl { get; set; } - public DateTime ValidUntil { get; set; } - } - } -} + public class PlaybackUrlsData + { + public IReadOnlyList Video { get; set; } + public IReadOnlyList Audio { get; set; } + public string LiveStreamUrl { get; set; } + public DateTime ValidUntil { get; set; } + } + } +} \ No newline at end of file diff --git a/YouTube.API/Resources/CaptionsResource.cs b/YouTube.API/Resources/CaptionsResource.cs index f421fe7..9fe8cfe 100644 --- a/YouTube.API/Resources/CaptionsResource.cs +++ b/YouTube.API/Resources/CaptionsResource.cs @@ -6,52 +6,52 @@ using YoutubeExplode; namespace YouTube.Resources { - public class CaptionsResource : Google.Apis.YouTube.v3.CaptionsResource - { - IClientService Service { get; } - public CaptionsResource(IClientService service) : base(service) => - Service = service; + public class CaptionsResource : Google.Apis.YouTube.v3.CaptionsResource + { + IClientService Service { get; } + public CaptionsResource(IClientService service) : base(service) => + Service = service; - public LoadRequest Load(ClosedCaptionInfo captionInfo) => - new LoadRequest(Service, captionInfo); + public LoadRequest Load(ClosedCaptionInfo captionInfo) => + new LoadRequest(Service, captionInfo); - public class LoadRequest - { - public ClosedCaptionInfo CaptionInfo { get; set; } - IClientService Service { get; set; } + public class LoadRequest + { + public ClosedCaptionInfo CaptionInfo { get; set; } + IClientService Service { get; set; } - public LoadRequest(IClientService service, ClosedCaptionInfo captionInfo) - { - CaptionInfo = captionInfo; - Service = service; - } + public LoadRequest(IClientService service, ClosedCaptionInfo captionInfo) + { + CaptionInfo = captionInfo; + Service = service; + } - public async Task ExecuteAsync() - { - YoutubeClient client = new YoutubeClient(Service.HttpClient); - var response = await client.GetClosedCaptionTrackAsync(CaptionInfo.TrackInfo); - List captions = new List(); - foreach (var i in response.Captions) - captions.Add(new ClosedCaptionTrack.ClosedCaption - { - Offset = i.Offset, - Duration = i.Duration, - Content = i.Text - }); + public async Task ExecuteAsync() + { + YoutubeClient client = new YoutubeClient(Service.HttpClient); + var response = await client.GetClosedCaptionTrackAsync(CaptionInfo.TrackInfo); + List captions = new List(); + foreach (var i in response.Captions) + captions.Add(new ClosedCaptionTrack.ClosedCaption + { + Offset = i.Offset, + Duration = i.Duration, + Content = i.Text + }); - return new ClosedCaptionTrack - { - Info = CaptionInfo, - Captions = captions.AsReadOnly() - }; - } + return new ClosedCaptionTrack + { + Info = CaptionInfo, + Captions = captions.AsReadOnly() + }; + } - public ClosedCaptionTrack Execute() - { - Task task = ExecuteAsync(); - task.Wait(); - return task.Result; - } - } - } -} + public ClosedCaptionTrack Execute() + { + Task task = ExecuteAsync(); + task.Wait(); + return task.Result; + } + } + } +} \ No newline at end of file diff --git a/YouTube.API/Resources/DashManifestsResource.cs b/YouTube.API/Resources/DashManifestsResource.cs index b54710b..00c31e8 100644 --- a/YouTube.API/Resources/DashManifestsResource.cs +++ b/YouTube.API/Resources/DashManifestsResource.cs @@ -6,39 +6,39 @@ using YouTube.Models; namespace YouTube.Resources { - public class DashManifestsResource - { - IClientService Service { get; } - public DashManifestsResource(IClientService service) => - Service = service; + public class DashManifestsResource + { + IClientService Service { get; } + public DashManifestsResource(IClientService service) => + Service = service; - public ListRequest List(string videoId) => - new ListRequest(Service, videoId); + public ListRequest List(string videoId) => + new ListRequest(Service, videoId); - public class ListRequest - { - public string Id { get; set; } - IClientService Service { get; set; } + public class ListRequest + { + public string Id { get; set; } + IClientService Service { get; set; } - public ListRequest(IClientService service, string id) - { - Id = id; - Service = service; - } + public ListRequest(IClientService service, string id) + { + Id = id; + Service = service; + } - public async Task> ExecuteAsync() - { - ManifestGenerator generator = new ManifestGenerator(Service, Id); + public async Task> ExecuteAsync() + { + ManifestGenerator generator = new ManifestGenerator(Service, Id); - return await generator.GenerateManifestsAsync(); - } + return await generator.GenerateManifestsAsync(); + } - public IReadOnlyList Execute() - { - Task> task = ExecuteAsync(); - task.Wait(); - return task.Result; - } - } - } -} + public IReadOnlyList Execute() + { + Task> task = ExecuteAsync(); + task.Wait(); + return task.Result; + } + } + } +} \ No newline at end of file diff --git a/YouTube.API/Resources/HistoryResource.cs b/YouTube.API/Resources/HistoryResource.cs index 5950d81..0be8e61 100644 --- a/YouTube.API/Resources/HistoryResource.cs +++ b/YouTube.API/Resources/HistoryResource.cs @@ -6,31 +6,31 @@ using Google.Apis.YouTube.v3.Data; namespace YouTube.Resources { - public class HistoryResource - { - public class ListRequest { } - public class InsertRequest { } - public class DeleteRequest { } - public class ClearRequest { } + public class HistoryResource + { + public class ListRequest { } + public class InsertRequest { } + public class DeleteRequest { } + public class ClearRequest { } - public ListRequest List() - { - return new ListRequest(); - } + public ListRequest List() + { + return new ListRequest(); + } - public InsertRequest Insert(string videoId, TimeSpan? leftOn) - { - return new InsertRequest(); - } + public InsertRequest Insert(string videoId, TimeSpan? leftOn) + { + return new InsertRequest(); + } - public DeleteRequest Delete(string videoId) - { - return new DeleteRequest(); - } + public DeleteRequest Delete(string videoId) + { + return new DeleteRequest(); + } - public ClearRequest Clear() - { - return new ClearRequest(); - } - } -} + public ClearRequest Clear() + { + return new ClearRequest(); + } + } +} \ No newline at end of file diff --git a/YouTube.API/Resources/VideoPlaybackResource.cs b/YouTube.API/Resources/VideoPlaybackResource.cs index ae05805..b7635f8 100644 --- a/YouTube.API/Resources/VideoPlaybackResource.cs +++ b/YouTube.API/Resources/VideoPlaybackResource.cs @@ -10,102 +10,102 @@ using YoutubeExplode.Models.MediaStreams; namespace YouTube.Resources { - public class VideoPlaybackResource - { - IClientService ClientService { get; } - public VideoPlaybackResource(IClientService clientService) => - ClientService = clientService; + public class VideoPlaybackResource + { + IClientService ClientService { get; } + public VideoPlaybackResource(IClientService clientService) => + ClientService = clientService; - public ListRequest List(string videoId) => - new ListRequest(ClientService, videoId); + public ListRequest List(string videoId) => + new ListRequest(ClientService, videoId); - public class ListRequest - { - IClientService Service { get; } + public class ListRequest + { + IClientService Service { get; } - public string Id { get; set; } + public string Id { get; set; } - public async Task ExecuteAsync() - { - VideoPlayback item = new VideoPlayback(); - YoutubeClient client = new YoutubeClient(Service.HttpClient); - MediaStreamInfoSet streamSet = await client.GetVideoMediaStreamInfosAsync(Id); - item.Id = Id; - item.PlaybackUrls.ValidUntil = streamSet.ValidUntil.DateTime; + public async Task ExecuteAsync() + { + VideoPlayback item = new VideoPlayback(); + YoutubeClient client = new YoutubeClient(Service.HttpClient); + MediaStreamInfoSet streamSet = await client.GetVideoMediaStreamInfosAsync(Id); + item.Id = Id; + item.PlaybackUrls.ValidUntil = streamSet.ValidUntil.DateTime; - if(!string.IsNullOrWhiteSpace(streamSet.HlsLiveStreamUrl)) - { - item.PlaybackUrls.LiveStreamUrl = streamSet.HlsLiveStreamUrl; - return item; - } + if (!string.IsNullOrWhiteSpace(streamSet.HlsLiveStreamUrl)) + { + item.PlaybackUrls.LiveStreamUrl = streamSet.HlsLiveStreamUrl; + return item; + } - List audio = new List(); - foreach (AudioStreamInfo i in streamSet.Audio) - audio.Add(new AudioPlaybackUrl - { - Url = i.Url, - Bitrate = (int)i.Bitrate, - Format = (AudioFormat)i.AudioEncoding, - Quality = Extensions.RangeOffset((int)i.Bitrate / 1024, 128, 255) switch - { - -1 => AudioQuality.Low, - 1 => AudioQuality.High, - _ => AudioQuality.Medium - } - }); - item.PlaybackUrls.Audio = audio.AsReadOnly(); + List audio = new List(); + foreach (AudioStreamInfo i in streamSet.Audio) + audio.Add(new AudioPlaybackUrl + { + Url = i.Url, + Bitrate = (int)i.Bitrate, + Format = (AudioFormat)i.AudioEncoding, + Quality = Extensions.RangeOffset((int)i.Bitrate / 1024, 128, 255) switch + { + -1 => AudioQuality.Low, + 1 => AudioQuality.High, + _ => AudioQuality.Medium + } + }); + item.PlaybackUrls.Audio = audio.AsReadOnly(); - List video = new List(); - foreach (VideoStreamInfo i in streamSet.Video) - video.Add(new VideoPlaybackUrl - { - Format = (VideoFormat)i.VideoEncoding, - HasAudio = false, - Quality = i.VideoQualityLabel, - Url = i.Url, - Resolution = new Size(i.Resolution.Width, i.Resolution.Height), - Bitrate = (int)i.Bitrate - }); + List video = new List(); + foreach (VideoStreamInfo i in streamSet.Video) + video.Add(new VideoPlaybackUrl + { + Format = (VideoFormat)i.VideoEncoding, + HasAudio = false, + Quality = i.VideoQualityLabel, + Url = i.Url, + Resolution = new Size(i.Resolution.Width, i.Resolution.Height), + Bitrate = (int)i.Bitrate + }); - foreach (MuxedStreamInfo i in streamSet.Muxed) - video.Add(new VideoPlaybackUrl - { - Format = (VideoFormat)i.VideoEncoding, - HasAudio = true, - Quality = i.VideoQualityLabel, - Url = i.Url, - Resolution = new Size(i.Resolution.Width, i.Resolution.Height), - Bitrate = 0 - }); - item.PlaybackUrls.Video = video.AsReadOnly(); + foreach (MuxedStreamInfo i in streamSet.Muxed) + video.Add(new VideoPlaybackUrl + { + Format = (VideoFormat)i.VideoEncoding, + HasAudio = true, + Quality = i.VideoQualityLabel, + Url = i.Url, + Resolution = new Size(i.Resolution.Width, i.Resolution.Height), + Bitrate = 0 + }); + item.PlaybackUrls.Video = video.AsReadOnly(); - var ccSet = await client.GetVideoClosedCaptionTrackInfosAsync(Id); + var ccSet = await client.GetVideoClosedCaptionTrackInfosAsync(Id); - List captions = new List(); - foreach (ClosedCaptionTrackInfo i in ccSet) - captions.Add(new ClosedCaptionInfo - { - AutoGenerated = i.IsAutoGenerated, - Url = i.Url, - Language = new CultureInfo(i.Language.Code), - TrackInfo = i - }); - item.ClosedCaptions = captions.AsReadOnly(); + List captions = new List(); + foreach (ClosedCaptionTrackInfo i in ccSet) + captions.Add(new ClosedCaptionInfo + { + AutoGenerated = i.IsAutoGenerated, + Url = i.Url, + Language = new CultureInfo(i.Language.Code), + TrackInfo = i + }); + item.ClosedCaptions = captions.AsReadOnly(); - return item; - } + return item; + } - public VideoPlayback Execute() - { - Task task = ExecuteAsync(); - task.Wait(); - return task.Result; - } - public ListRequest(IClientService service, string id) - { - Id = id; - Service = service; - } - } - } -} + public VideoPlayback Execute() + { + Task task = ExecuteAsync(); + task.Wait(); + return task.Result; + } + public ListRequest(IClientService service, string id) + { + Id = id; + Service = service; + } + } + } +} \ No newline at end of file diff --git a/YouTube.API/Resources/WatchLaterResource.cs b/YouTube.API/Resources/WatchLaterResource.cs index b96009a..096537d 100644 --- a/YouTube.API/Resources/WatchLaterResource.cs +++ b/YouTube.API/Resources/WatchLaterResource.cs @@ -13,97 +13,97 @@ using System.Threading.Tasks; namespace YouTube.Resources { - public class WatchLaterResource - { - IClientService Service { get; } + public class WatchLaterResource + { + IClientService Service { get; } - public WatchLaterResource(IClientService service) => - Service = service; + public WatchLaterResource(IClientService service) => + Service = service; - public ListRequest List() - { - return new ListRequest(); - } + public ListRequest List() + { + return new ListRequest(); + } - public InsertRequest Insert(string videoId, string part) => - new InsertRequest(Service, videoId, part); + public InsertRequest Insert(string videoId, string part) => + new InsertRequest(Service, videoId, part); - public DeleteRequest Delete(string videoId) => - new DeleteRequest(Service, videoId); + public DeleteRequest Delete(string videoId) => + new DeleteRequest(Service, videoId); - public class ListRequest { } - public class InsertRequest - { - IClientService Service { get; set; } - public string Id { get; set; } - public string Part { get; set; } + public class ListRequest { } + public class InsertRequest + { + IClientService Service { get; set; } + public string Id { get; set; } + public string Part { get; set; } - public InsertRequest(IClientService service, string videoId, string part) - { - Service = service; - Id = videoId; - Part = part; - } + public InsertRequest(IClientService service, string videoId, string part) + { + Service = service; + Id = videoId; + Part = part; + } - public async Task ExecuteAsync() - { - PlaylistItem playlist = new PlaylistItem - { - Snippet = new PlaylistItemSnippet - { - PlaylistId = "WL", - ResourceId = new ResourceId - { - VideoId = Id, - Kind = "youtube#video" - } - } - }; - PlaylistItemsResource.InsertRequest request = (Service as YouTubeService).PlaylistItems.Insert(playlist, Part); + public async Task ExecuteAsync() + { + PlaylistItem playlist = new PlaylistItem + { + Snippet = new PlaylistItemSnippet + { + PlaylistId = "WL", + ResourceId = new ResourceId + { + VideoId = Id, + Kind = "youtube#video" + } + } + }; + PlaylistItemsResource.InsertRequest request = (Service as YouTubeService).PlaylistItems.Insert(playlist, Part); - return await request.ExecuteAsync(); - } + return await request.ExecuteAsync(); + } - public PlaylistItem Execute() - { - Task task = ExecuteAsync(); - task.Wait(); - return task.Result; - } - } - public class DeleteRequest - { - IClientService Service { get; set; } - public string Id { get; set; } + public PlaylistItem Execute() + { + Task task = ExecuteAsync(); + task.Wait(); + return task.Result; + } + } + public class DeleteRequest + { + IClientService Service { get; set; } + public string Id { get; set; } - public DeleteRequest(IClientService service, string videoId) - { - Service = service; - Id = videoId; - } + public DeleteRequest(IClientService service, string videoId) + { + Service = service; + Id = videoId; + } - public async Task ExecuteAsync() - { - ConfigurableHttpClient client = Service.HttpClient; - string data = await client.GetStringAsync($"https://youtube.com/watch?v={Id}&disable_polymer=true&bpctr=9999999999&hl=en"); - string plid = Regex.Match(data, @"(?<=plid=).?\w+").Value; - IHtmlDocument html = await new HtmlParser().ParseDocumentAsync(data); - string sessionToken = html.GetElementsByTagName("input").FirstOrDefault(i => i.GetAttribute("name") == "session_token")?.GetAttribute("value"); - Dictionary body = new Dictionary - { - { "video_ids", Id }, - { "full_list_id", "WL" }, - { "plid", plid }, - { "session_token", sessionToken } - }; - HttpResponseMessage response = await client.PostAsync("https://www.youtube.com/playlist_video_ajax?action_delete_from_playlist=1", new FormUrlEncodedContent(body)); - string responseStr = await response.Content.ReadAsStringAsync(); - if (!responseStr.Contains("SUCCESS")) - throw new Exception(responseStr); - } + public async Task ExecuteAsync() + { + ConfigurableHttpClient client = Service.HttpClient; + string data = await client.GetStringAsync($"https://youtube.com/watch?v={Id}&disable_polymer=true&bpctr=9999999999&hl=en"); + string plid = Regex.Match(data, @"(?<=plid=).?\w+").Value; + IHtmlDocument html = await new HtmlParser().ParseDocumentAsync(data); + string sessionToken = html.GetElementsByTagName("input").FirstOrDefault(i => i.GetAttribute("name") == "session_token")?.GetAttribute("value"); + Dictionary body = new Dictionary + { + { "video_ids", Id }, + { "full_list_id", "WL" }, + { "plid", plid }, + { "session_token", sessionToken } + }; + HttpResponseMessage response = await client.PostAsync("https://www.youtube.com/playlist_video_ajax?action_delete_from_playlist=1", new FormUrlEncodedContent(body)); + string responseStr = await response.Content.ReadAsStringAsync(); + if (!responseStr.Contains("SUCCESS")) + throw new Exception(responseStr); + } - public void Execute() => - ExecuteAsync().Wait(); - } - } -} + public void Execute() => + ExecuteAsync().Wait(); + } + } +} \ No newline at end of file diff --git a/YouTube.API/VideoQuality.cs b/YouTube.API/VideoQuality.cs index 2938ed5..a59897d 100644 --- a/YouTube.API/VideoQuality.cs +++ b/YouTube.API/VideoQuality.cs @@ -1,42 +1,38 @@ -using System; -using System.Collections.Generic; -using System.Text; - -namespace YouTube +namespace YouTube { - public static class VideoQuality - { - public static string Auto => QualityConstants.Auto; - public static string Low144 => QualityConstants.Low144; - public static string Low240 => QualityConstants.Low240; - public static string Medium360 => QualityConstants.Medium360; - public static string Meduim480 => QualityConstants.Meduim480; - public static string High720 => QualityConstants.High720; - public static string High720p60 => QualityConstants.High720p60; - public static string High1080 => QualityConstants.High1080; - public static string High1080p60 => QualityConstants.High1080p60; - public static string High1440 => QualityConstants.High1440; - public static string High2160 => QualityConstants.High2160; - public static string High2880 => QualityConstants.High2880; - public static string High3072 => QualityConstants.High3072; - public static string High4320 => QualityConstants.High4320; + public static class VideoQuality + { + public static string Auto => QualityConstants.Auto; + public static string Low144 => QualityConstants.Low144; + public static string Low240 => QualityConstants.Low240; + public static string Medium360 => QualityConstants.Medium360; + public static string Meduim480 => QualityConstants.Meduim480; + public static string High720 => QualityConstants.High720; + public static string High720p60 => QualityConstants.High720p60; + public static string High1080 => QualityConstants.High1080; + public static string High1080p60 => QualityConstants.High1080p60; + public static string High1440 => QualityConstants.High1440; + public static string High2160 => QualityConstants.High2160; + public static string High2880 => QualityConstants.High2880; + public static string High3072 => QualityConstants.High3072; + public static string High4320 => QualityConstants.High4320; - public static class QualityConstants - { - public const string Auto = "auto"; - public const string Low144 = "144p"; - public const string Low240 = "240p"; - public const string Medium360 = "360p"; - public const string Meduim480 = "480p"; - public const string High720 = "720p"; - public const string High720p60 = "720p60"; - public const string High1080 = "1080p"; - public const string High1080p60 = "1080p60"; - public const string High1440 = "1440p"; - public const string High2160 = "2160p"; - public const string High2880 = "2880p"; - public const string High3072 = "3072p"; - public const string High4320 = "4320p"; - } - } -} + public static class QualityConstants + { + public const string Auto = "auto"; + public const string Low144 = "144p"; + public const string Low240 = "240p"; + public const string Medium360 = "360p"; + public const string Meduim480 = "480p"; + public const string High720 = "720p"; + public const string High720p60 = "720p60"; + public const string High1080 = "1080p"; + public const string High1080p60 = "1080p60"; + public const string High1440 = "1440p"; + public const string High2160 = "2160p"; + public const string High2880 = "2880p"; + public const string High3072 = "3072p"; + public const string High4320 = "4320p"; + } + } +} \ No newline at end of file diff --git a/YouTube.API/YouTube.API.csproj b/YouTube.API/YouTube.API.csproj index 149dd95..d096a51 100644 --- a/YouTube.API/YouTube.API.csproj +++ b/YouTube.API/YouTube.API.csproj @@ -26,7 +26,7 @@ - + diff --git a/YouTube.API/YouTubeService.cs b/YouTube.API/YouTubeService.cs index 5f22dc9..569446c 100644 --- a/YouTube.API/YouTubeService.cs +++ b/YouTube.API/YouTubeService.cs @@ -2,17 +2,17 @@ namespace YouTube { - public partial class ExtendedYouTubeService : Google.Apis.YouTube.v3.YouTubeService - { - public DashManifestsResource DashManifests => new DashManifestsResource(this); - public VideoPlaybackResource VideoPlayback => new VideoPlaybackResource(this); - public new CaptionsResource Captions => new CaptionsResource(this); - public HistoryResource History { get; } - public WatchLaterResource WatchLater => new WatchLaterResource(this); - // TODO: Add Activities override for recomendations and subscriptions - - public ExtendedYouTubeService() : base() { } + public partial class ExtendedYouTubeService : Google.Apis.YouTube.v3.YouTubeService + { + public DashManifestsResource DashManifests => new DashManifestsResource(this); + public VideoPlaybackResource VideoPlayback => new VideoPlaybackResource(this); + public new CaptionsResource Captions => new CaptionsResource(this); + public HistoryResource History { get; } + public WatchLaterResource WatchLater => new WatchLaterResource(this); + // TODO: Add Activities override for recomendations and subscriptions - public ExtendedYouTubeService(Initializer initializer) : base(initializer) { } - } -} + public ExtendedYouTubeService() : base() { } + + public ExtendedYouTubeService(Initializer initializer) : base(initializer) { } + } +} \ No newline at end of file