From bfb58f53f5f3ff33ecceef8c64fc0df0cbc79ac3 Mon Sep 17 00:00:00 2001 From: JigSaw <JigSawFr@users.noreply.github.com> Date: Sun, 3 Apr 2016 20:31:44 +0200 Subject: [PATCH] Xthor Provider French Private Tracker --- README.md | 1 + src/Jackett/Content/logos/xthor.png | Bin 0 -> 52300 bytes src/Jackett/Indexers/Xthor.cs | 592 ++++++++++++++++++ src/Jackett/Jackett.csproj | 5 + .../Bespoke/ConfigurationDataXthor.cs | 27 + 5 files changed, 625 insertions(+) create mode 100644 src/Jackett/Content/logos/xthor.png create mode 100644 src/Jackett/Indexers/Xthor.cs create mode 100644 src/Jackett/Models/IndexerConfig/Bespoke/ConfigurationDataXthor.cs diff --git a/README.md b/README.md index 9d19f2a4..3a0a939b 100644 --- a/README.md +++ b/README.md @@ -57,6 +57,7 @@ Developer note: The software implements the [Torznab](https://github.com/Sonarr/ * TV Chaos UK * World-In-HD * XSpeeds + * Xthor #### Installation on Windows diff --git a/src/Jackett/Content/logos/xthor.png b/src/Jackett/Content/logos/xthor.png new file mode 100644 index 0000000000000000000000000000000000000000..104fbe5c2150a8b1d33bc55df5c669666cb344a7 GIT binary patch literal 52300 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 N;OXk;vd$@?2>|BU@pS+I literal 0 HcmV?d00001 diff --git a/src/Jackett/Indexers/Xthor.cs b/src/Jackett/Indexers/Xthor.cs new file mode 100644 index 00000000..29721f1f --- /dev/null +++ b/src/Jackett/Indexers/Xthor.cs @@ -0,0 +1,592 @@ +using System; +using System.Collections.Generic; +using System.Collections.Specialized; +using System.Linq; +using System.Reflection; +using System.Threading.Tasks; +using System.Web; +using Jackett.Models; +using Jackett.Models.IndexerConfig.Bespoke; +using Jackett.Services; +using Jackett.Utils; +using Jackett.Utils.Clients; +using Newtonsoft.Json; +using Newtonsoft.Json.Linq; +using NLog; + +namespace Jackett.Indexers +{ + /// <summary> + /// Provider for Xthor Private French Tracker + /// </summary> + public class Xthor : BaseIndexer, IIndexer + { + private static string ApiEndpoint => "https://api.xthor.bz/"; + private string TorrentCommentUrl => TorrentDescriptionUrl; + private string TorrentDescriptionUrl => SiteLink + "details.php?id={id}"; + private bool DevMode => ConfigData.DevMode.Value; + private bool CacheMode => ConfigData.HardDriveCache.Value; + private static string Directory => System.IO.Path.GetTempPath() + "Jackett\\" + MethodBase.GetCurrentMethod().DeclaringType?.Name + "\\"; + public Dictionary<string, string> EmulatedBrowserHeaders { get; } = new Dictionary<string, string>(); + private ConfigurationDataXthor ConfigData => (ConfigurationDataXthor)configData; + + public Xthor(IIndexerManagerService i, IWebClient w, Logger l, IProtectionService ps) + : base( + name: "Xthor", + description: "General French Private Tracker", + link: "https://xthor.bz/", + caps: new TorznabCapabilities(), + manager: i, + client: w, + logger: l, + p: ps, + downloadBase: "https://xthor.bz/download.php?torrent=", + configData: new ConfigurationDataXthor()) + { + // Clean capabilities + TorznabCaps.Categories.Clear(); + + // Movies + AddCategoryMapping(6, TorznabCatType.MoviesSD); // XVID + AddCategoryMapping(7, TorznabCatType.MoviesSD); // X264 + AddCategoryMapping(95, TorznabCatType.MoviesSD); // WEBRIP + AddCategoryMapping(5, TorznabCatType.MoviesHD); // HD 720P + AddCategoryMapping(4, TorznabCatType.MoviesHD); // HD 1080P X264 + AddCategoryMapping(100, TorznabCatType.MoviesHD); // HD 1080P X265 + AddCategoryMapping(94, TorznabCatType.MoviesHD); // WEBDL + AddCategoryMapping(1, TorznabCatType.MoviesBluRay); // FULL BLURAY + AddCategoryMapping(2, TorznabCatType.MoviesBluRay); // BLURAY REMUX + AddCategoryMapping(3, TorznabCatType.MoviesBluRay); // FULL BLURAY 3D + AddCategoryMapping(8, TorznabCatType.MoviesDVD); // FULL DVD + AddCategoryMapping(9, TorznabCatType.MoviesOther); // VOSTFR + AddCategoryMapping(36, TorznabCatType.XXX); // XXX + + // Series + AddCategoryMapping(14, TorznabCatType.TVSD); // SD VF + AddCategoryMapping(16, TorznabCatType.TVSD); // SD VF VOSTFR + AddCategoryMapping(15, TorznabCatType.TVHD); // HD VF + AddCategoryMapping(17, TorznabCatType.TVHD); // HD VF VOSTFR + AddCategoryMapping(13, TorznabCatType.TVOTHER); // PACK + AddCategoryMapping(98, TorznabCatType.TVOTHER); // PACK VOSTFR HD + AddCategoryMapping(16, TorznabCatType.TVOTHER); // PACK VOSTFR SD + AddCategoryMapping(30, TorznabCatType.TVOTHER); // EMISSIONS + AddCategoryMapping(34, TorznabCatType.TVOTHER); // EMISSIONS + AddCategoryMapping(33, TorznabCatType.TVOTHER); // SHOWS + + // Anime + AddCategoryMapping(31, TorznabCatType.TVAnime); // MOVIES ANIME + AddCategoryMapping(32, TorznabCatType.TVAnime); // SERIES ANIME + + // Documentaries + AddCategoryMapping(12, TorznabCatType.TVDocumentary); // DOCS + + // Music + AddCategoryMapping(20, TorznabCatType.AudioVideo); // CONCERT + + // Other + AddCategoryMapping(21, TorznabCatType.PC); // PC + AddCategoryMapping(22, TorznabCatType.PCMac); // PC + AddCategoryMapping(25, TorznabCatType.PCGames); // GAMES + AddCategoryMapping(26, TorznabCatType.ConsoleXbox360); // GAMES + AddCategoryMapping(28, TorznabCatType.ConsoleWii); // GAMES + AddCategoryMapping(27, TorznabCatType.ConsolePS3); // GAMES + AddCategoryMapping(29, TorznabCatType.ConsoleNDS); // GAMES + AddCategoryMapping(24, TorznabCatType.BooksEbook); // EBOOKS + AddCategoryMapping(96, TorznabCatType.BooksEbook); // EBOOKS MAGAZINES + AddCategoryMapping(99, TorznabCatType.BooksEbook); // EBOOKS ANIME + AddCategoryMapping(23, TorznabCatType.PCPhoneAndroid); // ANDROID + } + + /// <summary> + /// Configure our Provider + /// </summary> + /// <param name="configJson">Our params in Json</param> + /// <returns>Configuration state</returns> + #pragma warning disable 1998 + public async Task<IndexerConfigurationStatus> ApplyConfiguration(JToken configJson) + #pragma warning restore 1998 + { + // Provider not yet configured + IsConfigured = false; + + // Retrieve config values set by Jackett's user + ConfigData.LoadValuesFromJson(configJson); + + // Check & Validate Config + ValidateConfig(); + + // Setting our data for a better emulated browser (maximum security) + // TODO: Encoded Content not supported by Jackett at this time + // emulatedBrowserHeaders.Add("Accept-Encoding", "gzip, deflate"); + + // Clean headers + EmulatedBrowserHeaders.Clear(); + + // Inject headers + EmulatedBrowserHeaders.Add("Accept", "application/json-rpc, application/json"); + EmulatedBrowserHeaders.Add("Content-Type", "application/json-rpc"); + + // Tracker is now configured + IsConfigured = true; + + // Saving data + SaveConfig(); + + return IndexerConfigurationStatus.RequiresTesting; + } + + /// <summary> + /// Execute our search query + /// </summary> + /// <param name="query">Query</param> + /// <returns>Releases</returns> + public async Task<IEnumerable<ReleaseInfo>> PerformQuery(TorznabQuery query) + { + var releases = new List<ReleaseInfo>(); + var searchTerm = query.GetQueryString(); + + // Check cache first so we don't query the server (if search term used or not in dev mode) + if(!DevMode && !string.IsNullOrEmpty(searchTerm)) + { + lock (cache) + { + // Remove old cache items + CleanCache(); + + // Search in cache + var cachedResult = cache.FirstOrDefault(i => i.Query == searchTerm); + if (cachedResult != null) + return cachedResult.Results.Select(s => (ReleaseInfo)s.Clone()).ToArray(); + } + } + + // Build our query + var request = BuildQuery(searchTerm, query, ApiEndpoint); + + // Getting results & Store content + var results = await QueryExec(request); + + try + { + // Deserialize our Json Response + var xthorResponse = JsonConvert.DeserializeObject<XthorResponse>(results.Content); + + // Check Tracker's State + CheckApiState(xthorResponse.error); + + // If contains torrents + if (xthorResponse.torrents != null) + { + // Adding each torrent row to releases + releases.AddRange(xthorResponse.torrents.Select(torrent => new ReleaseInfo + { + // Mapping data + Category = MapTrackerCatToNewznab(torrent.category.ToString()), + Title = torrent.name, Seeders = torrent.seeders, + Peers = torrent.seeders + torrent.leechers, + MinimumRatio = 1, + MinimumSeedTime = 345600, + PublishDate = DateTimeUtil.UnixTimestampToDateTime(torrent.added), + Size = torrent.size, + Guid = new Uri(TorrentDescriptionUrl.Replace("{id}", torrent.id.ToString())), + Comments = new Uri(TorrentCommentUrl.Replace("{id}", torrent.id.ToString())), + Link = new Uri(torrent.download_link) + })); + } + } + catch (Exception ex) + { + OnParseError("Error, unable to parse result \n" + ex.StackTrace, ex); + } + + // Return found releases + return releases; + } + + /// <summary> + /// Response from Tracker's API + /// </summary> + public class XthorResponse + { + public XthorError error { get; set; } + public XthorUser user { get; set; } + public List<XthorTorrent> torrents { get; set; } + } + + /// <summary> + /// State of API + /// </summary> + public class XthorError + { + public int code { get; set; } + public string descr { get; set; } + } + + /// <summary> + /// User Informations + /// </summary> + public class XthorUser + { + public int id { get; set; } + public string username { get; set; } + public long uploaded { get; set; } + public long downloaded { get; set; } + public int uclass { get; set; } // Class is a reserved keyword. + public decimal bonus_point { get; set; } + public int hits_and_run { get; set; } + public string avatar_url { get; set; } + } + + /// <summary> + /// Torrent Informations + /// </summary> + public class XthorTorrent + { + public int id { get; set; } + public int category { get; set; } + public int seeders { get; set; } + public int leechers { get; set; } + public string name { get; set; } + public int times_completed { get; set; } + public long size { get; set; } + public int added { get; set; } + public int freeleech { get; set; } + public int numfiles { get; set; } + public string release_group { get; set; } + public string download_link { get; set; } + } + + /// <summary> + /// Build query to process + /// </summary> + /// <param name="term">Term to search</param> + /// <param name="query">Torznab Query for categories mapping</param> + /// <param name="url">Search url for provider</param> + /// <returns>URL to query for parsing and processing results</returns> + private string BuildQuery(string term, TorznabQuery query, string url) + { + var parameters = new NameValueCollection(); + var categoriesList = MapTorznabCapsToTrackers(query); + + // Passkey + parameters.Add("passkey", ConfigData.PassKey.Value); + + // If search term provided + if (!string.IsNullOrWhiteSpace(term)) + { + // Add search term + // ReSharper disable once AssignNullToNotNullAttribute + parameters.Add("search", HttpUtility.UrlEncode(term)); + } + else + { + parameters.Add("search", string.Empty); + // Showing all torrents (just for output function) + term = "all"; + } + + // Loop on Categories needed + switch (categoriesList.Count) + { + case 0: + // No category + parameters.Add("category", string.Empty); + break; + case 1: + // One category + parameters.Add("category", categoriesList[0]); + break; + default: + // Multiple Categories + string categories = null; + foreach (var category in categoriesList) + { + // Initiate our categories parameter + if (categoriesList.First() == category) + { + categories = categoriesList[0]; + } + // Adding next categories + categories += "+" + category; + } + // Add categories + if (categories != null) parameters.Add("category", categories); + break; + } + + // If Only Freeleech Enabled + if (ConfigData.Freeleech.Value) + { + parameters.Add("freeleech", "1"); + } + + // Building our query -- Cannot use GetQueryString due to UrlEncode (generating wrong category param) + url += "?" + string.Join("&", parameters.AllKeys.Select(a => a + "=" + parameters[a])); + + Output("\nBuilded query for \"" + term + "\"... " + url); + + // Return our search url + return url; + } + + /// <summary> + /// Switch Method for Querying + /// </summary> + /// <param name="request">URL created by Query Builder</param> + /// <returns>Results from query</returns> + private async Task<WebClientStringResult> QueryExec(string request) + { + WebClientStringResult results; + + // Switch in we are in DEV mode with Hard Drive Cache or not + if (DevMode && CacheMode) + { + // Check Cache before querying and load previous results if available + results = await QueryCache(request); + } + else + { + // Querying tracker directly + results = await QueryTracker(request); + } + return results; + } + + /// <summary> + /// Get Torrents Page from Cache by Query Provided + /// </summary> + /// <param name="request">URL created by Query Builder</param> + /// <returns>Results from query</returns> + private async Task<WebClientStringResult> QueryCache(string request) + { + WebClientStringResult results; + + // Create Directory if not exist + System.IO.Directory.CreateDirectory(Directory); + + // Clean Storage Provider Directory from outdated cached queries + CleanCacheStorage(); + + // Create fingerprint for request + string file = Directory + request.GetHashCode() + ".json"; + + // Checking modes states + if (System.IO.File.Exists(file)) + { + // File exist... loading it right now ! + Output("Loading results from hard drive cache ..." + request.GetHashCode() + ".json"); + results = JsonConvert.DeserializeObject<WebClientStringResult>(System.IO.File.ReadAllText(file)); + } + else + { + // No cached file found, querying tracker directly + results = await QueryTracker(request); + + // Cached file didn't exist for our query, writing it right now ! + Output("Writing results to hard drive cache ..." + request.GetHashCode() + ".json"); + System.IO.File.WriteAllText(file, JsonConvert.SerializeObject(results)); + } + return results; + } + + /// <summary> + /// Get Torrents Page from Tracker by Query Provided + /// </summary> + /// <param name="request">URL created by Query Builder</param> + /// <returns>Results from query</returns> + private async Task<WebClientStringResult> QueryTracker(string request) + { + // Cache mode not enabled or cached file didn't exist for our query + Output("\nQuerying tracker for results...."); + + // Build WebRequest for index + var myIndexRequest = new WebRequest() + { + Type = RequestType.GET, + Url = request, + Headers = EmulatedBrowserHeaders + }; + + // Request our first page + var results = await webclient.GetString(myIndexRequest); + + // Return results from tracker + return results; + } + + /// <summary> + /// Check API's state + /// </summary> + /// <param name="state">State of API</param> + private void CheckApiState(XthorError state) + { + // Switch on state + switch (state.code) + { + case 0: + // Everything OK + Output("\nAPI State : Everything OK ... -> " + state.descr); + break; + case 1: + // Passkey not found + Output("\nAPI State : Error, Passkey not found in tracker's database, aborting... -> " + state.descr); + throw new Exception("API State : Error, Passkey not found in tracker's database, aborting... -> " + state.descr); + case 2: + // No results + Output("\nAPI State : No results for query ... -> " + state.descr); + break; + case 3: + // Power Saver + Output("\nAPI State : Power Saver mode, only cached query with no parameters available ... -> " + state.descr); + break; + case 4: + // DDOS Attack, API disabled + Output("\nAPI State : Tracker is under DDOS attack, API disabled, aborting ... -> " + state.descr); + throw new Exception("\nAPI State : Tracker is under DDOS attack, API disabled, aborting ... -> " + state.descr); + default: + // Unknown state + Output("\nAPI State : Unknown state, aborting querying ... -> " + state.descr); + throw new Exception("API State : Unknown state, aborting querying ... -> " + state.descr); + } + } + + /// <summary> + /// Clean Hard Drive Cache Storage + /// </summary> + /// <param name="force">Force Provider Folder deletion</param> + private void CleanCacheStorage(bool force = false) + { + // Check cleaning method + if(force) + { + // Deleting Provider Storage folder and all files recursively + Output("\nDeleting Provider Storage folder and all files recursively ..."); + + // Check if directory exist + if(System.IO.Directory.Exists(Directory)) + { + // Delete storage directory of provider + System.IO.Directory.Delete(Directory, true); + Output("-> Storage folder deleted successfully."); + } + else + { + // No directory, so nothing to do + Output("-> No Storage folder found for this provider !"); + } + } + else + { + var i = 0; + // Check if there is file older than ... and delete them + Output("\nCleaning Provider Storage folder... in progress."); + System.IO.Directory.GetFiles(Directory) + .Select(f => new System.IO.FileInfo(f)) + .Where(f => f.LastAccessTime < DateTime.Now.AddMilliseconds(-Convert.ToInt32(ConfigData.HardDriveCacheKeepTime.Value))) + .ToList() + .ForEach(f => { + Output("Deleting cached file << " + f.Name + " >> ... done."); + f.Delete(); + i++; + }); + + // Inform on what was cleaned during process + if(i > 0) { + Output("-> Deleted " + i + " cached files during cleaning."); + } + else { + Output("-> Nothing deleted during cleaning."); + } + } + } + + /// <summary> + /// Output message for logging or developpment (console) + /// </summary> + /// <param name="message">Message to output</param> + /// <param name="level">Level for Logger</param> + private void Output(string message, string level = "debug") + { + // Check if we are in dev mode + if(DevMode) + { + // Output message to console + Console.WriteLine(message); + } + else + { + // Send message to logger with level + switch (level) + { + default: + goto case "debug"; + case "debug": + // Only if Debug Level Enabled on Jackett + if (Engine.Logger.IsDebugEnabled) + { + logger.Debug(message); + } + break; + case "info": + logger.Info(message); + break; + case "error": + logger.Error(message); + break; + } + } + } + + /// <summary> + /// Validate Config entered by user on Jackett + /// </summary> + private void ValidateConfig() + { + Output("\nValidating Settings ... \n"); + + // Check Passkey Setting + if (string.IsNullOrEmpty(ConfigData.PassKey.Value)) + { + throw new ExceptionWithConfigData("You must provide your passkey for this tracker to be allowed to use API !", ConfigData); + } + else + { + Output("Validated Setting -- PassKey (auth) => " + ConfigData.PassKey.Value); + } + + // Check Dev Cache Settings + if (ConfigData.HardDriveCache.Value) + { + Output("\nValidated Setting -- DEV Hard Drive Cache enabled"); + + // Check if Dev Mode enabled ! + if (!ConfigData.DevMode.Value) + { + throw new ExceptionWithConfigData("Hard Drive is enabled but not in DEV MODE, Please enable DEV MODE !", ConfigData); + } + + // Check Cache Keep Time Setting + if (!string.IsNullOrEmpty(ConfigData.HardDriveCacheKeepTime.Value)) + { + try + { + Output("Validated Setting -- Cache Keep Time (ms) => " + Convert.ToInt32(ConfigData.HardDriveCacheKeepTime.Value)); + } + catch (Exception) + { + throw new ExceptionWithConfigData("Please enter a numeric hard drive keep time in ms !", ConfigData); + } + } + else + { + throw new ExceptionWithConfigData("Hard Drive Cache enabled, Please enter a maximum keep time for cache !", ConfigData); + } + } + else + { + // Delete cache if previously existed + CleanCacheStorage(true); + } + } + } +} \ No newline at end of file diff --git a/src/Jackett/Jackett.csproj b/src/Jackett/Jackett.csproj index 25c2c5a3..a50663c5 100644 --- a/src/Jackett/Jackett.csproj +++ b/src/Jackett/Jackett.csproj @@ -186,6 +186,7 @@ <Compile Include="Controllers\TorznabController.cs" /> <Compile Include="Controllers\DownloadController.cs" /> <Compile Include="Engine.cs" /> + <Compile Include="Indexers\Xthor.cs" /> <Compile Include="Indexers\PhxBit.cs" /> <Compile Include="Indexers\AlphaRatio.cs" /> <Compile Include="Indexers\BitSoup.cs" /> @@ -221,6 +222,7 @@ <Compile Include="Indexers\XSpeeds.cs" /> <Compile Include="Models\GitHub\Asset.cs" /> <Compile Include="Models\GitHub\Release.cs" /> + <Compile Include="Models\IndexerConfig\Bespoke\ConfigurationDataXthor.cs" /> <Compile Include="Models\IndexerConfig\Bespoke\ConfigurationDataPhxBit.cs" /> <Compile Include="Models\IndexerConfig\Bespoke\ConfigurationDataBlueTigers.cs" /> <Compile Include="Models\IndexerConfig\Bespoke\ConfigurationDataAbnormal.cs" /> @@ -442,6 +444,9 @@ <Content Include="Content\login.html"> <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> </Content> + <Content Include="Content\logos\xthor.png"> + <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> + </Content> <Content Include="Content\logos\phxbit.png"> <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> </Content> diff --git a/src/Jackett/Models/IndexerConfig/Bespoke/ConfigurationDataXthor.cs b/src/Jackett/Models/IndexerConfig/Bespoke/ConfigurationDataXthor.cs new file mode 100644 index 00000000..b0f8c9dc --- /dev/null +++ b/src/Jackett/Models/IndexerConfig/Bespoke/ConfigurationDataXthor.cs @@ -0,0 +1,27 @@ +namespace Jackett.Models.IndexerConfig.Bespoke +{ + class ConfigurationDataXthor : ConfigurationData + { + public DisplayItem CredentialsWarning { get; private set; } + public StringItem PassKey { get; set; } + public DisplayItem PagesWarning { get; private set; } + public BoolItem Freeleech { get; private set; } + public DisplayItem DevWarning { get; private set; } + public BoolItem DevMode { get; private set; } + public BoolItem HardDriveCache { get; private set; } + public StringItem HardDriveCacheKeepTime { get; private set; } + + public ConfigurationDataXthor() + : base() + { + CredentialsWarning = new DisplayItem("<b>Credentials Configuration</b> (<i>Private Tracker</i>),<br /><br /> <ul><li><b>PassKey</b> is your private key on your account</li></ul>") { Name = "Credentials" }; + PassKey = new StringItem { Name = "PassKey", Value = "" }; + PagesWarning = new DisplayItem("<b>Preferences Configuration</b> (<i>Tweak your search settings</i>),<br /><br /> <ul><li><b>Freeleech Only</b> let you search <u>only</u> for torrents which are marked Freeleech.</li></ul>") { Name = "Preferences" }; + Freeleech = new BoolItem() { Name = "Freeleech Only (Optional)", Value = false }; + DevWarning = new DisplayItem("<b>Development Facility</b> (<i>For Developers ONLY</i>),<br /><br /> <ul><li>By enabling development mode, <b>Jackett will bypass his cache</b> and will <u>output debug messages to console</u> instead of his log file.</li><li>By enabling Hard Drive Cache, <b>This provider</b> will <u>save each query answers from tracker</u> in temp directory, in fact this reduce drastically HTTP requests when building a provider at parsing step for example. So, <b> Jackett will search for a cached query answer on hard drive before executing query on tracker side !</b> <i>DEV MODE must be enabled to use it !</li></ul>") { Name = "Development" }; + DevMode = new BoolItem { Name = "Enable DEV MODE (Developers ONLY)", Value = false }; + HardDriveCache = new BoolItem { Name = "Enable HARD DRIVE CACHE (Developers ONLY)", Value = false }; + HardDriveCacheKeepTime = new StringItem { Name = "Keep Cached files for (ms)", Value = "300000" }; + } + } +} -- GitLab