Skip to content
Heist/ feed
Back to feed
Medium

Authorization Bypass in API Key/OAuth Scopes via Path Parsing Discrepancy

Type: advisorySources: OSV

Outline is a service that allows for collaborative documentation. Prior to 1.8.0, the AuthenticationHelper.canAccess function uses ctx.originalUrl to verify if an API key or OAuth token has the required scopes for a request. It extracts the resource by splitting the URL by / and taking the last segment. However, it fails to strip the URL fragment (#). Because Koa's router uses ctx.path (which strips the fragment) for routing, an attacker can append a fragment containing a permitted path (e.g., #foo/api/documents.info) to a restricted endpoint (e.g., /api/documents.create). The router will route the request to the restricted endpoint, but canAccess will evaluate the permitted path in the fragment, bypassing the API key scope restrictions and allowing privilege escalation. This vulnerability is fixed in 1.8.0.

Products
Not specified
Affected versions
Not specified
Fixed versions
Not specified
CVEs
CVE-2026-54573
Confirmed fixed CVEs
Not specified
Updated in this feed
2 Nov 2026, 21:09 UTC · Revision 1

Source evidence

Authorization Bypass in API Key/OAuth Scopes via Path Parsing Discrepancy

core-osv · Original source

Published 25 Jun 2026, 15:59 UTC

Outline is a service that allows for collaborative documentation. Prior to 1.8.0, the AuthenticationHelper.canAccess function uses ctx.originalUrl to verify if an API key or OAuth token has the required scopes for a request. It extracts the resource by splitting the URL by / and taking the last segment. However, it fails to strip the URL fragment (#). Because Koa's router uses ctx.path (which strips the fragment) for routing, an attacker can append a fragment containing a permitted path (e.g., #foo/api/documents.info) to a restricted endpoint (e.g., /api/documents.create). The router will route the request to the restricted endpoint, but canAccess will evaluate the permitted path in the fragment, bypassing the API key scope restrictions and allowing privilege escalation. This vulnerability is fixed in 1.8.0.

osv:CVE-2026-54573
Complete source record
{
  "id": "130c387dcbc32285a839f96efd8c405bc6d11ff107b186c7b890592cdf2ee4aa",
  "url": "https://osv.dev/vulnerability/CVE-2026-54573",
  "method": "structured",
  "payload": {
    "kind": "advisory",
    "title": "Authorization Bypass in API Key/OAuth Scopes via Path Parsing Discrepancy",
    "summary": "Outline is a service that allows for collaborative documentation. Prior to 1.8.0, the AuthenticationHelper.canAccess function uses ctx.originalUrl to verify if an API key or OAuth token has the required scopes for a request. It extracts the resource by splitting the URL by / and taking the last segment. However, it fails to strip the URL fragment (#). Because Koa's router uses ctx.path (which strips the fragment) for routing, an attacker can append a fragment containing a permitted path (e.g., #foo/api/documents.info) to a restricted endpoint (e.g., /api/documents.create). The router will route the request to the restricted endpoint, but canAccess will evaluate the permitted path in the fragment, bypassing the API key scope restrictions and allowing privilege escalation. This vulnerability is fixed in 1.8.0.",
    "evidence": "osv:CVE-2026-54573",
    "products": [],
    "severity": "medium",
    "structured": {
      "id": "CVE-2026-54573",
      "aliases": [
        "CVE-2026-54573",
        "GHSA-5x79-rj4g-qrh8"
      ],
      "metrics": [
        {
          "type": "CVSS_V4",
          "score": "CVSS:4.0/AV:N/AC:L/AT:N/PR:L/UI:N/VC:N/VI:L/VA:N/SC:N/SI:N/SA:N"
        }
      ],
      "affected": [
        {
          "ranges": [
            {
              "repo": "https://github.com/outline/outline",
              "type": "GIT",
              "events": [
                {
                  "introduced": "0"
                },
                {
                  "fixed": "b2309df76d18991bde369894c8a9054277eae698"
                }
              ],
              "database_specific": {
                "extracted_events": [
                  {
                    "range": [
                      {
                        "introduced": "0"
                      },
                      {
                        "fixed": "1.8.0"
                      }
                    ],
                    "source": "AFFECTED_FIELD",
                    "strategy": "StringRangeExpression"
                  },
                  {
                    "range": [
                      {
                        "introduced": "0"
                      },
                      {
                        "fixed": "1.8.0"
                      }
                    ],
                    "source": "DESCRIPTION"
                  }
                ]
              }
            }
          ],
          "versions": [
            "v1.7.1",
            "v1.7.0",
            "v1.6.1",
            "v1.6.0",
            "v1.5.0",
            "v1.4.0",
            "v1.2.0",
            "v1.2.0-0",
            "v1.1.0",
            "v1.0.1",
            "v1.0.0",
            "v0.87.4",
            "v0.87.2",
            "v0.87.1",
            "v0.87.0",
            "v0.86.0",
            "v0.82.0",
            "v0.80.2",
            "v0.80.1",
            "v0.80.0",
            "v0.79.1",
            "v0.79.0",
            "v0.78.0-0",
            "v0.77.1",
            "v0.77.0",
            "v0.76.2-0",
            "v0.76.1",
            "v0.76.0",
            "v0.76.0-2",
            "v0.76.0-1",
            "v0.76.0-0",
            "v0.75.2",
            "v0.75.1",
            "v0.75.0",
            "v0.73.1",
            "v0.73.0",
            "v0.72.0",
            "v0.71.0",
            "v0.70.2",
            "v0.70.1",
            "v0.70.0",
            "v0.69.1",
            "v0.69.0",
            "v0.67.2",
            "v0.67.1",
            "v0.67.0",
            "v0.67.0-pre.1",
            "v0.66.0",
            "v0.65.1",
            "v0.65.0",
            "v0.64.3",
            "v0.64.2",
            "v0.64.1",
            "v0.64.0",
            "v0.63.0",
            "v0.62.0",
            "v0.61.0",
            "v0.60.1",
            "v0.60.0",
            "v0.59.0",
            "v0.58.0",
            "v0.57.0",
            "v0.56.0",
            "v0.55.0",
            "v0.54.0",
            "v0.53.1",
            "v0.53.0",
            "v0.52.0",
            "v0.51.0",
            "v0.50.0",
            "v0.49.0",
            "v0.48.1",
            "v0.48.0",
            "v0.46.0",
            "v0.45.0",
            "v0.44.0",
            "v0.43.3",
            "v0.43.2",
            "v0.43.1",
            "v0.43.0",
            "v0.42.2",
            "v0.42.1",
            "v0.42.0",
            "v0.41.0",
            "v0.40.2",
            "v0.40.1",
            "v0.40.0",
            "v0.39.0",
            "0.39.0",
            "v0.38.1",
            "v0.38.0",
            "v0.37.0",
            "v0.36.1",
            "v0.36.0",
            "v0.35.0",
            "v0.34.0",
            "v0.33.0",
            "v0.32.0",
            "v0.31.0",
            "v0.30.0",
            "v0.29.0",
            "v0.28.0",
            "v0.27.0",
            "v0.26.0",
            "v0.25.0",
            "v0.24.0",
            "v0.23.0",
            "v0.22.1",
            "v0.22.0",
            "v0.21.0",
            "v0.20.0",
            "v0.19.1",
            "v0.19.0",
            "v0.18.0",
            "v0.16.3",
            "v0.16.2",
            "v0.17.0",
            "v0.16.1",
            "0.16.0",
            "v0.15.1",
            "v0.15.0",
            "v0.14.0",
            "v0.13.5",
            "v0.13.4",
            "v0.13.3",
            "v0.13.2",
            "v0.13.1",
            "v0.9.0",
            "v0.8.1",
            "v0.8.0",
            "v0.7.0",
            "v0.6.1",
            "v0.6.0",
            "v0.5.0",
            "v0.4.0",
            "v0.3.1",
            "v0.3.0",
            "v0.2.0",
            "0.1.0"
          ],
          "database_specific": {
            "source": "https://storage.googleapis.com/cve-osv-conversion/osv-output/CVE-2026-54573.json"
          }
        }
      ],
      "modified": "2026-10-28T02:30:23.693320759Z",
      "provider": "osv",
      "references": [
        "https://github.com/CVEProject/cvelistV5/tree/main/cves/2026/54xxx/CVE-2026-54573.json",
        "https://github.com/outline/outline/security/advisories/GHSA-5x79-rj4g-qrh8",
        "https://nvd.nist.gov/vuln/detail/CVE-2026-54573"
      ],
      "provider_metadata": {
        "cwe_ids": [
          "CWE-863"
        ],
        "cna_assigner": "GitHub_M",
        "osv_generated_from": "https://github.com/CVEProject/cvelistV5/tree/main/cves/2026/54xxx/CVE-2026-54573.json"
      }
    },
    "related_cves": [
      {
        "value": "CVE-2026-54573",
        "evidence": "/id"
      }
    ],
    "security_relevant": true,
    "severity_evidence": "/severity/0/score"
  },
  "source_id": "core-osv",
  "document_id": 490097,
  "published_at": "2026-06-25T15:59:35.297+00:00"
}