GitHub Advisoryadvisory · PyPI

GHSA-8whx-v8qq-pq64 changedetection.io has Reflected XSS in its RSS Tag Error Response

MEDIUM Published 2026-03-04 Modified 2026-03-06 Official page ↗
Aliases
CVE-2026-29038
Ecosystem
PyPI
Packages
changedetection.io
Severity
Moderate
CVSS vector
CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:L/I:L/A:N
Weaknesses
CWE-79
Reviewed
2026-03-04

Affected packages

• PyPI changedetection.io: < 0.54.4 → fixed in 0.54.4

Description

A reflected cross-site scripting (XSS) vulnerability was identified in the `/rss/tag/` endpoint of changedetection.io. The `tag_uuid` path parameter is reflected directly in the HTTP response body without HTML escaping. Since Flask returns `text/html` by default for plain string responses, the browser parses and executes injected JavaScript. This vulnerability persists in version 0.54.1, which patched the related XSS in `/rss/watch/` (CVE-2026-27645 / GHSA-mw8m-398g-h89w) but did not address the identical pattern in the tag RSS endpoint. Package • Ecosystem: pip • Package: changedetection.io • Affected versions: ` HTML tag on the homepage without authentication: 1. Attacker visits the target's homepage (if unauthenticated) and extracts the RSS token from the `` tag 2. Crafts a malicious URL: ``` http://target:5000/rss/tag/?token=EXTRACTED_TOKEN ``` 3. Sends the link to a victim who has an active session on the changedetection.io instance 4. When the victim clicks the link, the server responds with: ``` Tag with UUID not found ``` 5. The browser renders the `` tag, the `onerror` fires, and JavaScript executes in the victim's session context Proof of Concept Request ```http GET /rss/tag/%3Cimg%20src%3Dx%20onerror%3Dalert(document.domain)%3E?token=60b83b06df98b24c66367bc3d233105b HTTP/1.1 Host: localhost:5000 ``` Response ```http HTTP/1.1 404 NOT FOUND Content-Type: text/html; charset=utf-8 Tag with UUID not found ``` The XSS payload is reflected unescaped in an HTML response. The browser executes `alert(document.domain)` and displays "localhost", confirming JavaScript execution. Tested on: changedetection.io v0.54.1 (Docker, localhost, Feb 25, 2026) https://github.com/user-attachments/assets/6db07f6a-6df8-48a7-a597-9f39dfa1bb29 Impact • Session cookie theft via `document.cookie` exfiltration • Account takeover if session cookies lack the `HttpOnly` flag • Phishing via crafted links that appear to originate from a trusted changedetection.io instance • Low exploitation barrier - the RSS token is obtainable without authentication from the homepage `` tag • Widespread exposure - prior scanning of internet-facing instances (during CVE-2026-27645 research) identified 500+ publicly accessible deployments Suggested Fix Escape the `tag_uuid` parameter before reflecting it in the response, or set the `Content-Type` to `text/plain`: Option A: HTML Escape (Recommended) ```python from markupsafe import escape if not tag: return f"Tag with UUID {escape(tag_uuid)} not found", 404 ``` Option B: Set Content-Type to text/plain ```python from flask import make_response if not tag: resp = make_response(f"Tag with UUID {tag_uuid} not found", 404) resp.headers['Content-Type'] = 'text/plain; charset=utf-8' return resp ``` Credits • Roberto Nunes (@Akokonunes) - Reporter • neo-ai-engineer (@neo-ai-engineer) - Reporter References • Related advisory: GHSA-mw8m-398g-h89w (CVE-2026-27645) • Vulnerable source: tag.py @ 1d72716

Related

Alias · CVE (1)

  • CVE-2026-29038 changedetection.io is a free open source web page change detection tool. vulnerability

Weakness · CWE (1)

  • CWE-79 Improper Neutralization of Input During Web Page Generation weakness

References