'use strict'; const unprint = require('unprint'); const slugify = require('../utils/slugify'); const capitalize = require('../utils/capitalize'); const { convert } = require('../utils/convert'); function scrapeAll(months, channel, year) { return months.flatMap(({ query: queryMonth, element }) => { const month = queryMonth.content('h3'); const scenes = unprint.query.all(element.nextElementSibling, 'li:nth-child(2n)'); return unprint.initAll(scenes).map(({ query }) => { const release = {}; const videoUrl = query.url('a.video-pop-up', { origin: `${channel.origin}/submissive/` }); release.entryId = new URL(videoUrl).searchParams.get('id'); release.forceDeep = true; release.title = query.content('.updates-item-title h4'); release.date = unprint.extractDate(`${month} ${year}`, 'MMMM YYYY', { match: null }); release.datePrecision = 'month'; release.actors = [{ name: capitalize(query.attribute('a.video-pop-up', 'data-modelname'), { uncapitalize: true }), gender: 'female', url: query.url('a.video-pop-up', { attribute: 'data-modellink', origin: `${channel.origin}/submissive/` }), }] .filter((actor) => !/lockdown/i.test(actor.name)) .concat({ name: 'Pascal White', gender: 'male', }); release.poster = query.img('img'); return release; }); }); } async function fetchLatest(channel, page = 1) { const year = new Date().getFullYear() - (page - 1); const url = `${channel.url}/submissive/updates.php?y=${year}`; const res = await unprint.get(url, { selectAll: '.month' }); if (res.ok) { return scrapeAll(res.context, channel, year); } return res.status; } function scrapeScene({ html }, baseRelease) { const release = {}; release.entryId = baseRelease.entryId; release.trailer = html.match(/file: '(.*)'/)[1]; return release; } async function fetchScene(_url, channel, baseRelease) { if (!baseRelease.entryId) { return null; } const res = await unprint.get(`${channel.origin}/submissive/player-load.php?id=${baseRelease.entryId}`); if (res.ok) { return scrapeScene(res.context, baseRelease); } return res.status; } function scrapeProfile({ query }) { const profile = {}; const bio = query.all('.about-desc li').reduce((acc, bioEl) => { const key = unprint.query.content(bioEl, 'strong'); const value = unprint.query.text(bioEl); return { ...acc, [slugify(key, '_')]: value, }; }, {}); profile.gender = 'female'; profile.nationality = bio.nationality; profile.age = bio.age; profile.hairColor = bio.hair; profile.height = /['"]|ft/.test(bio.height) ? convert(bio.height, 'cm') : parseInt(bio.height, 10); profile.description = query.content('.twocolumns'); profile.avatar = query.img('#individual-description img'); // no dates or links available // profile.releases = scrapeAll(unprint.initAll(query.all('.individal-video-item'))); // sic return profile; } async function fetchProfile({ name: actorName, url: actorUrl }, entity, include) { const url = actorUrl || `${entity.url}/submissive/subslut-${slugify(actorName)}.php`; const res = await unprint.get(url, { followRedirects: false, }); if (res.ok && res.status === 200) { return scrapeProfile(res.context, actorName, entity, include); } return res.status; } module.exports = { fetchLatest, fetchScene, fetchProfile, };