UNPKG

rsshub

Version:
120 lines (104 loc) 4.13 kB
import { Route } from '@/types'; import cache from '@/utils/cache'; import { load } from 'cheerio'; import got from '@/utils/got'; import { parseDate } from '@/utils/parse-date'; import { art } from '@/utils/render'; import path from 'node:path'; import { setCookies } from '@/utils/puppeteer-utils'; import { CookieJar } from 'tough-cookie'; import logger from '@/utils/logger'; import puppeteer from '@/utils/puppeteer'; export const route: Route = { path: '/:topicPath{.+}?', radar: [ { source: ['pnas.org/*topicPath'], target: '/:topicPath', }, ], name: 'Unknown', maintainers: [], handler, url: 'pnas.org/*topicPath', }; async function handler(ctx) { const baseUrl = 'https://www.pnas.org'; const topicPath = ctx.req.param('topicPath'); const link = `${baseUrl}/${topicPath ?? 'latest'}`; let cookieJar = await cache.get('pnas:cookieJar'); const cacheMiss = !cookieJar; cookieJar = cacheMiss ? new CookieJar() : CookieJar.fromJSON(cookieJar); const { data: res } = await got(link, { cookieJar, }); if (cacheMiss) { await cache.set('pnas:cookieJar', cookieJar.toJSON()); } const $ = load(res); const list = $('.card--row-reversed .card-content') .toArray() .map((item) => { item = $(item); const a = item.find('.article-title a'); return { title: a.text(), link: new URL(a.attr('href'), baseUrl).href, pubDate: parseDate(item.find('.card__meta__date').text()), }; }); const browser = await puppeteer(); const out = await Promise.all( list.map((item) => cache.tryGet(item.link, async () => { const page = await browser.newPage(); await setCookies(page, await cookieJar.getCookieString(item.link), '.pnas.org'); await page.setRequestInterception(true); page.on('request', (request) => { request.resourceType() === 'document' ? request.continue() : request.abort(); }); logger.http(`Requesting ${item.link}`); await page.goto(item.link, { waitUntil: 'domcontentloaded', referer: link, }); await page.waitForSelector('.core-container'); const res = await page.evaluate(() => document.documentElement.innerHTML); await page.close(); const $ = load(res); const PNASdataLayer = JSON.parse( $('script') .text() .match(/PNASdataLayer =(.*?);/)[1] ); $('.signup-alert-ad, .citations-truncation button').remove(); const { keywords, topic } = PNASdataLayer.page.attributes; item.category = [...keywords, topic]; item.author = PNASdataLayer.page.pageInfo.author; item.doi = PNASdataLayer.page.pageInfo.DOI; item.description = art(path.join(__dirname, 'templates/article.art'), { access: PNASdataLayer.user.access === 'yes', // abstracts: $('#abstracts .core-container').html(), // articleBody: $('[property=articleBody]').html(), // dataAvailability: $('#data-availability').html(), acknowledgments: $('#acknowledgments').html(), supplementaryMaterials: $('#supplementary-materials').html(), bibliography: $('#bibliography').html(), }); return item; }) ) ); await browser.close(); return { title: `${$('.banner-widget__content h1').text()} - PNAS`, description: $('.banner-widget__content p').text(), image: 'https://www.pnas.org/favicon.ico', language: 'en-US', link, item: out, }; }