UNPKG

eztv-crawler

Version:

A promised based node module to scrape TV shows, episodes and torrent info from EZTV.

192 lines 7.65 kB
"use strict"; var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.EztvCrawlerException = exports.getTorrentsByImdbId = exports.getTorrents = exports.search = exports.getShow = exports.getShows = void 0; const bytes_1 = __importDefault(require("bytes")); const cross_fetch_1 = __importDefault(require("cross-fetch")); const cheerio_1 = require("cheerio"); /** * Crawl any given url * * @link https://www.npmjs.com/package/crawler * @param url * @returns `Crawler.CrawlerRequestResponse` */ function crawl(url) { return __awaiter(this, void 0, void 0, function* () { const body = yield (0, cross_fetch_1.default)(url).then((resp) => __awaiter(this, void 0, void 0, function* () { return resp.text(); })); const $ = (0, cheerio_1.load)(body); return { body, $ }; }); } /** * Get all shows listen on EZTV * * @returns `object` */ function getShows() { return __awaiter(this, void 0, void 0, function* () { const { $ } = yield crawl(`https://eztv.wf/showlist/`); const shows = $('a[class="thread_link"]').toArray(); return shows.map(show => { var _a; const showIdRegex = (_a = $(show).attr('href')) === null || _a === void 0 ? void 0 : _a.match(/shows\/(\d+)\//); return { id: showIdRegex ? parseInt(showIdRegex[1]) : null, title: $(show).text() }; }).filter(show => show.id); }); } exports.getShows = getShows; /** * Get a show and its episodes * * Recommended to use an ID, if using a showname * it must be an exact match except for uppercase * * @param showId - A show ID or a show name * @returns `object` */ function getShow(show) { var _a; return __awaiter(this, void 0, void 0, function* () { /** * If a string is passed find show based on title */ if (typeof show === 'string') { const shows = yield getShows(); const findShow = shows.find(s => s.title.toLowerCase() === show.toLowerCase()); if (!findShow) { throw new EztvCrawlerException(`Did not find a show with name ${show}`); } return getShow(findShow.id); } const { $ } = yield crawl(`https://eztv.wf/shows/${show}/`); const episodes = $('[name="hover"]').toArray(); const imdbIdRegex = (_a = $('[itemprop="aggregateRating"] a').attr('href')) === null || _a === void 0 ? void 0 : _a.match(/tt\d+/); const result = { title: $('.section_post_header [itemprop="name"]').text(), summary: $('[itemprop="description"] p').text(), description: $('span[itemprop="description"] + br + br + hr + br + span').text(), imdbId: imdbIdRegex ? imdbIdRegex[0] : null, episodes: episodes.map(episode => { return transformToEpisode($, episode); }) }; if (!result || !result.title || result.title === '') { throw new EztvCrawlerException(`Did not find a show with name ${show}`); } return result; }); } exports.getShow = getShow; /** * Search for a TV show episode * * @param query - string * @returns `episodeObject` */ function search(query) { return __awaiter(this, void 0, void 0, function* () { const { $ } = yield crawl(`https://eztv.wf/search/${query}`); const episodes = $('[name="hover"]').toArray(); return episodes.map(episode => { return transformToEpisode($, episode); }); }); } exports.search = search; /** * Get a list of torrents * * @param limit * @param page * @param apiBaseUrl - If eztv domain changed or eztv is blocked in your country provide a proxy url here * @returns `ApiResponseType` */ function getTorrents(limit = 10, page = 1, apiBaseUrl = 'https://eztv.wf/api/') { return __awaiter(this, void 0, void 0, function* () { return yield makeApiRequest('/get-torrents', { limit: limit.toString(), page: page.toString() }, apiBaseUrl); }); } exports.getTorrents = getTorrents; /** * Get a list of torrents based on IMDb ID * * NOTE: * For TV Shows provide the IMDb id of the show itself, it does not work * when you provide an IMDb for individual episodes * * @param imdbId - IMDb ID * @param apiBaseUrl - If eztv domain changed or eztv is blocked in your country provide a proxy url here * @returns `ApiResponseType` */ function getTorrentsByImdbId(imdbId, limit = 30, page = 1, apiBaseUrl = 'https://eztv.wf/api/') { return __awaiter(this, void 0, void 0, function* () { return yield makeApiRequest('/get-torrents', { imdb_id: imdbId, limit: limit.toString(), page: page.toString() }, apiBaseUrl); }); } exports.getTorrentsByImdbId = getTorrentsByImdbId; /** * Send a request to EZTV's API * * @param path * @param params * @param apiBaseUrl * @returns `ApiResponseType` */ function makeApiRequest(path, params, apiBaseUrl = 'https://eztv.wf/api/') { return __awaiter(this, void 0, void 0, function* () { if (params.imdb_id) { params.imdb_id = params.imdb_id.replace(/\D+/, ''); } try { const request = yield (0, cross_fetch_1.default)(`${apiBaseUrl}/${path}?${new URLSearchParams(params)}`); const json = yield request.json(); return json; } catch (e) { if (e instanceof Error) { throw new EztvCrawlerException(e.message); } throw new EztvCrawlerException('Could not fullfill request.'); } }); } /** * Transforms a <table> Element into a episode object * * Note: in torrents, don't parse the `.download_2` class, it contains spam and malware in some cases * * @param $ - cheerio.CheerioAPI * @param episode - cheerio.Element * @returns `episodeObject` */ function transformToEpisode($, episode) { var _a, _b, _c; return { showLink: $(episode).find('td:nth-child(1) a').attr('href'), title: (_a = $(episode).find('td:nth-child(2)').text()) === null || _a === void 0 ? void 0 : _a.replace(/\n/g, ''), magnet: (_b = $(episode).find('td:nth-child(3) .magnet').attr('href')) === null || _b === void 0 ? void 0 : _b.replace(/\n/g, ''), torrent: (_c = $(episode).find('td:nth-child(3) .download_1').attr('href')) === null || _c === void 0 ? void 0 : _c.replace(/\n/g, ''), size: (0, bytes_1.default)($(episode).find('td:nth-child(4)').text()), released: $(episode).find('td:nth-child(5)').text(), seeds: parseInt($(episode).find('td:nth-child(6)').text()) || 0 }; } class EztvCrawlerException extends Error { } exports.EztvCrawlerException = EztvCrawlerException; //# sourceMappingURL=main.js.map