DIYgod/RSSHub · error · Error

Unhandled mark type: ${mark.type}

Error message

Unhandled mark type: ${mark.type}

What it means

Thrown (bare Error) inside the recursive render() function of the Netflix newsroom route when a rich-text 'text' node has a mark whose type is not one of the four handled: bold, italic, underline, strikethrough. The Netflix/Contentful-style document model added (or returned) an unrecognised inline mark (e.g. 'code', 'superscript', 'subscript', 'comment'), and the default branch of the switch throws instead of rendering or skipping it.

Source

Thrown at lib/routes/netflix/newsroom.ts:142

            if (!node.marks || node.marks.length === 0) {
                return text;
            }
            for (const mark of node.marks) {
                switch (mark.type) {
                    case 'bold':
                        text = `<strong>${text}</strong>`;
                        break;
                    case 'italic':
                        text = `<em>${text}</em>`;
                        break;
                    case 'underline':
                        text = `<u>${text}</u>`;
                        break;
                    case 'strikethrough':
                        text = `<s>${text}</s>`;
                        break;
                    default:
                        throw new Error(`Unhandled mark type: ${mark.type}`);
                }
            }
            return text;
        }
        case 'hyperlink': {
            const href = node.data?.uri || '#';
            const innerHTML = node.content?.map((c) => render(c)).join('') || '';
            return `<a href="${href}" target="_blank" rel="noopener noreferrer">${innerHTML}</a>`;
        }

        case 'embedded-asset-block': {
            const file = Object.values<any>(node.data?.file)[0];
            if (!file || !file.url) {
                return '';
            }

            const url = file.url.startsWith('//') ? 'https:' + file.url : file.url;
            const contentType = file.contentType || '';

View on GitHub (pinned to bed535e087)

Solutions

  1. Patch the switch to handle (or ignore) the new mark type — add cases for the missing types, and make the default return the text unmodified instead of throwing, so future marks don't break the feed.
  2. Inspect the failing article's JSON (fetch the upstream payload) to see exactly which mark.type triggered it.
  3. If you only need a quick unblock, default to returning `text` (no formatting) for unknown marks.

Example fix

// before
default:
    throw new Error(`Unhandled mark type: ${mark.type}`);

// after — render known extra marks, gracefully ignore unknown ones
case 'code':
    text = `<code>${text}</code>`;
    break;
case 'superscript':
    text = `<sup>${text}</sup>`;
    break;
case 'subscript':
    text = `<sub>${text}</sub>`;
    break;
default:
    // unknown mark: keep the text, do not fail the whole feed
    break;
Defensive patterns

Strategy: validation

Validate before calling

// Defensive: never throw on an unknown mark; render known ones, ignore the rest.
for (const mark of node.marks ?? []) {
    switch (mark.type) {
        case 'bold': text = `<strong>${text}</strong>`; break;
        case 'italic': text = `<em>${text}</em>`; break;
        case 'underline': text = `<u>${text}</u>`; break;
        case 'strikethrough': text = `<s>${text}</s>`; break;
        case 'code': text = `<code>${text}</code>`; break;
        default: break; // ignore unknown marks
    }
}

Type guard

const KNOWN_MARKS = new Set(['bold', 'italic', 'underline', 'strikethrough', 'code']);
function isKnownMark(mark: any): boolean {
    return !!mark && typeof mark.type === 'string' && KNOWN_MARKS.has(mark.type);
}

Prevention

When it happens

Trigger: While rendering an article's rich-text body, a text node carries node.marks = [{type: 'code'}] (or any non-handled type). The switch falls through to default and throws, failing the whole feed even though only one article uses the new mark. Most likely after Netflix/CMS adds a new formatting option.

Common situations: Netflix's CMS introduces a new text decoration; an article copy-pasted from another tool carries an unusual mark; a Contentful schema upgrade adds marks the renderer doesn't know.

Related errors


AI-assisted analysis of DIYgod/RSSHub@bed535e087 (2026-08-12). Data as JSON: /api/errors/b28e461092594e60. Report an issue: GitHub.