From cd2d6949b62b16e52a2cea2809a4c7cadff6060f Mon Sep 17 00:00:00 2001 From: zone117x Date: Sat, 18 Apr 2015 14:18:14 -0600 Subject: [PATCH] Grabbing show names from Sonarr API, finished with BitMeTV --- src/Jackett/Indexers/BitMeTV.cs | 82 +++++++++--------- src/Jackett/Indexers/ThePirateBay.cs | 123 ++++++++++++++------------- src/Jackett/Server.cs | 7 +- src/Jackett/SonarApi.cs | 47 ++++++++-- src/Jackett/TorznabQuery.cs | 23 ++++- src/Jackett/WebContent/index.html | 6 +- 6 files changed, 174 insertions(+), 114 deletions(-) diff --git a/src/Jackett/Indexers/BitMeTV.cs b/src/Jackett/Indexers/BitMeTV.cs index d32bdcc8e..71fbd9559 100644 --- a/src/Jackett/Indexers/BitMeTV.cs +++ b/src/Jackett/Indexers/BitMeTV.cs @@ -133,53 +133,57 @@ namespace Jackett public async Task PerformQuery(TorznabQuery query) { - List releases = new List(); - var searchUrl = string.Format("{0}?search={1}&cat=0", SearchUrl, HttpUtility.UrlEncode("game of thrones s03e09")); - var results = await client.GetStringAsync(searchUrl); - CQ dom = results; - - var table = dom["tbody > tr > .latest"].Parent().Parent(); - - foreach (var row in table.Children().Skip(1)) + foreach (var title in query.ShowTitles) { - var release = new ReleaseInfo(); - CQ qRow = row.Cq(); - CQ qDetailsCol = row.ChildElements.ElementAt(1).Cq(); - CQ qLink = qDetailsCol.Children("a").First(); + var searchString = title + " " + query.GetEpisodeSearchString(); + var searchUrl = string.Format("{0}?search={1}&cat=0", SearchUrl, HttpUtility.UrlEncode(searchString)); + var results = await client.GetStringAsync(searchUrl); + CQ dom = results; - release.MinimumRatio = 1; - release.MinimumSeedTime = 172800; - release.Comments = new Uri(BaseUrl + "/" + qLink.Attr("href")); - release.Guid = release.Comments; - release.Title = qLink.Attr("title"); - release.Description = release.Title; + var table = dom["tbody > tr > .latest"].Parent().Parent(); - //"Tuesday, June 11th 2013 at 03:52:53 AM" to... - //"Tuesday June 11 2013 03 52 53 AM" - var timestamp = qDetailsCol.Children("font").Text().Trim() + " "; - var groups = new Regex(@"(.*?), (.*?) (.*?)th (.*?) at (.*?):(.*?):(.*?) (.*?) ").Match(timestamp).Groups; - var str = string.Join(" ", groups.Cast().Skip(1).Select(g => g.Value)); - release.PublishDate = DateTime.ParseExact(str, "dddd MMMM d yyyy hh mm ss tt", CultureInfo.InvariantCulture); - - release.Link = new Uri(BaseUrl + "/" + row.ChildElements.ElementAt(2).Cq().Children("a.index").Attr("href")); - - var sizeCol = row.ChildElements.ElementAt(6); - var sizeVal = float.Parse(sizeCol.ChildNodes[0].NodeValue); - var sizeUnit = sizeCol.ChildNodes[2].NodeValue; - - switch (sizeUnit) + foreach (var row in table.Children().Skip(1)) { - case "GB": release.Size = ReleaseInfo.BytesFromGB(sizeVal); break; - case "MB": release.Size = ReleaseInfo.BytesFromMB(sizeVal); break; - case "KB": release.Size = ReleaseInfo.BytesFromKB(sizeVal); break; - } + var release = new ReleaseInfo(); - release.Seeders = int.Parse(row.ChildElements.ElementAt(8).Cq().Text()); - release.Peers = int.Parse(row.ChildElements.ElementAt(9).Cq().Text()) + release.Seeders; - releases.Add(release); + CQ qRow = row.Cq(); + CQ qDetailsCol = row.ChildElements.ElementAt(1).Cq(); + CQ qLink = qDetailsCol.Children("a").First(); + + release.MinimumRatio = 1; + release.MinimumSeedTime = 172800; + release.Comments = new Uri(BaseUrl + "/" + qLink.Attr("href")); + release.Guid = release.Comments; + release.Title = qLink.Attr("title"); + release.Description = release.Title; + + //"Tuesday, June 11th 2013 at 03:52:53 AM" to... + //"Tuesday June 11 2013 03 52 53 AM" + var timestamp = qDetailsCol.Children("font").Text().Trim() + " "; + var groups = new Regex(@"(.*?), (.*?) (.*?)th (.*?) at (.*?):(.*?):(.*?) (.*?) ").Match(timestamp).Groups; + var str = string.Join(" ", groups.Cast().Skip(1).Select(g => g.Value)); + release.PublishDate = DateTime.ParseExact(str, "dddd MMMM d yyyy hh mm ss tt", CultureInfo.InvariantCulture); + + release.Link = new Uri(BaseUrl + "/" + row.ChildElements.ElementAt(2).Cq().Children("a.index").Attr("href")); + + var sizeCol = row.ChildElements.ElementAt(6); + var sizeVal = float.Parse(sizeCol.ChildNodes[0].NodeValue); + var sizeUnit = sizeCol.ChildNodes[2].NodeValue; + + switch (sizeUnit) + { + case "GB": release.Size = ReleaseInfo.BytesFromGB(sizeVal); break; + case "MB": release.Size = ReleaseInfo.BytesFromMB(sizeVal); break; + case "KB": release.Size = ReleaseInfo.BytesFromKB(sizeVal); break; + } + + release.Seeders = int.Parse(row.ChildElements.ElementAt(8).Cq().Text()); + release.Peers = int.Parse(row.ChildElements.ElementAt(9).Cq().Text()) + release.Seeders; + releases.Add(release); + } } return releases.ToArray(); diff --git a/src/Jackett/Indexers/ThePirateBay.cs b/src/Jackett/Indexers/ThePirateBay.cs index baa849c8a..e6935c5c3 100644 --- a/src/Jackett/Indexers/ThePirateBay.cs +++ b/src/Jackett/Indexers/ThePirateBay.cs @@ -120,72 +120,75 @@ namespace Jackett.Indexers { List releases = new List(); - var searchUrl = BaseUrl + string.Format(SearchUrl, HttpUtility.UrlEncode("game of thrones s05e01")); - - var message = new HttpRequestMessage + foreach (var title in query.ShowTitles) { - Method = HttpMethod.Get, - RequestUri = new Uri(BaseUrl + SwitchSingleViewUrl) - }; - message.Headers.Referrer = new Uri(searchUrl); + var searchString = title + " " + query.GetEpisodeSearchString(); + var searchUrl = BaseUrl + string.Format(SearchUrl, HttpUtility.UrlEncode(searchString)); - var response = await client.SendAsync(message); - var results = await response.Content.ReadAsStringAsync(); - - CQ dom = results; - - var rows = dom["#searchResult > tbody > tr"]; - foreach (var row in rows) - { - var release = new ReleaseInfo(); - CQ qRow = row.Cq(); - CQ qLink = row.ChildElements.ElementAt(1).Cq().Children("a").First(); - - release.MinimumRatio = 1; - release.MinimumSeedTime = 172800; - release.Title = qLink.Text().Trim(); - release.Description = release.Title; - release.Comments = new Uri(BaseUrl + qLink.Attr("href").TrimStart('/')); - release.Guid = release.Comments; - - var timeString = row.ChildElements.ElementAt(2).Cq().Text(); - if (timeString.Contains("mins ago")) - release.PublishDate = (DateTime.Now - TimeSpan.FromMinutes(int.Parse(timeString.Split(' ')[0]))); - else if (timeString.Contains("Today")) - release.PublishDate = (DateTime.UtcNow - TimeSpan.FromHours(2) - TimeSpan.Parse(timeString.Split(' ')[1])).ToLocalTime(); - else if (timeString.Contains("Y-day")) - release.PublishDate = (DateTime.UtcNow - TimeSpan.FromHours(26) - TimeSpan.Parse(timeString.Split(' ')[1])).ToLocalTime(); - else if (timeString.Contains(':')) + var message = new HttpRequestMessage { - var utc = DateTime.ParseExact(timeString, "MM-dd HH:mm", CultureInfo.InvariantCulture) - TimeSpan.FromHours(2); - release.PublishDate = DateTime.SpecifyKind(utc, DateTimeKind.Utc).ToLocalTime(); - } - else + Method = HttpMethod.Get, + RequestUri = new Uri(BaseUrl + SwitchSingleViewUrl) + }; + message.Headers.Referrer = new Uri(searchUrl); + + var response = await client.SendAsync(message); + var results = await response.Content.ReadAsStringAsync(); + + CQ dom = results; + + var rows = dom["#searchResult > tbody > tr"]; + foreach (var row in rows) { - var utc = DateTime.ParseExact(timeString, "MM-dd yyyy", CultureInfo.InvariantCulture) - TimeSpan.FromHours(2); - release.PublishDate = DateTime.SpecifyKind(utc, DateTimeKind.Utc).ToLocalTime(); + var release = new ReleaseInfo(); + CQ qRow = row.Cq(); + CQ qLink = row.ChildElements.ElementAt(1).Cq().Children("a").First(); + + release.MinimumRatio = 1; + release.MinimumSeedTime = 172800; + release.Title = qLink.Text().Trim(); + release.Description = release.Title; + release.Comments = new Uri(BaseUrl + qLink.Attr("href").TrimStart('/')); + release.Guid = release.Comments; + + var timeString = row.ChildElements.ElementAt(2).Cq().Text(); + if (timeString.Contains("mins ago")) + release.PublishDate = (DateTime.Now - TimeSpan.FromMinutes(int.Parse(timeString.Split(' ')[0]))); + else if (timeString.Contains("Today")) + release.PublishDate = (DateTime.UtcNow - TimeSpan.FromHours(2) - TimeSpan.Parse(timeString.Split(' ')[1])).ToLocalTime(); + else if (timeString.Contains("Y-day")) + release.PublishDate = (DateTime.UtcNow - TimeSpan.FromHours(26) - TimeSpan.Parse(timeString.Split(' ')[1])).ToLocalTime(); + else if (timeString.Contains(':')) + { + var utc = DateTime.ParseExact(timeString, "MM-dd HH:mm", CultureInfo.InvariantCulture) - TimeSpan.FromHours(2); + release.PublishDate = DateTime.SpecifyKind(utc, DateTimeKind.Utc).ToLocalTime(); + } + else + { + var utc = DateTime.ParseExact(timeString, "MM-dd yyyy", CultureInfo.InvariantCulture) - TimeSpan.FromHours(2); + release.PublishDate = DateTime.SpecifyKind(utc, DateTimeKind.Utc).ToLocalTime(); + } + + var downloadCol = row.ChildElements.ElementAt(3).Cq().Find("a"); + release.MagnetUrl = new Uri(downloadCol.Attr("href")); + release.InfoHash = release.MagnetUrl.ToString().Split(':')[3].Split('&')[0]; + + var sizeString = row.ChildElements.ElementAt(4).Cq().Text().Split(' '); + var sizeVal = float.Parse(sizeString[0]); + var sizeUnit = sizeString[1]; + switch (sizeUnit) + { + case "GiB": release.Size = ReleaseInfo.BytesFromGB(sizeVal); break; + case "MiB": release.Size = ReleaseInfo.BytesFromMB(sizeVal); break; + case "KiB": release.Size = ReleaseInfo.BytesFromKB(sizeVal); break; + } + + release.Seeders = int.Parse(row.ChildElements.ElementAt(5).Cq().Text()); + release.Peers = int.Parse(row.ChildElements.ElementAt(6).Cq().Text()) + release.Seeders; + + releases.Add(release); } - - var downloadCol = row.ChildElements.ElementAt(3).Cq().Find("a"); - release.MagnetUrl = new Uri(downloadCol.Attr("href")); - release.InfoHash = release.MagnetUrl.ToString().Split(':')[3].Split('&')[0]; - - var sizeString = row.ChildElements.ElementAt(4).Cq().Text().Split(' '); - var sizeVal = float.Parse(sizeString[0]); - var sizeUnit = sizeString[1]; - switch (sizeUnit) - { - case "GiB": release.Size = ReleaseInfo.BytesFromGB(sizeVal); break; - case "MiB": release.Size = ReleaseInfo.BytesFromMB(sizeVal); break; - case "KiB": release.Size = ReleaseInfo.BytesFromKB(sizeVal); break; - } - - release.Seeders = int.Parse(row.ChildElements.ElementAt(5).Cq().Text()); - release.Peers = int.Parse(row.ChildElements.ElementAt(6).Cq().Text()) + release.Seeders; - - releases.Add(release); } - return releases.ToArray(); } diff --git a/src/Jackett/Server.cs b/src/Jackett/Server.cs index faf0b9ee6..d173c1fec 100644 --- a/src/Jackett/Server.cs +++ b/src/Jackett/Server.cs @@ -99,6 +99,11 @@ namespace Jackett } var torznabQuery = TorznabQuery.FromHttpQuery(query); + + torznabQuery.ShowTitles = await sonarrApi.GetShowTitle(torznabQuery.RageID); + + var releases = await indexer.PerformQuery(torznabQuery); + var severUrl = string.Format("{0}://{1}:{2}/", context.Request.Url.Scheme, context.Request.Url.Host, context.Request.Url.Port); var resultPage = new ResultPage(new ChannelInfo @@ -112,8 +117,6 @@ namespace Jackett ImageDescription = indexer.DisplayName }); - var releases = await indexer.PerformQuery(torznabQuery); - // add Jackett proxy to download links... foreach (var release in releases) { diff --git a/src/Jackett/SonarApi.cs b/src/Jackett/SonarApi.cs index 33fb362aa..cca79e80b 100644 --- a/src/Jackett/SonarApi.cs +++ b/src/Jackett/SonarApi.cs @@ -45,6 +45,8 @@ namespace Jackett HttpClientHandler handler; HttpClient client; + Dictionary IdNameMappings; + public SonarrApi() { LoadSettings(); @@ -57,6 +59,28 @@ namespace Jackett UseCookies = true, }; client = new HttpClient(handler); + + IdNameMappings = new Dictionary(); + } + + async Task ReloadNameMappings(string host, int port, string apiKey) + { + Uri hostUri = new Uri(host); + var queryUrl = string.Format("http://{0}:{1}/api/series?apikey={2}", hostUri.Host, port, apiKey); + var response = await client.GetStringAsync(queryUrl); + var json = JArray.Parse(response); + + IdNameMappings.Clear(); + foreach (var item in json) + { + var titles = new List(); + titles.Add((string)item["title"]); + foreach (var t in item["alternateTitles"]) + { + titles.Add((string)t["title"]); + } + IdNameMappings.Add((int)item["tvRageId"], titles.ToArray()); + } } void LoadSettings() @@ -99,7 +123,7 @@ namespace Jackett { var config = new ConfigurationSonarr(); config.LoadValuesFromJson(configJson); - await TestConnection(config.Host.Value, int.Parse(config.Port.Value), config.ApiKey.Value); + await ReloadNameMappings(config.Host.Value, int.Parse(config.Port.Value), config.ApiKey.Value); Host = "http://" + new Uri(config.Host.Value).Host; Port = int.Parse(config.Port.Value); ApiKey = config.ApiKey.Value; @@ -108,15 +132,24 @@ namespace Jackett public async Task TestConnection() { - await TestConnection(Host, Port, ApiKey); + await ReloadNameMappings(Host, Port, ApiKey); } - async Task TestConnection(string host, int port, string apiKey) + public async Task GetShowTitle(int rid) { - Uri hostUri = new Uri(host); - var queryUrl = string.Format("http://{0}:{1}/api/series?apikey={2}", hostUri.Host, port, apiKey); - var response = await client.GetStringAsync(queryUrl); - var json = JArray.Parse(response); + if (rid == 0) + return null; + + int tries = 0; + while (tries < 2) + { + string[] titles; + if (IdNameMappings.TryGetValue(rid, out titles)) + return titles; + await ReloadNameMappings(Host, Port, ApiKey); + tries++; + } + return null; } } } diff --git a/src/Jackett/TorznabQuery.cs b/src/Jackett/TorznabQuery.cs index 375f20a0e..4937d511c 100644 --- a/src/Jackett/TorznabQuery.cs +++ b/src/Jackett/TorznabQuery.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Generic; using System.Collections.Specialized; +using System.Globalization; using System.Linq; using System.Text; using System.Threading.Tasks; @@ -17,7 +18,23 @@ namespace Jackett public int Offset { get; private set; } public int RageID { get; private set; } public int Season { get; private set; } - public int Episode { get; private set; } + public string Episode { get; private set; } + public string[] ShowTitles { get; set; } + + public string GetEpisodeSearchString() + { + if (Season == 0) + return string.Empty; + + string episodeString; + DateTime showDate; + if (DateTime.TryParseExact(string.Format("{0} {1}", Season, Episode), "yyyy MM/dd", CultureInfo.InvariantCulture, DateTimeStyles.None, out showDate)) + episodeString = showDate.ToString("yyyy.MM.dd"); + else + episodeString = string.Format("S{0:00}E{1:00}", Season, int.Parse(Episode)); + + return episodeString; + } public static TorznabQuery FromHttpQuery(NameValueCollection query) { @@ -36,8 +53,8 @@ namespace Jackett q.RageID = temp; if (int.TryParse(query["season"], out temp)) q.Season = temp; - if (int.TryParse(query["ep"], out temp)) - q.Episode = int.Parse(query["ep"]); + + q.Episode = query["ep"]; return q; } diff --git a/src/Jackett/WebContent/index.html b/src/Jackett/WebContent/index.html index f26d30d21..a50314326 100644 --- a/src/Jackett/WebContent/index.html +++ b/src/Jackett/WebContent/index.html @@ -308,12 +308,12 @@
{{{value_element}}}
- +
{{#if value}} - + {{else}} - + {{/if}}