使用Telegram轻松订阅Pixiv新图

作为一名艺术爱好者,时刻关注在Pixiv上喜爱的画师更新是我生活中重要的一部分。然而,每天手动检查新图既费时又费力。有没有更便捷的方法来推送这些喜欢的作品,让每一张图都能够展现它的光彩?

我想到了一种常见的资讯订阅方式:RSS。在查阅RSSHub文档时,我发现了用于Pixiv关注画师新图的订阅接口。

虽然RSS订阅的确是个不错的选择,但这依然需要一个单独的阅读器。相比之下,将这些资讯直接推送至通讯工具上来得更为高效。之前,我使用基于IFTTT的方案,将RSSHub生成的内容推送至Telegram频道。然而,由于IFTTT对非付费用户的限制,我最终决定自己开发一个类似的处理工具。这不仅能够锻炼我的编码能力,还能实现更高的自定义需求。

于是,我开始查询各种API接口,整理资料。基本思路是通过RSS采集数据,然后利用Bot API接口将其发送至Telegram频道。由于我习惯使用Node.js进行开发,这次也继续沿用这个平台。

第一步:RSS采集

首先是RSS的采集工作。为了避免手动分析XML文件的麻烦,我使用了一个现成的组件:rss-parser。这个组件能将RSS信息获取并转换成方便后续处理的对象。

安装这个组件:
bash
npm i rss-parser --save

使用时传参也非常简单。虽然可以使用官方示例中的async与await异步处理方式,我选择了更直接的参数传递。

在测试时,我将获取的feed信息输出,基于RSSHub生成的数据,我们可以看到内部其实是一个对象数组,因此可以直接使用相关字段进行内容处理。

第二步:数据处理

由于RSSHub的设计初衷是方便阅读,因此生成的内容格式是以可读形式呈现的,并使用了pixiv.cat的图片传递接口为主要组成部分。不过好在获取的内容中包含了我们需要的所有信息,因此可以使用正则表达式进行提取。

对于单张图片的内容,RSSHub会将其处理成形如`的链接;而多图内容的处理则需要关注ArtworkID后的-PicID`。我们可以使用以下正则表达式进行处理:

javascript
const picIdReg = /https:\/\/pixiv.cat\/(\d+)-?(\d+)?.(jpg|png|gif)/gi;

然后结合这条正则表达式,生成内容数组:

javascript
const artworks = [...item.content.matchAll(picIdReg)];

这样我们能得到单图的链接信息,并能进一步处理以适应Telegram对图片大小的限制。

通过查看Pixiv前端页面的源码,我发现预览图的地址由前缀、发布时间(UTC+9)、作品ID和一些固定组合构成。我们可以依据RSS中的isoDate手动计算获取时间,从而组合出所需的预览图片地址。

第三步:消息发送

最初在IFTTT中,直接推送订阅内容让Telegram自动获取的方式导致大图片无法有效获取,出现了图片缓存请求限制的问题。因此,这次我加入了请求缓冲队列和预览图来尝试解决这些问题。

经过考虑,我决定使用got来发送POST请求,以下是请求的样式:

javascript
const apiBaseUrl = https://api.telegram.org/bot${confData.bot.token};

got('sendPhoto', {
method: 'POST',
prefixUrl: apiBaseUrl,
json: {
chat_id: confData.bot.chat,
photo: picItem.preview,
caption: picItem.text,
reply_markup: {
inline_keyboard: [
[{
text: '🌏',
url: picItem.url
}, {
text: '⤵',
url: picItem.pic
}]
]
}
}
});

我通过调用Telegram的sendPhoto接口来发送请求数据,并加入了消息下的内联按钮,以方便用户操作。

为了避免每次启动时将所有图片加入队列,而造成不必要的等待,同时考虑到项目提供的数据均按时间排序,我维护了一个timestamp变量,初始化为当前时间,以便仅发送更新的内容。

最后,我利用js-yaml组件读取yml配置文件,整合所有代码已发布至GitHub的PhanDream仓库;您可以使用如pm2等方式运行:

bash
pm2 start bot.js --name phandream

当一切准备完成后,过一会就能在频道中看到新的图片啦!

👉 野卡 | 一分钟注册,轻松订阅海外线上服务

THE END