From d879c6336f11cdc27f08ae4e8b8650a152dfed96 Mon Sep 17 00:00:00 2001 From: shanmite Date: Fri, 29 May 2026 10:56:30 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E8=BD=AC=E5=8F=91=E7=B1=BB=E5=9E=8B?= =?UTF-8?q?=E5=8A=A8=E6=80=81=E8=8E=B7=E5=8F=96=E4=B8=8D=E5=88=B0rid?= =?UTF-8?q?=E6=97=A0=E6=B3=95=E8=AF=84=E8=AE=BA=20(#466)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixed #466 --- lib/core/searcher.js | 288 ++++++-------------------------------- lib/net/api.bili.js | 1 - lib/net/bili.js | 7 - test/dynamic_card.test.js | 65 +-------- 4 files changed, 46 insertions(+), 315 deletions(-) diff --git a/lib/core/searcher.js b/lib/core/searcher.js index 27a28c5..ea3a783 100644 --- a/lib/core/searcher.js +++ b/lib/core/searcher.js @@ -24,18 +24,18 @@ const { log } = utils; * @property {boolean} is_charge_lottery * @property {boolean} hasOfficialLottery * @property {Array>} ctrl - * @property {number} origin_create_time 10 - * @property {number} origin_uid - * @property {string} origin_uname - * @property {string} origin_rid_str - * @property {number} origin_chat_type - * @property {string} origin_dynamic_id - * @property {number} origin_type - * @property {string} origin_description - * @property {string} origin_reserve_id - * @property {string} origin_reserve_lottery_text - * @property {boolean} origin_is_charge_lottery - * @property {boolean} origin_hasOfficialLottery + * @property {number} origin.create_time 10 + * @property {number} origin.uid + * @property {string} origin.uname + * @property {string} origin.rid_str + * @property {number} origin.chat_type + * @property {string} origin.dynamic_id + * @property {number} origin.type + * @property {string} origin.description + * @property {string} origin.reserve_id + * @property {string} origin.reserve_lottery_text + * @property {boolean} origin.is_charge_lottery + * @property {boolean} origin.hasOfficialLottery * * 整理后的抽奖信息 * @typedef {object} LotteryInfo @@ -59,10 +59,6 @@ const { log } = utils; * @return {UsefulDynamicInfo} */ function parseDynamicCard(data) { - if (data?.card?.desc?.uid) { - return oldParseDynamicCard(data?.card); - } - // 如果是多个 items,返回一个数组 if (Array.isArray(data?.items)) { return data.items.map(item => parseDynamicCard({ item })); @@ -96,10 +92,10 @@ function parseDynamicCard(data) { obj.create_time = ditem?.modules?.module_author?.pub_ts || 0; /* 动态类型 */ obj.type = dy_typeenum2num.get(ditem?.type) || 0; - /* 用于发送评论 */ + /* 用于发送评论 无法获取到源动态的rid_str*/ obj.rid_str = ditem?.basic?.comment_id_str || ''; /* 用于发送评论 */ - obj.chat_type = ditem?.basic?.comment_type || 0; + obj.chat_type = dy_type2chat_type.get(ditem?.type) || 0; /* 转发者的动态ID !!!!此为大数需使用字符串值,不然JSON.parse()会有丢失精度 */ obj.dynamic_id = ditem?.id_str || ''; /* 定位@信息 */ @@ -146,7 +142,7 @@ function parseDynamicCard(data) { } /* 预约抽奖信息 */ obj.reserve_id = ditem?.modules?.module_dynamic?.additional?.reserve?.rid || 0; - obj.reserve_lottery_text = ditem?.modules?.module_dynamic?.additional?.reserve?.title || '信息丢失'; + obj.reserve_lottery_text = ditem?.modules?.module_dynamic?.additional?.reserve?.title || '未获取到'; /* 充电抽奖 */ obj.is_charge_lottery = false; if (ditem?.modules?.module_dynamic?.additional?.type === 'ADDITIONAL_TYPE_UPOWER_LOTTERY') { @@ -154,208 +150,7 @@ function parseDynamicCard(data) { } /* 转发 */ if (obj.type === 1) { - /* 被转发者的UID */ - obj.origin_uid = ditem?.orig?.modules?.module_author?.mid || 0; - /* 被转发者的name */ - obj.origin_uname = ditem?.orig?.modules?.module_author?.name || ''; - /* 源动态的ts10 */ - obj.origin_create_time = ditem?.orig?.modules?.module_author?.pub_ts || 0; - /* 源动态类型 */ - obj.origin_type = dy_typeenum2num.get(ditem?.orig?.type) || 0; - /* 被转发者的rid(用于发评论) */ - switch (ditem?.orig?.type) { - case 'DYNAMIC_TYPE_DRAW': - obj.origin_rid_str = ditem?.orig?.modules?.module_dynamic?.major?.draw?.id?.toString() || ''; - break; - case 'DYNAMIC_TYPE_AV': - obj.origin_rid_str = ditem?.orig?.modules?.module_dynamic?.major?.archive?.aid || ''; - break; - case 'DYNAMIC_TYPE_ARTICLE': - obj.origin_rid_str = ditem?.orig?.modules?.module_dynamic?.major?.article?.id?.toString() || ''; - break; - default: - obj.origin_rid_str = ditem?.orig?.id_str || ''; - break; - } - /* 用于发送评论 */ - obj.origin_chat_type = dy_type2chat_type.get(ditem?.orig?.type) || 0; - /* 被转发者的动态的ID !!!!此为大数需使用字符串值,不然JSON.parse()会有丢失精度 */ - obj.origin_dynamic_id = ditem?.orig?.id_str || ''; - /* 预约抽奖信息 */ - obj.origin_reserve_id = ditem?.orig?.modules?.module_dynamic?.additional?.reserve?.rid || 0; - obj.origin_reserve_lottery_text = ditem?.orig?.modules?.module_dynamic?.additional?.reserve?.title || '信息丢失'; - /* 充电抽奖 */ - obj.origin_is_charge_lottery = false; - if (ditem?.orig?.modules?.module_dynamic?.additional?.type === 'ADDITIONAL_TYPE_UPOWER_LOTTERY') { - obj.origin_is_charge_lottery = true; - } - /* 是否有官方抽奖 */ - obj.origin_hasOfficialLottery = false; - /* 转发描述 */ - obj.origin_description = ''; - if (Array.isArray(ditem?.orig?.modules?.module_dynamic?.desc?.rich_text_nodes)) { - ditem?.orig?.modules?.module_dynamic?.desc?.rich_text_nodes.forEach(node => { - /* 是否有官方抽奖 */ - if (node.type === 'RICH_TEXT_NODE_TYPE_LOTTERY') { - obj.origin_hasOfficialLottery = true; - } - obj.origin_description += node.orig_text; - }); - } else { - ditem?.orig.modules?.module_dynamic?.major?.opus?.summary?.rich_text_nodes.forEach(node => { - /* 是否有官方抽奖 */ - if (node.type === 'RICH_TEXT_NODE_TYPE_LOTTERY') { - obj.origin_hasOfficialLottery = true; - } - obj.origin_description += node.orig_text; - }); - } - } - } catch (e) { - log.error('动态卡片解析', e); - } - - return obj; -} - -/** - * @param {object} dynamic_detail_card - * @return {UsefulDynamicInfo} - */ -function oldParseDynamicCard(dynamic_detail_card) { - const { strToJson } = utils; - /**临时储存单个动态中的信息 */ - let obj = {}; - try { - const { desc, card, extension, extend_json = '{}', display = {} } = dynamic_detail_card - , { is_liked = 1, user_profile = {} } = desc - , { info = {} } = user_profile || {} - , cardToJson = strToJson(card) - , extendjsonToJson = strToJson(extend_json) - , { add_on_card_info = [] } = display || {} - , { item } = cardToJson; - const dy_type2chat_type = new Map([[1, 17], [2, 11], [4, 17], [8, 1], [64, 12]]); - /* 转发者的UID */ - obj.uid = desc.uid; - /* 转发者的name */ - obj.uname = info.uname || ''; - /* 动态是否点过赞 */ - obj.is_liked = is_liked > 0; - /* 动态的ts10 */ - obj.create_time = desc.timestamp; - /* 动态类型 */ - obj.type = desc.type; - /* 用于发送评论 */ - obj.rid_str = desc.rid_str.length > 12 ? desc.dynamic_id_str : desc.rid_str; - /* 用于发送评论 */ - obj.chat_type = dy_type2chat_type.get(obj.type) || 0; - /* 转发者的动态ID !!!!此为大数需使用字符串值,不然JSON.parse()会有丢失精度 */ - obj.dynamic_id = desc.dynamic_id_str; - /* 定位@信息 */ - obj.ctrl = (extendjsonToJson.ctrl) || []; - /* 预约抽奖信息 */ - obj.reserve_id = ''; - obj.reserve_lottery_text = '信息丢失'; - if (add_on_card_info.length > 0) { - const [status, oid_str, text] = add_on_card_info - .filter(it => typeof it.reserve_attach_card !== 'undefined' - && typeof it.reserve_attach_card.reserve_lottery !== 'undefined' - && typeof it.reserve_attach_card.reserve_button !== 'undefined') - .map(({ reserve_attach_card }) => [ - reserve_attach_card.reserve_button.status, - reserve_attach_card.oid_str, - reserve_attach_card.reserve_lottery.text])[0] || []; - if (status === 1) { - obj.reserve_id = oid_str; - obj.reserve_lottery_text = text; - } - } - if (extendjsonToJson['']) { - let r = extendjsonToJson[''].reserve || {}; - let { reserve_id, reserve_lottery } = r; - if (reserve_lottery === 1) { - obj.reserve_id = reserve_id + ''; - obj.reserve_lottery_text = '信息丢失'; - } - } - obj.is_charge_lottery = false; - if (extend_json.match(/"":\{"lottery/)) { - obj.is_charge_lottery = true; - } - /* 是否有官方抽奖 */ - obj.hasOfficialLottery = extension && extension.lott && true || false; - /* 转发者的描述 纯文字内容 图片动态描述 后两个分别是视频动态的描述和视频本身的描述*/ - obj.description = - (item && ((item.content || '') + (item.description || ''))) - || ( - (cardToJson.dynamic || '') - + (cardToJson.desc || '') - + (cardToJson.vest && cardToJson.vest.content || '') - ) - || ''; - if (obj.description.startsWith('互动抽奖 ')) { - obj.hasOfficialLottery = true; - } - /* 转发 */ - if (obj.type === 1) { - const { origin_extension, origin, origin_extend_json = '{}' } = cardToJson - , originToJson = strToJson(origin) - , { add_on_card_info = [] } = display.origin || {} - , originExtendjsonToJson = strToJson(origin_extend_json) - , { user, item } = originToJson; - /* 源动态的ts10 */ - obj.origin_create_time = desc.origin.timestamp; - /* 被转发者的UID */ - obj.origin_uid = desc.origin.uid; - /* 源动态类型 */ - obj.origin_type = desc.orig_type; - /* 被转发者的rid(用于发评论) */ - obj.origin_rid_str = desc.origin.rid_str.length > 12 ? desc.origin.dynamic_id_str : desc.origin.rid_str; - /* 用于发送评论 */ - obj.origin_chat_type = dy_type2chat_type.get(obj.origin_type) || 0; - /* 被转发者的动态的ID !!!!此为大数需使用字符串值,不然JSON.parse()会有丢失精度 */ - obj.origin_dynamic_id = desc.orig_dy_id_str; - /* 预约抽奖信息 */ - obj.origin_reserve_id = ''; - obj.origin_reserve_lottery_text = '信息丢失'; - if (add_on_card_info.length > 0) { - const [status, oid_str, text] = add_on_card_info - .filter(it => typeof it.reserve_attach_card !== 'undefined' - && typeof it.reserve_attach_card.reserve_lottery !== 'undefined' - && typeof it.reserve_attach_card.reserve_button !== 'undefined') - .map(({ reserve_attach_card }) => [ - reserve_attach_card.reserve_button.status, - reserve_attach_card.oid_str, - reserve_attach_card.reserve_lottery.text])[0] || []; - if (status === 1) { - obj.origin_reserve_id = oid_str; - obj.origin_reserve_lottery_text = text; - } - } - if (originExtendjsonToJson['']) { - let r = originExtendjsonToJson[''].reserve || {}; - let { reserve_id, reserve_lottery } = r; - if (reserve_lottery === 1) { - obj.origin_reserve_id = reserve_id + ''; - obj.origin_reserve_lottery_text = '信息丢失'; - } - } - obj.origin_is_charge_lottery = false; - if (origin_extend_json.match(/"":\{"lottery/)) { - obj.origin_is_charge_lottery = true; - } - /* 是否有官方抽奖 */ - obj.origin_hasOfficialLottery = origin_extension && origin_extension.lott || false; - /* 被转发者的name */ - obj.origin_uname = (user && (user.name || user.uname)) || ''; - /* 被转发者的描述 */ - obj.origin_description = - (item && (item.content || '' + item.description || '')) - || (originToJson.dynamic || '' + originToJson.desc || '') - || ''; - if (obj.origin_description.startsWith('互动抽奖 ')) { - obj.origin_hasOfficialLottery = true; - } + obj.origin = parseDynamicCard({item: ditem.orig}); } } catch (e) { log.error('动态卡片解析', e); @@ -513,36 +308,33 @@ class Searcher { } }) .reduce(async (pre, cur) => { - let - results = await pre, - { origin_dynamic_id } = cur, - is_liked = false; + let results = await pre; - if (!check_if_duplicated || check_if_duplicated >= 2) { - const card = await bili.getOneDynamicByDyid(origin_dynamic_id); - log.info('获取动态', `查看源动态(${origin_dynamic_id})是否点赞 (${length--})`); - if (card) { - ({ is_liked } = parseDynamicCard(card)); - } - await utils.delay(get_dynamic_detail_wait); + const card = await bili.getOneDynamicByDyid(cur.origin.dynamic_id); + log.info('获取动态', `查看源动态(${cur.origin.dynamic_id})详细信息获取rid用于评论 (${length--})`); + if (card) { + let pdc = parseDynamicCard(card); + cur.origin.is_liked = pdc.is_liked; + cur.origin.rid_str= pdc.rid_str; } + await utils.delay(get_dynamic_detail_wait); results.push({ lottery_info_type: 'uid', - create_time: cur.origin_create_time, - is_liked, - uids: [cur.uid, cur.origin_uid], - uname: cur.origin_uname, + create_time: cur.origin.create_time, + is_liked: cur.origin.is_liked, + uids: [cur.uid, cur.origin.uid], + uname: cur.origin.uname, ctrl: [], - dyid: cur.origin_dynamic_id, - reserve_id: cur.origin_reserve_id, - reserve_lottery_text: cur.origin_reserve_lottery_text, - is_charge_lottery: cur.origin_is_charge_lottery, - rid: cur.origin_rid_str, - chat_type: cur.origin_chat_type, - des: cur.origin_description, - type: cur.origin_type, - hasOfficialLottery: cur.origin_hasOfficialLottery + dyid: cur.origin.dynamic_id, + reserve_id: cur.origin.reserve_id, + reserve_lottery_text: cur.origin.reserve_lottery_text, + is_charge_lottery: cur.origin.is_charge_lottery, + rid: cur.origin.rid_str, + chat_type: cur.origin.chat_type, + des: cur.origin.description, + type: cur.origin.type, + hasOfficialLottery: cur.origin.hasOfficialLottery }); return results; @@ -595,7 +387,7 @@ class Searcher { lottery_info_type: 'tag', create_time: o.create_time, is_liked: o.is_liked, - uids: [o.uid, o.origin_uid], + uids: [o.uid, o.origin.uid], uname: o.uname, ctrl: o.ctrl, dyid: o.dynamic_id, @@ -688,7 +480,7 @@ class Searcher { lottery_info_type: 'article', create_time: o.create_time, is_liked: o.is_liked, - uids: [o.uid, o.origin_uid], + uids: [o.uid, o.origin.uid], uname: o.uname, ctrl: o.ctrl, dyid: o.dynamic_id, @@ -829,7 +621,7 @@ class Searcher { lottery_info_type: 'txt', create_time: o.create_time, is_liked: o.is_liked, - uids: [o.uid, o.origin_uid], + uids: [o.uid, o.origin.uid], uname: o.uname, ctrl: o.ctrl, dyid: o.dynamic_id, diff --git a/lib/net/api.bili.js b/lib/net/api.bili.js index 6b352c7..a739d23 100644 --- a/lib/net/api.bili.js +++ b/lib/net/api.bili.js @@ -5,7 +5,6 @@ module.exports = Object.freeze({ DYNAMIC_REPOST_SHARE: 'https://api.vc.bilibili.com/dynamic_repost/v1/dynamic_repost/share', DYNAMIC_SVR_CREATE_DRAW: 'https://api.vc.bilibili.com/dynamic_svr/v1/dynamic_svr/create_draw', DYNAMIC_SVR_CREATE: 'https://api.vc.bilibili.com/dynamic_svr/v1/dynamic_svr/create', - DYNAMIC_SVR_GET_DYNAMIC_DETAIL: 'https://api.vc.bilibili.com/dynamic_svr/v1/dynamic_svr/get_dynamic_detail', DYNAMIC_SVR_RM_DYNAMIC: 'https://api.vc.bilibili.com/dynamic_svr/v1/dynamic_svr/rm_dynamic', FEED_GET_ATTENTION_LIST: 'https://api.vc.bilibili.com/feed/v1/feed/get_attention_list', FEED_SETUSERFOLLOW: 'https://api.vc.bilibili.com/feed/v1/feed/SetUserFollow', diff --git a/lib/net/bili.js b/lib/net/bili.js index 2c9388b..682fb8b 100644 --- a/lib/net/bili.js +++ b/lib/net/bili.js @@ -423,13 +423,6 @@ const bili_client = { features: 'itemOpusStyle' } }), - (dynamic_id) => get({ - url: API.DYNAMIC_SVR_GET_DYNAMIC_DETAIL, - config: { retry: false }, - query: { - dynamic_id - } - }), ] , responseText => { const diff --git a/test/dynamic_card.test.js b/test/dynamic_card.test.js index ea307e3..683982e 100644 --- a/test/dynamic_card.test.js +++ b/test/dynamic_card.test.js @@ -1,70 +1,17 @@ -const assert = require('assert'); +//const assert = require('assert'); const bili_client = require('../lib/net/bili'); const searcher = require('../lib/core/searcher'); const util = require('./util'); (async () => { - await util.par_run([0, 1], [ + await util.par_run([0], [ // 0 async () => { - let info = await bili_client.getOneDynamicByDyid('728424890210713624'); - assert(searcher.parseDynamicCard(info).is_charge_lottery); - info = await bili_client.getOneDynamicByDyid('1143258210499559428'); - assert(searcher.parseDynamicCard(info).is_charge_lottery); - }, - // 1 - async () => { - let info = await bili_client.getOneDynamicByDyid('1150096953788334085'); - assert(searcher.parseDynamicCard(info).origin_is_charge_lottery); - }, - // 2 - async () => { - let card = searcher.parseDynamicCard(await bili_client.getOneDynamicByDyid('746824225190314008')); - let chats = await bili_client.getChat(card.rid_str, card.chat_type); - assert(chats.length > 0 && typeof chats[0][0] == 'string'); - }, - // 3 - async () => { - let card = searcher.parseDynamicCard(await bili_client.getOneDynamicByDyid('900172162530279445')); - assert.equal(card.chat_type, 11); - card = searcher.parseDynamicCard(await bili_client.getOneDynamicByDyid('926978638295859236')); - assert.equal(card.chat_type, 17); - assert.equal(card.origin_chat_type, 11); - }, - // 4 - async () => { - // assert.equal(await bili_client.getOneDynamicByDyid("111111111111111111"), undefined); - // assert.notEqual(await bili_client.getOneDynamicByDyid("746824225190314008"), undefined); - // assert.equal(await bili_client.getOneDynamicByDyid("761475750233636886"), undefined); - }, - // 5 - async () => { - let card = searcher.parseDynamicCard(await bili_client.getOneDynamicByDyid('762591475338838053')); - let chats = await bili_client.getChat(card.rid_str, card.chat_type); - assert.equal(chats.length, 19); - card = searcher.parseDynamicCard(await bili_client.getOneDynamicByDyid('762502724122050647')); - chats = await bili_client.getChat(card.rid_str, card.chat_type); - assert.equal(chats.filter(it => it[0] === '六的月').length, 0); - }, - // 6 - async () => { - const dy = await bili_client.getOneDynamicByDyid('774973685666676768'); - const card = searcher.parseDynamicCard(dy); - assert.notEqual(card.description + '', undefined + ''); - }, - // 7 - async () => { - const dy = await bili_client.getOneDynamicByDyid('924676093465591832'); - const card = searcher.parseDynamicCard(dy); - assert.equal(card.reserve_id, '3715576'); - }, - // 8 - async () => { - const dy = await bili_client.getOneDynamicByDyid('925061227481137187'); - const card = searcher.parseDynamicCard(dy); - assert.equal(card.origin_reserve_id, '3715576'); + let info = await bili_client.getOneDynamicByDyid('1207028214165143570'); + let card = searcher.parseDynamicCard(info); + console.log(JSON.stringify(card, null, 4)); }, ]); console.log('dynamic_card.test ... ok!'); -})(); \ No newline at end of file +})();