UNPKG

nhentai-tools

Version:

A toolset to interact with the doujin site nhentai.net

106 lines (105 loc) 5.21 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()); }); }; Object.defineProperty(exports, "__esModule", { value: true }); exports.getCaptcha = exports.logout = exports.login = exports.getUser = exports.updateUser = exports.isLoggedIn = exports.notLoggedInError = void 0; const client_1 = require("./client"); const utils_1 = require("./utils"); const puppeteer = require("puppeteer"); exports.notLoggedInError = new Error('User is not logged in'); exports.isLoggedIn = false; let _data = null; const updateUser = () => client_1.client.get('/') .then(({ data }) => { var _a; const user = (_a = data.match(/user: (.+),/)) === null || _a === void 0 ? void 0 : _a[1]; if (!user || !user.includes('JSON.parse')) throw new Error('User is not logged in'); return JSON.parse((0, utils_1.unescapeUTF8)(user.match(/JSON\.parse\("(.+)"\)/)[1])); }); exports.updateUser = updateUser; const getUser = () => { if (!exports.isLoggedIn) throw exports.notLoggedInError; return _data; }; exports.getUser = getUser; /** Login as username/password. If you're logging in multiple times, make sure to include a method to get a captcha token. */ const login = (username_or_email, password, captcha) => { if (exports.isLoggedIn) throw new Error('Already logged in'); // wrapped in promise to allow early breakout if a captcha is required return new Promise((resolve, reject) => { client_1.client.get('/login/') .then(({ data }) => __awaiter(void 0, void 0, void 0, function* () { // grab the csrfmiddlewaretoken from the body const [, csrfmiddlewaretoken] = data.match(/name="csrfmiddlewaretoken" value="(\w{64})"/); // create the body of the post request, containing the csrfmiddlewaretoken and the username/password const body = new URLSearchParams({ csrfmiddlewaretoken, username_or_email, password }); // if we have a captcha, wait for it to be solved, then add it to the body if (data.includes('captcha')) { if (captcha) body.set('g-recaptcha-response', yield captcha()); else throw new Error('Captcha required, but no captcha function was provided'); } return client_1.client.post('/login/', body.toString(), { validateStatus: status => status === 302 || status === 200 }); })) .then(({ data }) => { // if the data has a captcha, we need to retry the login if (data.includes('captcha')) resolve((0, exports.login)(username_or_email, password, captcha)); if (data.includes('Invalid username (or email) or password.')) reject('Invalid username or password'); return (0, exports.updateUser)(); }) .then(data => { _data = data; exports.isLoggedIn = true; resolve(_data); }); }); }; exports.login = login; /** Logout from the current user. */ const logout = () => { if (!exports.isLoggedIn) throw exports.notLoggedInError; return client_1.client.get('/logout/') .then(({ data }) => { const csrfmiddlewaretoken = data.match(/"csrfmiddlewaretoken" value="\w{64}/)[0].split('value="')[1]; return client_1.client.post('/logout/', new URLSearchParams({ csrfmiddlewaretoken }).toString(), { validateStatus: status => status === 302 }); }) .then(() => { _data = null; exports.isLoggedIn = false; }); }; exports.logout = logout; /** A method, using puppeteer, to get captcha tokens. */ //eslint-disable-next-line no-async-promise-executor const getCaptcha = () => new Promise((resolve) => __awaiter(void 0, void 0, void 0, function* () { const browser = yield puppeteer.launch({ headless: false, ignoreDefaultArgs: true }); const page = (yield browser.pages())[0]; yield page.setRequestInterception(true); page.on('request', req => { if (req.method() === 'POST' && req.url() === 'https://nhentai.net/login/') { req.abort(); browser.close(); resolve(new URLSearchParams(req.postData()).get('g-recaptcha-response')); } else { req.continue(); } }); yield page.goto('https://nhentai.net/login/'); page.$$eval('.inputs .row', elems => elems.forEach(e => e.remove())); })); exports.getCaptcha = getCaptcha;