90 lines
3.1 KiB
JavaScript
90 lines
3.1 KiB
JavaScript
const parser = require('@/utils/rss-parser');
|
|
const got = require('@/utils/got');
|
|
const cheerio = require('cheerio');
|
|
|
|
const getArticleDetail = (link, ctx) =>
|
|
ctx.cache.tryGet(link, async () => {
|
|
const response = await got(link);
|
|
const $ = cheerio.load(response.data);
|
|
|
|
const categories = $('.slug').text().trim();
|
|
|
|
// ignore item until audio is available
|
|
if ($('.audio-availability-message').length > 0) {
|
|
return null;
|
|
}
|
|
|
|
// handle multiple audios
|
|
$('.audio-module')
|
|
.toArray()
|
|
.forEach((x) => {
|
|
const audioLink = $($(x).find('.audio-tool-download a')).attr('href');
|
|
const audio_tag = `<audio controls><source src="${audioLink}" type="audio/mp3"></audio>`;
|
|
$(x).replaceWith(audio_tag);
|
|
});
|
|
|
|
// primaryaudio is not in `.storytext`, prepend to it
|
|
const primaryaudio = $('#primaryaudio');
|
|
const audio = primaryaudio.length > 0 ? $('#primaryaudio').html() : '';
|
|
|
|
// replace video
|
|
const regex = /\?storyId=(\d+)&mediaId=(\d+)/;
|
|
const m = $.html().match(regex);
|
|
if (m) {
|
|
const storyId = m[1];
|
|
const mediaId = m[2];
|
|
const video_tag = `<iframe width="740" height="416" src="https://www.npr.org/embedded-video?storyId=${storyId}&mediaId=${mediaId}&jwMediaType=music" frameborder="0" scrolling="no"></iframe>`;
|
|
const nprVideo = $('.npr-video');
|
|
if (nprVideo.length === 1) {
|
|
nprVideo.replaceWith(video_tag);
|
|
}
|
|
}
|
|
|
|
// remove duplicate caption and images
|
|
$('.enlarge_measure').remove();
|
|
$('.enlarge_html').remove();
|
|
$('.hide-caption').remove();
|
|
$('.toggle-caption').remove();
|
|
$('.credit-caption b.credit').remove();
|
|
$('.credit-caption span.credit').wrap('<figcaption></figcaption>');
|
|
$('.caption > p').wrap('<figcaption></figcaption>');
|
|
|
|
const article =
|
|
audio +
|
|
$('.storytext')
|
|
.toArray()
|
|
.map((el) => $(el).html())
|
|
.join('');
|
|
|
|
return { article, categories };
|
|
});
|
|
|
|
module.exports = async (ctx) => {
|
|
const endpoint = ctx.params.endpoint || '1001';
|
|
const feed = await parser.parseURL(`https://feeds.npr.org/${endpoint}/rss.xml`);
|
|
|
|
const items = (
|
|
await Promise.all(
|
|
feed.items.map(async (item) => {
|
|
const itemDetails = await getArticleDetail(item.link, ctx);
|
|
if (itemDetails === null) {
|
|
return null;
|
|
}
|
|
return {
|
|
...item,
|
|
description: itemDetails.article,
|
|
category: itemDetails.categories,
|
|
};
|
|
})
|
|
)
|
|
).filter(Boolean);
|
|
|
|
ctx.state.data = {
|
|
title: feed.title,
|
|
link: feed.link,
|
|
description: feed.description,
|
|
icon: 'https://media.npr.org/images/podcasts/primary/npr_generic_image_300.jpg?s=200',
|
|
item: items,
|
|
};
|
|
};
|