jupyterlite-pyodide-lock#

Create pre-solved environments for jupyterlite-pyodide-kernel.

Addons#

Addons for supporting pyodide-lock in JupyterLite.

PyodideLockAddon#

A JupyterLite addon for patching pyodide-lock.json files.

class jupyterlite_pyodide_lock.addons.lock.PyodideLockAddon(**kwargs: Any)[source]#

Bases: BaseAddon

Patches a pyodide to include pyodide-kernel and custom packages.

Can handle simple PEP508 specs, wheels, and their dependencies.

Known Limitations:

  • Special pyodide-specific .zip packages are not supported.

  • specs and constraints may not use the pkg-name@http... form as they don’t resolve well in micropip yet

Create a configurable given a config config.

Parameters#

configConfig

If this is empty, default values are used. If config is a Config instance, it will be used to configure the instance.

parentConfigurable instance, optional

The parent Configurable instance of this object.

Notes#

Subclasses of Configurable must call the __init__() method of Configurable before doing anything else and using super():

class MyConfigurable(Configurable):
    def __init__(self, config=None):
        super(MyConfigurable, self).__init__(config=config)
        # Then any other code you need to finish initialization.

This ensures that instances will be configured properly.

aliases: ClassVar = {'pyodide-lock-date-epoch': 'PyodideLockAddon.lock_date_epoch'}#
property bootstrap_packages: list[str]#

Get wheels for loadPackages.

bootstrap_wheels c.PyodideLockAddon.bootstrap_wheels = TypedTuple()#

packages names from the lockfile (or .whl URLs or local paths) to load before the solve, such as a custom micropip

constraints c.PyodideLockAddon.constraints = TypedTuple()#

simple PEP-508 specifications that constrain the bootstrap solve. Requires micropip >=0.9.0.

copy_wheel(wheel) Generator[dict[str, Any], None, None][source]#

Copy one wheel to {output_dir}.

Parameters:

wheel (Path)

Return type:

Generator[dict[str, Any], None, None]

enabled c.PyodideLockAddon.enabled = Bool(False)#

whether pyodide-lock integration is enabled

extra_preload_packages c.PyodideLockAddon.extra_preload_packages = TypedTuple()#

extra packages to add to PyodideAddon.loadPyodideOptions.packages. These will be downloaded at kernel startup, and installed, but _not_ imported to sys.modules

property federated_wheel_dirs: list[Path]#

The locations of wheels referenced by federated labextensions.

get_packages() list[Path][source]#

Find all file-based packages to install with micropip.

Return type:

list[Path]

lock(*, packages, specs, constraints, lockfile) bool[source]#

Generate the lockfile.

Parameters:
Return type:

bool

lock_date_epoch c.PyodideLockAddon.lock_date_epoch = CInt(0)#

a UNIX epoch timestamp: packages modified after this time will be removed from proxied JSON responses

locker c.PyodideLockAddon.locker = Enum('BrowserLocker')#

approach to use for running pyodide and solving the lock: these will have further configuration options under the same-named configurable

property locker_config: Any#

A preview of the locker config.

property package_candidates: list[str]#

Get all paths (or URLs) that might be (or contain) packages.

packages c.PyodideLockAddon.packages = TypedTuple()#

URLs of packages, or local (folders of) compatible wheels for pyodide dependencies

post_build(manager) Generator[dict[str, Any], None, None][source]#

Collect all the packages and generate a pyodide-lock.json file.

This includes those provided by federated labextensions (such as jupyterlite-pyodide-kernel itself), copied during build:federated_extensions, which will be left in-place.

Parameters:

manager (LiteManager)

Return type:

Generator[dict[str, Any], None, None]

post_init(manager) Generator[dict[str, Any], None, None][source]#

Handle downloading of packages to the package cache.

Parameters:

manager (LiteManager)

Return type:

Generator[dict[str, Any], None, None]

pre_status(manager) Generator[dict[str, Any], None, None][source]#

Patch configuration of PyodideAddon if needed.

Parameters:

manager (LiteManager)

Return type:

Generator[dict[str, Any], None, None]

preload_packages c.PyodideLockAddon.preload_packages = TypedTuple()#

pyodide_kernel dependencies to add to PyodideAddon.loadPyodideOptions.packages. These will be downloaded and installed, but _not_ imported to sys.modules

pyodide_cdn_url Unicode('https://cdn.jsdelivr.net/pyodide/v0.27.6/full')#

the URL prefix for all packages not managed by pyodide-lock

pyodide_url Unicode('https://github.com/pyodide/pyodide/releases/download/0.27.6/pyodide-core-0.27.6.tar.bz2')#

a URL, folder, or path to a pyodide distribution, if not configured in PyodideAddon.pyodide_url

resolve_one_file_requirement(path_or_url, cache_root) Generator[dict[str, Any], None, None][source]#

Download a wheel, and copy to the cache.

Parameters:
Return type:

Generator[dict[str, Any], None, None]

specs c.PyodideLockAddon.specs = TypedTuple()#

simple PEP-508 specifications for pyodide dependencies; may not be of the form name@http:.. (use .packages)

status(manager) Generator[dict[str, Any], None, None][source]#

Report on the status of pyodide-lock.

Parameters:

manager (LiteManager)

Return type:

Generator[dict[str, Any], None, None]

property well_known_packages: Path#

The location of .whl in the {lite_dir} to pick up.

jupyterlite_pyodide_lock.addons.lock.list_packages(package_dir) list[Path][source]#

Get all wheels we know how to handle in a directory.

Parameters:

package_dir (Path)

Return type:

list[Path]

PyodideLockOfflineAddon#

A JupyterLite addon for resolving remote pyodide-lock.json.

class jupyterlite_pyodide_lock.addons.offline.PyodideLockOfflineAddon(**kwargs: Any)[source]#

Bases: BaseAddon

Rewrite pyodide-lock.json with locally-downloaded packages.

Create a configurable given a config config.

Parameters#

configConfig

If this is empty, default values are used. If config is a Config instance, it will be used to configure the instance.

parentConfigurable instance, optional

The parent Configurable instance of this object.

Notes#

Subclasses of Configurable must call the __init__() method of Configurable before doing anything else and using super():

class MyConfigurable(Configurable):
    def __init__(self, config=None):
        super(MyConfigurable, self).__init__(config=config)
        # Then any other code you need to finish initialization.

This ensures that instances will be configured properly.

property all_excludes: list[str]#

Get all exclusion patterns.

property all_includes: list[str]#

Get all inclusion patterns.

enabled c.PyodideLockOfflineAddon.enabled = Bool(False)#

whether pyodide-lock integration is enabled

excludes c.PyodideLockOfflineAddon.excludes = TypedTuple()#

regular expressions to exclude from downloading

extra_excludes c.PyodideLockOfflineAddon.extra_excludes = TypedTuple()#

more regular expressions to exclude from downloading

extra_includes c.PyodideLockOfflineAddon.extra_includes = TypedTuple()#

more regular expressions for package names to download for offline usage

get_included_names(raw_packages) tuple[set[str], set[str]][source]#

Generate the lock.

Parameters:

raw_packages (dict[str, dict[str, Any]])

Return type:

tuple[set[str], set[str]]

get_pruned_packges(raw_packages, leaf_included, dep_included) dict[str, dict[str, Any]][source]#

Provide a copy of packages, potentially with pruning.

Parameters:
Return type:

dict[str, dict[str, Any]]

includes c.PyodideLockOfflineAddon.includes = TypedTuple()#

regular expressions for package names to download for offline usage

is_included(pkg_name, includes, excludes) bool[source]#

Get the URL and filename if a package should be downloaded.

Parameters:
Return type:

bool

property offline_lockfile: Path#

A convenience property for a derived offline pyodide-lock output.

post_build(manager) Generator[dict[str, Any], None, None][source]#

Collect all the packages and generate a pyodide-lock.json file.

Parameters:

manager (LiteManager)

Return type:

Generator[dict[str, Any], None, None]

prune c.PyodideLockOfflineAddon.prune = Bool(False)#

prune packages not requested to be offline

resolve_offline() bool[source]#

Download and rewrite lockfile with selected packages and dependencies.

Return type:

bool

resolve_one_offline(pkg_name, out_dir, stem, packages) None[source]#

Rewrite a single package’s info (if needed).

Parameters:
Return type:

None

status(manager) Generator[dict[str, Any], None, None][source]#

Report on the status of offline pyodide-lock.

Parameters:

manager (LiteManager)

Return type:

Generator[dict[str, Any], None, None]

FixHtmlConfigAddon#

An addon for patching paths in jupyter-config-data in HTML files.

class jupyterlite_pyodide_lock.addons.fix_html_config.FixHtmlConfigAddon(**kwargs: Any)[source]#

Bases: BaseAddon

Patch jupyter-config-data scripts in HTML.

Create a configurable given a config config.

Parameters#

configConfig

If this is empty, default values are used. If config is a Config instance, it will be used to configure the instance.

parentConfigurable instance, optional

The parent Configurable instance of this object.

Notes#

Subclasses of Configurable must call the __init__() method of Configurable before doing anything else and using super():

class MyConfigurable(Configurable):
    def __init__(self, config=None):
        super(MyConfigurable, self).__init__(config=config)
        # Then any other code you need to finish initialization.

This ensures that instances will be configured properly.

enabled c.FixHtmlConfigAddon.enabled = Bool(False)#

enable fixing paths of jupyter-config-data in HTML

extra_ignore_attributes TypedTuple()#

extra jupyter-config-data attributes to ignore

file_dep c.FixHtmlConfigAddon.file_dep = TypedTuple()#

output HTML globs that should be updated for pyodide-lock.json, e.g. ['voici/**/*.html']

ignore_attributes TypedTuple()#

jupyter-config-data attributes to ignore

post_build(manager) TTaskGenerator[source]#

Fix embedded jupyter-config-data in HTML paths.

Parameters:

manager (LiteManager)

Return type:

Generator[dict[str, Any], None, None]

task_dep c.FixHtmlConfigAddon.task_dep = TypedTuple()#

task names to wait for; may use any manager traits e.g. ['post_build:voici:voici:update_index:{output_dir}']

Lockers#

pyodide-lock.json resolvers.

jupyterlite_pyodide_lock.lockers.get_locker_entry_points(force: Any = None) dict[str, EntryPoint][source]#

Discover (and cache) modern entrypoints as a dict with sorted keys.

Pass some noise (like date.date) to the force argument to reload.

Parameters:

force (Any, default: None)

Return type:

dict[str, EntryPoint]

BrowserLocker#

Solve pyodide-lock with the browser manged as a naive subprocess.

jupyterlite_pyodide_lock.lockers.browser.BROWSERS = {'chrome': {'headless': ['--headless=new'], 'launch': ['google-chrome', '--new-window'], 'private_mode': ['--incognito'], 'profile': ['--user-data-dir={PROFILE_DIR}']}, 'chromium': {'headless': ['--headless=new'], 'launch': ['chromium-browser', '--new-window'], 'private_mode': ['--incognito'], 'profile': ['--user-data-dir={PROFILE_DIR}']}, 'firefox': {'headless': ['--headless'], 'launch': ['firefox'], 'private_mode': ['--private-window'], 'profile': ['--new-instance', '--profile', '{PROFILE_DIR}']}}#

browser CLI args, keyed by configurable

jupyterlite_pyodide_lock.lockers.browser.BROWSER_CHROMIUM_BASE = {'headless': ['--headless=new'], 'private_mode': ['--incognito'], 'profile': ['--user-data-dir={PROFILE_DIR}']}#

chromium base args

class jupyterlite_pyodide_lock.lockers.browser.BrowserLocker(**kwargs) None[source]#

Bases: TornadoLocker

Use a web server and browser subprocess to build a pyodide-lock.json.

See tornado.TornadoLocker for server details.

Parameters:

kwargs (Any)

Create a configurable given a config config.

Parameters#

configConfig

If this is empty, default values are used. If config is a Config instance, it will be used to configure the instance.

parentConfigurable instance, optional

The parent Configurable instance of this object.

Notes#

Subclasses of Configurable must call the __init__() method of Configurable before doing anything else and using super():

class MyConfigurable(Configurable):
    def __init__(self, config=None):
        super(MyConfigurable, self).__init__(config=config)
        # Then any other code you need to finish initialization.

This ensures that instances will be configured properly.

param kwargs:

type kwargs:

Any

browser c.BrowserLocker.browser = Unicode('')#

an alias for a pre-configured browser

browser_argv c.BrowserLocker.browser_argv = TypedTuple()#

the non-URL arguments for the browser process: if configured, ignore ‘browser’, ‘headless’, ‘private_mode’, ‘temp_profile’, and ‘profile’

browser_cli_arg(browser, trait_name) list[str][source]#

Find the CLI args for specific browser by trait name.

Parameters:
  • browser (str)

  • trait_name (str)

Return type:

list[str]

cleanup() None[source]#

Clean up the browser process and profile directory.

Return type:

None

ensure_temp_profile(baseline=None) str[source]#

Create a temporary browser profile.

Parameters:

baseline (Path | None, default: None)

Return type:

str

extra_browser_argv c.BrowserLocker.extra_browser_argv = TypedTuple()#

additional non-URL arguments for the browser process.

extra_micropip_args c.BrowserLocker.extra_micropip_args = Dict()#

options for micropip.install

async fetch() None[source]#

Open the browser to the lock page, and wait for it to finish.

Return type:

None

headless c.BrowserLocker.headless = Bool(True)#

run the browser in headless mode

host c.BrowserLocker.host = Unicode('127.0.0.1')#

the host on which to bind

port c.BrowserLocker.port = Int(0)#

the port on which to listen

private_mode c.BrowserLocker.private_mode = Bool(True)#

run the browser in private mode

profile c.BrowserLocker.profile = Unicode(None)#

run the browser with a copy of the given profile directory

protocol c.BrowserLocker.protocol = Unicode('http')#

the protocol to serve

pyodide_cdn_url c.BrowserLocker.pyodide_cdn_url = Unicode('https://cdn.jsdelivr.net/pyodide/v0.27.6/full')#

remote URL for the version of a full pyodide distribution; defaults to the version provided by jupyterlite_pyodide_kernel

pypi_api_url c.BrowserLocker.pypi_api_url = Unicode('https://pypi.org/pypi')#

remote URL for a Warehouse-compatible JSON API

temp_profile c.BrowserLocker.temp_profile = Bool(True)#

run the browser with a temporary profile: clobbered by profile

timeout c.BrowserLocker.timeout = Int(0)#

seconds to wait for a solve

tornado_settings c.BrowserLocker.tornado_settings = Dict()#

override settings used by the tornado server

Locker Bases#

BaseLocker#

Base classes for jupyterlite-pyodide-lock implementations.

class jupyterlite_pyodide_lock.lockers._base.BaseLocker(**kwargs) None[source]#

Bases: LoggingConfigurable

Common traits and methods for ‘pyodide-lock.json’ resolving strategies.

Parameters:

kwargs (Any)

Create a configurable given a config config.

Parameters#

configConfig

If this is empty, default values are used. If config is a Config instance, it will be used to configure the instance.

parentConfigurable instance, optional

The parent Configurable instance of this object.

Notes#

Subclasses of Configurable must call the __init__() method of Configurable before doing anything else and using super():

class MyConfigurable(Configurable):
    def __init__(self, config=None):
        super(MyConfigurable, self).__init__(config=config)
        # Then any other code you need to finish initialization.

This ensures that instances will be configured properly.

param kwargs:

type kwargs:

Any

constraints List()#
extra_micropip_args c.BaseLocker.extra_micropip_args = Dict()#

options for micropip.install

lockfile Instance()#
micropip_args Dict()#
packages List()#
parent Instance()#
pyodide_cdn_url c.BaseLocker.pyodide_cdn_url = Unicode('https://cdn.jsdelivr.net/pyodide/v0.27.6/full')#

remote URL for the version of a full pyodide distribution; defaults to the version provided by jupyterlite_pyodide_kernel

pypi_api_url c.BaseLocker.pypi_api_url = Unicode('https://pypi.org/pypi')#

remote URL for a Warehouse-compatible JSON API

pythonhosted_cdn_url Unicode('https://files.pythonhosted.org')#

remote URL for python packages (third-party not supported)

async resolve() bool | None[source]#

Asynchronous solve.

An async locker should overload this.

Return type:

bool | None

async resolve_async() bool | None[source]#

Asynchronous solve that handles timeout.

An async locker should _not_ overload this unless it has some other means of timing out.

Return type:

bool | None

resolve_sync() bool | None[source]#

Provide a sync facade for doing async solves, called by PyodideLockAddon.

If a locker is entirely synchronous, it can overload this.

Return type:

bool | None

specs List()#
timeout c.BaseLocker.timeout = Int(0)#

seconds to wait for a solve

TornadoLocker#

Host a tornado web application to solve``pyodide-lock.json`` .

jupyterlite_pyodide_lock.lockers.tornado.THandler#

a type for tornado rules

alias of tuple[str, type, dict[str, Any]]

class jupyterlite_pyodide_lock.lockers.tornado.TornadoLocker(**kwargs) None[source]#

Bases: BaseLocker

Start a web server and a browser (somehow) to build a pyodide-lock.json.

For an example strategy, see browser.BrowserLocker.

The server serves a number of mostly-static files, with a fallback to any files in the output_dir.

GET of the page the client loads:

  • /lock.html

POST/GET of the initial baseline lockfile, to be updated with the lock solution:

  • /pyodide-lock.json

POST of log messages:

  • /log

GET of a Warehouse/pythonhosted CDN proxied to configured remote URLs:

  • /_proxy/pypi

  • /_proxy/pythonhosted

If an {output_dir}/static/pyodide distribution is found, these will also be proxied from the configured URL.

Parameters:

kwargs (Any)

Create a configurable given a config config.

Parameters#

configConfig

If this is empty, default values are used. If config is a Config instance, it will be used to configure the instance.

parentConfigurable instance, optional

The parent Configurable instance of this object.

Notes#

Subclasses of Configurable must call the __init__() method of Configurable before doing anything else and using super():

class MyConfigurable(Configurable):
    def __init__(self, config=None):
        super(MyConfigurable, self).__init__(config=config)
        # Then any other code you need to finish initialization.

This ensures that instances will be configured properly.

param kwargs:

type kwargs:

Any

property base_url: str#

The effective base URL.

property cache_dir: Path#

The location of cached files discovered during the solve.

cleanup() None[source]#

Handle any cleanup tasks, as needed by specific implementations.

Return type:

None

collect() dict[str, Path][source]#

Copy all packages in the cached lockfile to output_dir, and fix lock.

Return type:

dict[str, Path]

collect_one_package(package) dict[str, Path][source]#

Find a package in the cache.

Parameters:

package (dict[str, Any])

Return type:

dict[str, Path]

extra_micropip_args c.TornadoLocker.extra_micropip_args = Dict()#

options for micropip.install

async fetch() None[source]#

Actually perform the solve.

Return type:

None

fix_lock(found) None[source]#

Fill in missing metadata from the micropip.freeze output.

Parameters:

found (dict[str, Path])

Return type:

None

fix_one_package(root_posix, lock_dir, package, found_path) None[source]#

Update a pyodide-lock URL for deployment.

Parameters:
Return type:

None

host c.TornadoLocker.host = Unicode('127.0.0.1')#

the host on which to bind

property load_pyodide_options: dict[str, Any]#

Provide default loadPyodide options.

property lock_html_url: str#

The as-served URL for the lock HTML page.

property lockfile_cache: Path#

The location of the updated lockfile.

port c.TornadoLocker.port = Int(0)#

the port on which to listen

preflight() None[source]#

Prepare the cache.

The PyPI cache is removed before each build, as the JSON cache is invalidated by both references to the temporary files.pythonhosted.org proxy and a potential change to lock_date_epoch.

Return type:

None

protocol c.TornadoLocker.protocol = Unicode('http')#

the protocol to serve

pyodide_cdn_url c.TornadoLocker.pyodide_cdn_url = Unicode('https://cdn.jsdelivr.net/pyodide/v0.27.6/full')#

remote URL for the version of a full pyodide distribution; defaults to the version provided by jupyterlite_pyodide_kernel

pypi_api_url c.TornadoLocker.pypi_api_url = Unicode('https://pypi.org/pypi')#

remote URL for a Warehouse-compatible JSON API

async resolve() bool | None[source]#

Launch a web application, then delegate to actually run the solve.

Return type:

bool | None

timeout c.TornadoLocker.timeout = Int(0)#

seconds to wait for a solve

tornado_settings c.TornadoLocker.tornado_settings = Dict()#

override settings used by the tornado server

Miscellaneous#

Base Addons#

JupyterLite addon base for pyodide-lock.json.

class jupyterlite_pyodide_lock.addons._base.BaseAddon(**kwargs: Any)[source]#

Bases: _BaseAddon

A base for jupyterlite-pyodide-lock addons.

Create a configurable given a config config.

Parameters#

configConfig

If this is empty, default values are used. If config is a Config instance, it will be used to configure the instance.

parentConfigurable instance, optional

The parent Configurable instance of this object.

Notes#

Subclasses of Configurable must call the __init__() method of Configurable before doing anything else and using super():

class MyConfigurable(Configurable):
    def __init__(self, config=None):
        super(MyConfigurable, self).__init__(config=config)
        # Then any other code you need to finish initialization.

This ensures that instances will be configured properly.

property addons: dict[str, _BaseAddon]#
property cache_dir: Path#

Provide jupyterlite_core.addons.base.LiteBuildConfig.cache_dir.

enabled c.BaseAddon.enabled = Bool(False)#

whether pyodide-lock integration is enabled

property lite_dir: Path#

Provide jupyterlite_core.addons.base.LiteBuildConfig.lite_dir.

property lock_output_dir: Path#

The folder where the pyodide-lock.json and packages will be stored.

property lockfile: Path#

The pyodide-lock.json file in the {output_dir}.

property output_dir: Path#

Provide jupyterlite_core.addons.base.LiteBuildConfig.output_dir.

property package_cache: Path#

The root of the pyodide-lock cache.

patch_config(jupyterlite_json, lockfile) None[source]#

Update the runtime jupyter-lite-config.json.

Parameters:
  • jupyterlite_json (Path)

  • lockfile (Path)

Return type:

None

property pyodide_addon: PyodideAddon#

The manager’s pyodide addon, which will be reconfigured if needed.

property pyodide_lock_addon: BaseAddon#

The manager’s pyodide-lock addon.

property pyodide_lock_offline_addon: BaseAddon#

The manager’s pyodide-lock offline addon.

App#

A command line for pyodide-lock in JupyterLite.

class jupyterlite_pyodide_lock.app.BrowsersApp(**kwargs) None[source]#

Bases: DescribedMixin, JupyterApp

An app that lists discoverable browsers.

Parameters:

kwargs (Any)

answer_yes c.BrowsersApp.answer_yes = Bool(False)#

Answer yes to any prompts.

check_timeout c.BrowsersApp.check_timeout = Float(5.0)#

max seconds to wait to check a browser version

check_versions c.BrowsersApp.check_versions = Bool(False)#

fail if no browser versions are found

collect_browser(browser) dict[str, Any][source]#

Gather data for a single browser.

Parameters:

browser (str)

Return type:

dict[str, Any]

config_file c.BrowsersApp.config_file = Unicode('')#

Full path of a config file.

config_file_name c.BrowsersApp.config_file_name = Unicode('')#

Specify a config file to load.

emit_console(results) None[source]#

Print out logs for browsers.

Parameters:

results (dict[str, Any])

Return type:

None

emit_console_one_browser(browser, result) None[source]#

Print out logs for one browser.

Parameters:
Return type:

None

emit_json(results) None[source]#

Emit raw results JSON.

Parameters:

results (dict[str, Any])

Return type:

None

flags c.BrowsersApp.config_file_name = Unicode('')#
format c.BrowsersApp.format = Unicode('')#

output format, e.g. json

generate_config c.BrowsersApp.generate_config = Bool(False)#

Generate default config file.

get_browser_version(browser, found_bin) str | None[source]#

Try to get a browser version.

Parameters:
  • browser (str)

  • found_bin (str)

Return type:

str | None

log_datefmt c.BrowsersApp.log_datefmt = Unicode('%Y-%m-%d %H:%M:%S')#

The date format used by logging formatters for %(asctime)s

log_format c.BrowsersApp.log_format = Unicode('[%(name)s]%(highlevel)s %(message)s')#

The Logging format template

log_level c.BrowsersApp.log_level = Enum(30)#

Set the log level by value or name.

logging_config c.BrowsersApp.logging_config = Dict()#

Configure additional log handlers.

The default stderr logs handler is configured by the log_level, log_datefmt and log_format settings.

This configuration can be used to configure additional handlers (e.g. to output the log to a file) or for finer control over the default handlers.

If provided this should be a logging configuration dictionary, for more information see: https://docs.python.org/3/library/logging.config.html#logging-config-dictschema

This dictionary is merged with the base logging configuration which defines the following:

  • A logging formatter intended for interactive use called console.

  • A logging handler that writes to stderr called console which uses the formatter console.

  • A logger with the name of this application set to DEBUG level.

This example adds a new handler that writes to a file:

c.Application.logging_config = {
    "handlers": {
        "file": {
            "class": "logging.FileHandler",
            "level": "DEBUG",
            "filename": "<path/to/file>",
        }
    },
    "loggers": {
        "<application-name>": {
            "level": "DEBUG",
            # NOTE: if you don't list the default "console"
            # handler here then it will be disabled
            "handlers": ["console", "file"],
        },
    },
}
show_config c.BrowsersApp.show_config = Bool(False)#

Instead of starting the Application, dump configuration to stdout

show_config_json c.BrowsersApp.show_config_json = Bool(False)#

Instead of starting the Application, dump configuration to stdout (as JSON)

start() None[source]#

Run the application.

Return type:

None

version Unicode('0.2.0')#

version of the app

class jupyterlite_pyodide_lock.app.PyodideLockApp(**kwargs) None[source]#

Bases: DescribedMixin, JupyterApp

Tools for working with ‘pyodide-lock’ in JupyterLite.

Parameters:

kwargs (Any)

answer_yes c.PyodideLockApp.answer_yes = Bool(False)#

Answer yes to any prompts.

config_file c.PyodideLockApp.config_file = Unicode('')#

Full path of a config file.

config_file_name c.PyodideLockApp.config_file_name = Unicode('')#

Specify a config file to load.

generate_config c.PyodideLockApp.generate_config = Bool(False)#

Generate default config file.

log_datefmt c.PyodideLockApp.log_datefmt = Unicode('%Y-%m-%d %H:%M:%S')#

The date format used by logging formatters for %(asctime)s

log_format c.PyodideLockApp.log_format = Unicode('[%(name)s]%(highlevel)s %(message)s')#

The Logging format template

log_level c.PyodideLockApp.log_level = Enum(30)#

Set the log level by value or name.

logging_config c.PyodideLockApp.logging_config = Dict()#

Configure additional log handlers.

The default stderr logs handler is configured by the log_level, log_datefmt and log_format settings.

This configuration can be used to configure additional handlers (e.g. to output the log to a file) or for finer control over the default handlers.

If provided this should be a logging configuration dictionary, for more information see: https://docs.python.org/3/library/logging.config.html#logging-config-dictschema

This dictionary is merged with the base logging configuration which defines the following:

  • A logging formatter intended for interactive use called console.

  • A logging handler that writes to stderr called console which uses the formatter console.

  • A logger with the name of this application set to DEBUG level.

This example adds a new handler that writes to a file:

c.Application.logging_config = {
    "handlers": {
        "file": {
            "class": "logging.FileHandler",
            "level": "DEBUG",
            "filename": "<path/to/file>",
        }
    },
    "loggers": {
        "<application-name>": {
            "level": "DEBUG",
            # NOTE: if you don't list the default "console"
            # handler here then it will be disabled
            "handlers": ["console", "file"],
        },
    },
}
show_config c.PyodideLockApp.show_config = Bool(False)#

Instead of starting the Application, dump configuration to stdout

show_config_json c.PyodideLockApp.show_config_json = Bool(False)#

Instead of starting the Application, dump configuration to stdout (as JSON)

subcommands c.PyodideLockApp.show_config_json = Bool(False)#
version Unicode('0.2.0')#

Tornado Handlers#

Tornado handlers for BrowserLocker.

jupyterlite_pyodide_lock.lockers.handlers.make_handlers(locker) tuple[tuple[str, type, dict[str, Any]]][source]#

Create the default handlers used for serving proxied CDN assets and locking.

Parameters:

locker (BrowserLocker)

Return type:

tuple[tuple[str, type, dict[str, Any]]]

jupyterlite_pyodide_lock.lockers.handlers.make_lock_date_epoch_replacer(locker) Callable[[str], str][source]#

Filter out releases newer than the lock date.

Parameters:

locker (BrowserLocker)

Return type:

Callable[[str], str]

jupyterlite_pyodide_lock.lockers.handlers.make_proxy(locker, path, remote, route=None, **extra_config) tuple[str, type, dict[str, Any]][source]#

Generate a proxied tornado handler rule.

Parameters:
Return type:

tuple[str, type, dict[str, Any]]

A tornado handler for proxying remote CDN files with a cache.

class jupyterlite_pyodide_lock.lockers.handlers.cacher.CachingRemoteFiles(application, request, **kwargs) None[source]#

Bases: ExtraMimeFiles

a handler which serves files from a cache, downloading them as needed.

Parameters:
  • application (Application)

  • request (HTTPServerRequest)

  • kwargs (Any)

async cache_file(path, cache_path) None[source]#

Get the file, and rewrite it.

Parameters:
Return type:

None

client: AsyncHTTPClient#

HTTP client

async fetch_body_with_retries(fetch_url, retries=5) bytes[source]#

Fetch the raw bytes of URL with retries.

In the event of a timeout, wait for an increasing number of seconds

Parameters:
  • fetch_url (str)

  • retries (int, default: 5)

Return type:

bytes

async get(path, include_body=True) None[source]#

Actually fetch a file.

Parameters:
  • path (str)

  • include_body (bool, default: True)

Return type:

None

initialize(*args, **kwargs) None[source]#

Extend the base initialize with instance members.

Parameters:
Return type:

None

remote: str#

remote URL root

rewrites: TRewriteMap#

URL patterns that should have text replaced

A tornado handler for accepting micropip.freeze output and errors.

class jupyterlite_pyodide_lock.lockers.handlers.freezer.MicropipFreeze(application, request, **kwargs) None[source]#

Bases: RequestHandler

Accept raw micropip.freeze output from the client and write it to disk.

Parameters:
  • application (Application)

  • request (HTTPServerRequest)

  • kwargs (Any)

initialize(locker, **kwargs) None[source]#

Initialize instance members.

Parameters:
Return type:

None

locker: BrowserLocker#
async post() None[source]#

Accept a pyodide-lock.json as the POST body.

Return type:

None

A handler that accepts log messages from the browser.

class jupyterlite_pyodide_lock.lockers.handlers.logger.Log(application, request, **kwargs) None[source]#

Bases: RequestHandler

Log repeater from the browser.

Parameters:
  • application (Application)

  • request (HTTPServerRequest)

  • kwargs (Any)

initialize(log, **kwargs) None[source]#

Initialize handler instance members.

Parameters:
Return type:

None

post(pipe) None[source]#

Accept a log message as the POST body.

Parameters:

pipe (str)

Return type:

None

A tornado handler with some extra MIME handling.

class jupyterlite_pyodide_lock.lockers.handlers.mime.ExtraMimeFiles(application, request, **kwargs) None[source]#

Bases: StaticFileHandler

Serve static files, with configurable MIME types.

Parameters:
  • application (Application)

  • request (HTTPServerRequest)

  • kwargs (Any)

get_content_type() str[source]#

Find an overloaded MIME type.

Return type:

str

initialize(log, mime_map=None, **kwargs) None[source]#

Initialize handler instance members.

Parameters:
Return type:

None

log: Logger#
mime_map: dict[str, str]#

map URL regex to content type

A tornado handler that serves a pyodide application, solves, and quits.

class jupyterlite_pyodide_lock.lockers.handlers.solver.SolverHTML(application, request, **kwargs) None[source]#

Bases: RequestHandler

Render a static HTML page to run micropip.freeze.

Parameters:
  • application (Application)

  • request (HTTPServerRequest)

  • kwargs (Any)

context: dict[str, str]#
async get(*args, **kwargs) None[source]#

Handle a GET request.

Parameters:
Return type:

None

initialize(context, *args, **kwargs) None[source]#

Initialize handler instance members.

Parameters:
Return type:

None

log: Logger#
template: Template#

Constants#

Constants for jupyterlite-pyodide-lock.

jupyterlite_pyodide_lock.constants.LOCKER_ENTRYPOINT = 'jupyterlite_pyodide_lock.locker.v0'#

the entry point name for locker implementations

jupyterlite_pyodide_lock.constants.LOCK_HTML = 'lock.html'#

the name of the hosted HTML app

jupyterlite_pyodide_lock.constants.NAME = 'jupyterlite-pyodide-lock'#

this distribution name

jupyterlite_pyodide_lock.constants.PROXY = '_proxy'#

the URL prefix for proxies

jupyterlite_pyodide_lock.constants.PYODIDE_LOCK_OFFLINE = 'pyodide-lock-offline.json'#

the default name for a re-solved offline lockfile

jupyterlite_pyodide_lock.constants.PYODIDE_LOCK_STEM = 'pyodide-lock'#

a base name for lock-related files

Utilities#

Utilities for psutil, the PyPI Warehouse API, and browsers.

jupyterlite_pyodide_lock.utils.TProcs#

some processes

alias of list[Process]

jupyterlite_pyodide_lock.utils.TWaitProcs#

the returned

alias of tuple[list[Process], list[Process]]

jupyterlite_pyodide_lock.utils.epoch_to_warehouse_date(epoch) str[source]#

Convert a UNIX epoch timestamp to a Warehouse upload date.

Parameters:

epoch (int)

Return type:

str

jupyterlite_pyodide_lock.utils.find_browser_binary(browser_binary, log) str[source]#

Resolve an absolute path to a browser binary.

Parameters:
Return type:

str

jupyterlite_pyodide_lock.utils.find_children(parent) list[Process][source]#

Try to find children processes.

Parameters:

parent (Process | None)

Return type:

list[Process]

jupyterlite_pyodide_lock.utils.get_browser_search_path() str[source]#

Append well-known browser locations to $PATH.

Return type:

str

jupyterlite_pyodide_lock.utils.get_unused_port(host='127.0.0.1') int[source]#

Get an unused ipv4 port.

Parameters:

host (str, default: '127.0.0.1')

Return type:

int

jupyterlite_pyodide_lock.utils.terminate_all(*parents, log=None) tuple[list[Process], list[Process]][source]#

Terminate processes and their children and wait for them to exit.

Parameters:
Return type:

tuple[list[Process], list[Process]]

jupyterlite_pyodide_lock.utils.url_wheel_filename(url_or_name) str | None[source]#

Check whether a string is a wheel URL, and return the filename.

Parameters:

url_or_name (str)

Return type:

str | None

jupyterlite_pyodide_lock.utils.warehouse_date_to_epoch(iso8601_str) int[source]#

Convert a Warehouse upload date to a UNIX epoch timestamp.

Parameters:

iso8601_str (str)

Return type:

int