GHSA-whvh-wf3x-g77j

GHSA-whvh-wf3x-g77j LOW
Published July 22, 2026

The extension allowlist/blocklist check inside `PyPIExtensionManager.install()` was not enforced due to a missing await. For purposes of JupyterLab this was a secondary defense-in-depth check: `install()` was intended to enforce the allowlist/blocklist itself for any future uses and users calling...

Full CISO analysis pending enrichment.

What systems are affected?

Package Ecosystem Vulnerable Range Patched
Jupyter pip >= 4.6.0, <= 4.6.1 4.6.2
13.2K OpenSSF 5.8 1.9K dependents Pushed 7d ago 56% patched ~28d to patch Full package profile →

Do you use Jupyter? You're affected.

How severe is it?

CVSS 3.1
N/A
EPSS
N/A
Exploitation Status
No known exploitation
Sophistication
N/A

What is the attack surface?

AV AC PR UI S C I A
AV Network
AC Low
PR Low
UI None
S Unchanged
C None
I None
A None

What should I do?

Patch available

Update Jupyter to version 4.6.2

Which compliance frameworks are affected?

Compliance analysis pending. Sign in for full compliance mapping when available.

Frequently Asked Questions

What is GHSA-whvh-wf3x-g77j?

The extension allowlist/blocklist check inside `PyPIExtensionManager.install()` was not enforced due to a missing await. For purposes of JupyterLab this was a secondary defense-in-depth check: `install()` was intended to enforce the allowlist/blocklist itself for any future uses and users calling this method directly (in addition to the separate check handling requests arriving through the HTTP API). The only runtime symptom was a `RuntimeWarning: coroutine 'is_install_allowed' was never awaited.` This has security implications only for deployments that combine all of the following: - a custom extension or downstream integration that imports `PyPIExtensionManager` and calls `install()` directly with a package name influenced by untrusted user input (the stock JupyterLab HTTP handler is not affected - it performs its own awaited allowlist check before calling `install()`); - an allowlist/blocklist configured with the intent of restricting which packages users can install; - the (default) PyPI Extension Manager enabled; and - kernels and terminals disabled or delegated to remote hosts, so that the custom extension's `install()` call is the only available package-install vector (otherwise a user with kernel access can install packages directly regardless of this check) ### Impact Low. No exposure for stock JupyterLab: the HTTP API and Extension Manager UI enforce the listing through a separate, correctly awaited check. The gap affected only custom extensions or downstream integrations that called the public `install()` method directly and relied on it to self-enforce. ### Patches JupyterLab [`v4.6.2`](https://github.com/jupyterlab/jupyterlab/releases/tag/v4.6.2) and [`v4.5.10`](https://github.com/jupyterlab/jupyterlab/releases/tag/v4.5.10) contain the patch. Users of applications that depend on JupyterLab, such as Notebook v7+, should update `jupyterlab` package too. ### Workarounds No action is required for deployments that only expose extension management through the JupyterLab HTTP API / Extension Manager UI, as that path was already enforcing the listing via the handler's own check. Deployments wanting to disable programmatic extension installation entirely can switch to the read-only extension manager: ```bash --LabApp.extension_manager=readonly ``` or the following traitlet: ```python c.LabApp.extension_manager = 'readonly' ``` You can confirm that the read-only manager is in use from GUI: <img width="293" height="293" alt="image" src="https://github.com/user-attachments/assets/8016c809-633e-4ed0-a5bc-6bc4793caa0f" />

Is GHSA-whvh-wf3x-g77j actively exploited?

No confirmed active exploitation of GHSA-whvh-wf3x-g77j has been reported, but organizations should still patch proactively.

How to fix GHSA-whvh-wf3x-g77j?

Update to patched version: Jupyter 4.6.2.

What is the CVSS score for GHSA-whvh-wf3x-g77j?

No CVSS score has been assigned yet.

What are the technical details?

Original Advisory

The extension allowlist/blocklist check inside `PyPIExtensionManager.install()` was not enforced due to a missing await. For purposes of JupyterLab this was a secondary defense-in-depth check: `install()` was intended to enforce the allowlist/blocklist itself for any future uses and users calling this method directly (in addition to the separate check handling requests arriving through the HTTP API). The only runtime symptom was a `RuntimeWarning: coroutine 'is_install_allowed' was never awaited.` This has security implications only for deployments that combine all of the following: - a custom extension or downstream integration that imports `PyPIExtensionManager` and calls `install()` directly with a package name influenced by untrusted user input (the stock JupyterLab HTTP handler is not affected - it performs its own awaited allowlist check before calling `install()`); - an allowlist/blocklist configured with the intent of restricting which packages users can install; - the (default) PyPI Extension Manager enabled; and - kernels and terminals disabled or delegated to remote hosts, so that the custom extension's `install()` call is the only available package-install vector (otherwise a user with kernel access can install packages directly regardless of this check) ### Impact Low. No exposure for stock JupyterLab: the HTTP API and Extension Manager UI enforce the listing through a separate, correctly awaited check. The gap affected only custom extensions or downstream integrations that called the public `install()` method directly and relied on it to self-enforce. ### Patches JupyterLab [`v4.6.2`](https://github.com/jupyterlab/jupyterlab/releases/tag/v4.6.2) and [`v4.5.10`](https://github.com/jupyterlab/jupyterlab/releases/tag/v4.5.10) contain the patch. Users of applications that depend on JupyterLab, such as Notebook v7+, should update `jupyterlab` package too. ### Workarounds No action is required for deployments that only expose extension management through the JupyterLab HTTP API / Extension Manager UI, as that path was already enforcing the listing via the handler's own check. Deployments wanting to disable programmatic extension installation entirely can switch to the read-only extension manager: ```bash --LabApp.extension_manager=readonly ``` or the following traitlet: ```python c.LabApp.extension_manager = 'readonly' ``` You can confirm that the read-only manager is in use from GUI: <img width="293" height="293" alt="image" src="https://github.com/user-attachments/assets/8016c809-633e-4ed0-a5bc-6bc4793caa0f" />

Weaknesses (CWE)

CWE-284 — Improper Access Control: The product does not restrict or incorrectly restricts access to a resource from an unauthorized actor.

  • [Architecture and Design, Operation] Very carefully manage the setting, management, and handling of privileges. Explicitly manage trust zones in the software.
  • [Architecture and Design] Compartmentalize the system to have "safe" areas where trust boundaries can be unambiguously drawn. Do not allow sensitive data to go outside of the trust boundary and always be careful when interfacing with a compartment outside of the safe area. Ensure that appropriate compartmentalization is built into the system design, and the compartmentalization allows for and reinforces privilege separation functionality. Architects and designers should rely on the principle of least privilege to decide the appropriate time to use privileges and the time to drop privileges.

Source: MITRE CWE corpus.

CVSS Vector

CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:N/I:N/A:N

Timeline

Published
July 22, 2026
Last Modified
July 22, 2026
First Seen
July 23, 2026

Related Vulnerabilities