CVE-2026-47724 is a critical-severity missing authorization vulnerability in github.com/juev/nebula-mesh (go), affecting versions < 0.3.4. It is fixed in 0.3.4.
The /api/v1/ route surface trusts the bearer token alone for authorisation on most endpoints. The codebase itself admits this at internal/api/hosts.go:384: "API trusts the bearer token for authorisation; per-CA ownership is enforced only in the Web layer." The Web UI gates state-changing routes through loadAccessibleCA (internal/web/cas.go); CA-management endpoints in internal/api/cas.go ALSO have proper canAccessCA gates. The gap is on the host, network, firewall, mobile-bundle, and most operator endpoints. Combined with the per-operator CA model from ADR 0002, this gives any non-admin operator API key broad cross-tenant access, instant privilege escalation in the worst case. Affected All released versions prior to v0.3.4. Exploit chain A) Mint admin API key from any operator key (instant privilege escalation) internal/api/operators.go:118, handleCreateOperatorAPIKey does no admin check and no actor/target-operator ownership check. Any operator key can call it for any operator (including admins) and receive a fresh bearer. Reuse the returned key for subsequent requests → full admin. B) Cross-operator host takeover via reenroll internal/api/hosts.go:321,330 → mintEnrollmentTokenForHost. Looks up host by URL param, mints a single-use enrollment token, returns it. No ownership check. Caller POSTs /api/v1/enroll with their own X25519 + Ed25519 keypairs. enroll.go:175 overwrites signingpubpem; SaveCertificateAndEnrollHost overwrites the cert. Legitimate agent's next signed poll fails bad_signature. Attacker now owns the victim's Nebula identity. C) Cross-tenant CRUD on hosts, networks, firewall The same gap applies across: /api/v1/hosts, create, list, get, update, delete, block, unblock /api/v1/networks, create, list, get /api/v1/networks/{id}/firewall, get, PUT /api/v1/hosts/{id}/mobile-bundle (already filed as public issue #119) All trust bearer-auth alone. Any operator can read or mutate any other operator's resources. Affected operator-management handlers (in addition to A) Beyond handleCreateOperatorAPIKey (covered by A), internal/api/operators.go is missing admin gates on: handleListOperators (line 66), operator roster info disclosure handleDisableOperator (line 79), DoS / sabotage handleEnableOperator (line 94), re-enable disabled operators handleRevokeOperatorAPIKey (line 157), invalidate any operator's API keys handleListOperatorAPIKeys (line 173), API-key metadata disclosure handleCreateOperator (line 26) IS properly gated (actorIsAdmin at line 27). NOT affected (verified) internal/api/cas.go properly gates every CA endpoint via canAccessCA (calls at lines 70, 176, 216) and admin shortcuts at lines 39, 82. An earlier description draft mistakenly listed /api/v1/cas/{id}/rotate as affected, that endpoint is properly protected. CAs are not in this gap. Impact Any non-admin operator → admin via one curl (A). Any non-admin operator → ownership of any victim's hosts with cert + identity transfer (B). Mass cross-tenant CRUD including firewall-rule mutation (C). Any operator → disable/enable other operators, revoke their API keys, enumerate the operator roster. CVSS 3.1: AV:N/AC:L/PR:L/UI:N/S:C/C:H/I:H/A:H, 9.6. Suggested fix Shared helpers in a new internal/api/authz.go, mirroring the Web layer's loadAccessibleCA: Each loads the resource, resolves its CA via .CAID, accepts if actorIsAdmin(ctx) OR actor owns the CA. Reject 403 forbidden; audit-log api.<resource>.forbidden with the reason. The operator-management endpoints take requireAdmin instead (operator ownership doesn't map to CA ownership). Apply at the top of every host-, network-, firewall-, mobile-bundle-touching API handler, plus the 5 operator endpoints listed above. The legacy config-key path retains admin (preserves backward compatibility); the broader legacy-fallback question is tracked separately as issue #121. Test matrix admin → all operations permitted owning non-admin → operations on owned hosts/networks permitted non-owner non-admin → 403 + audit entry legacy config-key → preserved (admin) unauthenticated → existing 401 from middleware Coordinated context Subsumes public issue #119 (mobile-bundle authz). Issue #121 (actor.go:40 legacy-admin fallback) is a separate concern tracked independently.
The application does not perform an authorization check before performing a sensitive operation. Typical impact: unauthorized access to restricted functionality or data.
CVE-2026-47724 has a CVSS score of 9.9 (Critical). The vector is network-reachable, low privileges required, and no user interaction. A CVSS score reflects the worst-case severity of the vulnerability, not your specific exposure. Whether this affects your application depends on whether the vulnerable code is present and reachable in your environment.
A fixed version is available (0.3.4). Upgrading removes the vulnerable code path.
go
github.com/juev/nebula-mesh (< 0.3.4)github.com/juev/nebula-mesh → 0.3.4 (go)Severity tells you how bad this could be in the worst case. It does not tell you whether you are exposed. Exploitability and impact are functions of runtime truth: whether the vulnerable code is present, reachable, and actually executes in your application. A vulnerable package can sit in your dependency tree and never run.
Kodem, an Intelligent Application Security platform, uses runtime intelligence to reveal which vulnerabilities actually execute in production, so teams prioritize the ones that genuinely matter instead of chasing every advisory.
Kodem's runtime-powered SCA identifies whether CVE-2026-47724 is reachable in your applications. Explore open-source security for your team.
See if CVE-2026-47724 is reachable in your applications. Get a demo
Already deployed Kodem? See CVE-2026-47724 in your environment →Upgrade github.com/juev/nebula-mesh to 0.3.4 or later to resolve this vulnerability.
Kodem Kai can prioritize this vulnerability in your dependency tree and generate a fix recommendation.
CVE-2026-47724 is a critical-severity missing authorization vulnerability in github.com/juev/nebula-mesh (go), affecting versions < 0.3.4. It is fixed in 0.3.4. The application does not perform an authorization check before performing a sensitive operation.
CVE-2026-47724 has a CVSS score of 9.9 (Critical). This score reflects the worst-case severity of the vulnerability, not your specific exposure. Whether it represents real risk in your environment depends on whether the vulnerable code is present and reachable.
github.com/juev/nebula-mesh (go) versions < 0.3.4 is affected.
Yes. CVE-2026-47724 is fixed in 0.3.4. Upgrade to this version or later.
Whether CVE-2026-47724 is exploitable in your environment depends on whether the vulnerable code is present and reachable. A CVSS score is a worst-case rating; it does not account for your specific deployment, configuration, or usage patterns. Kodem, an Intelligent Application Security platform, uses runtime intelligence to show which vulnerabilities actually execute in production, so you can focus on the ones that represent real risk. Get a demo
Exploitability and impact are not fixed properties of a CVE. They depend on runtime truth: whether the vulnerable code is present, reachable, and actually executes in your application. A high CVSS score on a dependency that never runs is not the same as real risk. Kodem, an Intelligent Application Security platform, uses runtime intelligence to reveal which vulnerabilities actually execute in production, so teams prioritize the ones that genuinely matter.
Upgrade github.com/juev/nebula-mesh to 0.3.4 or later.