DIYgod/RSSHub · error
Unknown type: ${contentItem.type}
Error message
Unknown type: ${contentItem.type} What it means
Thrown from the inner content-item switch while rendering a Zhihu "pin" (想法/short post) in the activities feed. The switch handles content item types `text`, `image`, `link`, `video`, and `link_card`; any other `contentItem.type` hits the `default` and throws, echoing the unknown type so the unhandled payload shape is visible.
Source
Thrown at lib/routes/zhihu/activities.ts:120
case 'link':
link = `<p><a href="${contentItem.url}" target="_blank">${contentItem.title}</a></p>`;
break;
case 'video':
link = `<p><video
controls="controls"
width="${contentItem.playlist[1].width}"
height="${contentItem.playlist[1].height}"
src="${contentItem.playlist[1].url}"></video></p>`;
break;
case 'link_card':
link = `<p><a href="${contentItem.url.split('?', 1)[0]}" target="_blank"></a></p>`;
break;
default:
throw new Error(`Unknown type: ${contentItem.type}`);
}
}
description = `${text}${link}${images.join('')}`;
url = `https://www.zhihu.com/pin/${detail.id}`;
break;
case 'question':
title = detail.title;
author = detail.author.name;
description = processImage(detail.detail);
url = `https://www.zhihu.com/question/${detail.id}`;
break;
case 'collection':
title = detail.title;
url = `https://www.zhihu.com/collection/${detail.id}`;
break;
case 'column':
title = detail.title;
description = `<p>${detail.intro}</p><p><img src="${detail.image_url}"/></p>`;View on GitHub (pinned to bed535e087)
Solutions
- Capture the `contentItem.type` from the error and add a `case` that renders it (commonly a link, an `<img>`, or an `<iframe>` depending on the payload fields).
- If the new type's rendering is unknown, make `default` skip the item (continue/break with empty HTML) instead of throwing, so the rest of the pin still renders.
- Check the Zhihu web/app pin UI for the new block to infer the right HTML mapping.
Example fix
// before
default:
throw new Error(`Unknown type: ${contentItem.type}`);
// after — graceful skip for unknown pin content types
default:
break; Defensive patterns
Strategy: type-guard
Validate before calling
const HANDLED_PIN_CONTENT_TYPES = new Set(['text', 'image', 'link', 'video', 'link_card']);
function filterPinContent(content) {
return content.filter((item) => HANDLED_PIN_CONTENT_TYPES.has(item.type));
} Type guard
type HandledPinType = 'text' | 'image' | 'link' | 'video' | 'link_card';
const HANDLED: Set<HandledPinType> = new Set(['text','image','link','video','link_card']);
function isHandledPinType(item: { type: string }): item is { type: HandledPinType } {
return HANDLED.has(item.type as HandledPinType);
} Try / catch
// Render only known content types; skip the rest instead of throwing
for (const contentItem of detail.content) {
if (!isHandledPinType(contentItem)) continue;
// ... existing switch
} Prevention
- Filter the pin content array to known types before the switch so unknown blocks are skipped, not fatal.
- Log unknown content types at warn level to detect Zhihu API additions.
- Add new types as explicit cases once their payload shape is understood.
When it happens
Trigger: A Zhihu pin contains a content block of a type the route has not encoded — e.g. Zhihu adds a new embed type (audio, poll, article-embed, repost) to the pin content array, or renames an existing type string.
Common situations: Zhihu rolls out a new pin content feature; the API starts returning a previously-unseen type for certain pins; a reposted/quoted pin carries a nested structure with a different type tag. Because the throw is uncaught it fails the entire activity feed for that user.
Related errors
- Unknown type: ${contentItem.type}
- Unknown type: ${item.type}
- Unknown type: ${item.type}
- Unknown type: ${item.type}
- Unhandled thirdparty on ${link}: ${elem.attr('alias')}
AI-assisted analysis of DIYgod/RSSHub@bed535e087 (2026-08-12).
Data as JSON: /api/errors/2473317e35f4d2c8.
Report an issue: GitHub.