badges/shields · error · InvalidResponse

${e.message}

Error message

${e.message}

What it means

Thrown by the dynamic-xml service's transform when new DOMParser().parseFromString(buffer, contentType) throws, and the original exception's message is surfaced as an InvalidResponse. This means the fetched document could not be parsed as the given content type (XML/HTML) — typically malformed markup or a non-XML response. Note that XML parse errors may surface here or as values-less downstream failures depending on the parser implementation.

Source

Thrown at services/dynamic/dynamic-xml.service.js:89

  }

  static defaultBadgeData = { label: 'custom badge' }

  getmimeType(contentType) {
    return MIME_TYPES.find(mime => contentType.includes(mime)) ?? 'text/xml'
  }

  transform({ pathExpression, buffer, contentType = 'text/xml' }) {
    // e.g. //book[2]/@id
    const pathIsAttr = (
      pathExpression.split('/').slice(-1)[0] || ''
    ).startsWith('@')

    let parsed
    try {
      parsed = new DOMParser().parseFromString(buffer, contentType)
    } catch (e) {
      throw new InvalidResponse({ prettyMessage: e.message })
    }

    let values
    try {
      if (contentType === 'text/html') {
        values = xpath
          .parse(pathExpression)
          .select({ node: parsed, isHtml: true })
      } else {
        values = xpath.select(pathExpression, parsed)
      }
    } catch (e) {
      throw new InvalidParameter({ prettyMessage: e.message })
    }

    if (
      typeof values === 'string' ||
      typeof values === 'number' ||

View on GitHub (pinned to 766fd8bc89)

Solutions

  1. Fetch the url and validate the document is well-formed XML/HTML (xmllint or an online validator).
  2. Ensure the contentType matches the actual response (use text/html for HTML documents).
  3. Check the upstream API status — an error page is often the real cause.
  4. Verify encoding/escaping of the url and response (UTF-8).

Example fix

// before
url=https://api.example.com/data.json parsed as XML
// after
url=https://api.example.com/data.xml (or switch service to dynamic/json)
Defensive patterns

Strategy: validation

Validate before calling

function looksLikeXml(s) {
  const t = s.trim();
  return t.startsWith('<') && !t.startsWith('<!DOCTYPE html') && /<\/?[\w:-]+[\s\S]*/.test(t);
}
const body = await fetch(url).then(r => r.text());
if (!looksLikeXml(body)) throw new Error('url does not return XML');

Type guard

function isHtmlContentType(ct) { return /^text\/html/i.test(ct || ''); }
function isXmlLike(body) { return typeof body === 'string' && body.trim().startsWith('<?xml'); }

Try / catch

try {
  const value = await dynamicXml({ url, path, contentType });
} catch (err) {
  // InvalidResponse wrapping parser error message — check the upstream response
  console.error('XML parse failed:', err.message);
  throw err;
}

Prevention

When it happens

Trigger: The url returns content that fails DOM parsing with the declared contentType: truncated XML, HTML when XML parsing was selected, a JSON or plain-text error page, or an encoding problem that breaks the parser.

Common situations: API outage returning an HTML error page; wrong url pointing at JSON instead of XML; missing/incorrect Content-Type handling; CDATA/entity issues in the upstream document.

Related errors


AI-assisted analysis of badges/shields@766fd8bc89 (2026-08-30). Data as JSON: /api/errors/dfdb60669933687f. Report an issue: GitHub.