From ff1c455a16e7ef6a78567ce6459f946bd6606d8a Mon Sep 17 00:00:00 2001 From: martinRenou Date: Thu, 5 Jan 2023 11:02:10 +0100 Subject: [PATCH 01/12] Allow pre-installing pip packages --- docs/build-environment.yml | 2 +- docs/environment.yml | 4 +++- jupyterlite_xeus_python/build.py | 33 +++++++++++++++++++++++++++----- 3 files changed, 32 insertions(+), 7 deletions(-) diff --git a/docs/build-environment.yml b/docs/build-environment.yml index f49ab48..ce9abcf 100644 --- a/docs/build-environment.yml +++ b/docs/build-environment.yml @@ -14,7 +14,7 @@ dependencies: - yarn - jupyterlab >=3.5.3,<3.6 - jupyterlite-core >=0.1.0,<0.2.0 - - empack >=3,<4 - pip: - jupyterlite-sphinx + - git+https://github.com/martinRenou/empack.git@pip - .. diff --git a/docs/environment.yml b/docs/environment.yml index 751e008..5fc92dd 100644 --- a/docs/environment.yml +++ b/docs/environment.yml @@ -5,4 +5,6 @@ channels: dependencies: - numpy - matplotlib - - ipycanvas + - mpmath + - pip: + - ipycanvas diff --git a/jupyterlite_xeus_python/build.py b/jupyterlite_xeus_python/build.py index 9011187..04ea3cf 100644 --- a/jupyterlite_xeus_python/build.py +++ b/jupyterlite_xeus_python/build.py @@ -6,6 +6,7 @@ from subprocess import check_call, run, DEVNULL from typing import List from urllib.parse import urlparse +import sys import yaml @@ -25,7 +26,9 @@ MICROMAMBA_COMMAND = shutil.which("micromamba") CONDA_COMMAND = shutil.which("conda") -PYTHON_VERSION = "3.10" +PYTHON_MAJOR = 3 +PYTHON_MINOR = 10 +PYTHON_VERSION = f"{PYTHON_MAJOR}.{PYTHON_MINOR}" XEUS_PYTHON_VERSION = "0.15.9" @@ -119,6 +122,23 @@ def _create_config(prefix_path): os.environ["CONDARC"] = str(prefix_path / ".condarc") +def _install_pip_dependencies(prefix_path, dependencies): + run( + [ + "pip", + "install", + *dependencies, + "--prefix", + prefix_path, + "--python-version", + PYTHON_VERSION, + "--no-input", + "--verbose", + ], + check=True, + ) + + def build_and_pack_emscripten_env( python_version: str = PYTHON_VERSION, xeus_python_version: str = XEUS_PYTHON_VERSION, @@ -146,6 +166,8 @@ def build_and_pack_emscripten_env( if packages or xeus_python_version or environment_file: bail_early = False + pip_dependencies = [] + # Process environment.yml file if environment_file and Path(environment_file).exists(): bail_early = False @@ -168,10 +190,7 @@ def build_and_pack_emscripten_env( if isinstance(dependency, str) and dependency not in specs: specs.append(dependency) elif isinstance(dependency, dict) and dependency.get("pip") is not None: - raise RuntimeError( - """Cannot install pip dependencies in the xeus-python Emscripten environment (yet?). - """ - ) + pip_dependencies = dependency["pip"] # Bail early if there is nothing to do if bail_early and not force: @@ -192,6 +211,10 @@ def build_and_pack_emscripten_env( # Create emscripten env with the given packages create_env(env_name, root_prefix, specs, channels) + # Install pip dependencies + if pip_dependencies: + _install_pip_dependencies(prefix_path, pip_dependencies) + pack_kwargs = {} # Download env filter config From 01cf5379fc003984289b6943dd3f51ff3cdf1f84 Mon Sep 17 00:00:00 2001 From: martinRenou Date: Thu, 20 Jul 2023 15:01:34 +0200 Subject: [PATCH 02/12] Run blabk --- docs/conf.py | 22 +++++++++++----------- jupyterlite_xeus_python/build.py | 11 ++++++----- jupyterlite_xeus_python/env_build_addon.py | 6 +----- tests/test_xeus_python_env.py | 16 ++++++++++++---- 4 files changed, 30 insertions(+), 25 deletions(-) diff --git a/docs/conf.py b/docs/conf.py index 4fcece8..c14246c 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -1,20 +1,20 @@ # -*- coding: utf-8 -*- extensions = [ - 'jupyterlite_sphinx', - 'myst_parser', + "jupyterlite_sphinx", + "myst_parser", ] myst_enable_extensions = [ "linkify", ] -master_doc = 'index' -source_suffix = '.rst' +master_doc = "index" +source_suffix = ".rst" -project = 'jupyterlite-xeus-python' -copyright = 'JupyterLite Team' -author = 'JupyterLite Team' +project = "jupyterlite-xeus-python" +copyright = "JupyterLite Team" +author = "JupyterLite Team" exclude_patterns = [] @@ -23,8 +23,8 @@ jupyterlite_dir = "." html_theme_options = { - "logo": { - "image_light": "xeus-python.svg", - "image_dark": "xeus-python.svg", - } + "logo": { + "image_light": "xeus-python.svg", + "image_dark": "xeus-python.svg", + } } diff --git a/jupyterlite_xeus_python/build.py b/jupyterlite_xeus_python/build.py index 04ea3cf..5c14ac8 100644 --- a/jupyterlite_xeus_python/build.py +++ b/jupyterlite_xeus_python/build.py @@ -226,9 +226,7 @@ def build_and_pack_emscripten_env( yaml.safe_load(empack_config_content) ) else: - pack_kwargs["file_filters"] = pkg_file_filter_from_yaml( - empack_config - ) + pack_kwargs["file_filters"] = pkg_file_filter_from_yaml(empack_config) else: pack_kwargs["file_filters"] = pkg_file_filter_from_yaml(DEFAULT_CONFIG_PATH) @@ -258,13 +256,16 @@ def build_and_pack_emscripten_env( worker = worker.replace("XEUS_KERNEL_FILE", "'xpython_wasm.js'") worker = worker.replace("LANGUAGE_DATA_FILE", "'python_data.js'") - worker = worker.replace("importScripts(DATA_FILE);", """ + worker = worker.replace( + "importScripts(DATA_FILE);", + """ await globalThis.Module.bootstrap_from_empack_packed_environment( `./empack_env_meta.json`, /* packages_json_url */ ".", /* package_tarballs_root_url */ false /* verbose */ ); - """) + """, + ) with open(Path(output_path) / "worker.ts", "w") as fobj: fobj.write(worker) diff --git a/jupyterlite_xeus_python/env_build_addon.py b/jupyterlite_xeus_python/env_build_addon.py index ca12d29..6c65451 100644 --- a/jupyterlite_xeus_python/env_build_addon.py +++ b/jupyterlite_xeus_python/env_build_addon.py @@ -38,7 +38,6 @@ def from_string(self, s): class XeusPythonEnv(FederatedExtensionAddon): - __all__ = ["post_build"] xeus_python_version = Unicode(XEUS_PYTHON_VERSION).tag( @@ -99,17 +98,14 @@ def post_build(self, manager): dest = self.output_extensions / "@jupyterlite" / "xeus-python-kernel" / "static" # copy *.tar.gz for all side packages - for item in Path(self.cwd.name) .iterdir(): + for item in Path(self.cwd.name).iterdir(): if item.suffix == ".gz": - file = item.name yield dict( name=f"xeus:copy:{file}", actions=[(self.copy_one, [item, dest / file])], ) - - for file in [ "empack_env_meta.json", "xpython_wasm.js", diff --git a/tests/test_xeus_python_env.py b/tests/test_xeus_python_env.py index 068597b..9f797e8 100644 --- a/tests/test_xeus_python_env.py +++ b/tests/test_xeus_python_env.py @@ -23,8 +23,12 @@ def test_python_env(): # Check env assert os.path.isdir("/tmp/xeus-python-kernel/envs/xeus-python-kernel") - assert os.path.isfile("/tmp/xeus-python-kernel/envs/xeus-python-kernel/bin/xpython_wasm.js") - assert os.path.isfile("/tmp/xeus-python-kernel/envs/xeus-python-kernel/bin/xpython_wasm.wasm") + assert os.path.isfile( + "/tmp/xeus-python-kernel/envs/xeus-python-kernel/bin/xpython_wasm.js" + ) + assert os.path.isfile( + "/tmp/xeus-python-kernel/envs/xeus-python-kernel/bin/xpython_wasm.wasm" + ) # Check empack output assert os.path.isfile(Path(addon.cwd.name) / "empack_env_meta.json") @@ -46,8 +50,12 @@ def test_python_env_from_file_1(): # Check env assert os.path.isdir("/tmp/xeus-python-kernel/envs/xeus-python-kernel-1") - assert os.path.isfile("/tmp/xeus-python-kernel/envs/xeus-python-kernel-1/bin/xpython_wasm.js") - assert os.path.isfile("/tmp/xeus-python-kernel/envs/xeus-python-kernel-1/bin/xpython_wasm.wasm") + assert os.path.isfile( + "/tmp/xeus-python-kernel/envs/xeus-python-kernel-1/bin/xpython_wasm.js" + ) + assert os.path.isfile( + "/tmp/xeus-python-kernel/envs/xeus-python-kernel-1/bin/xpython_wasm.wasm" + ) # Check empack output assert os.path.isfile(Path(addon.cwd.name) / "empack_env_meta.json") From 7d73e7618aa6b93edb5f055252f3f7355b767c6a Mon Sep 17 00:00:00 2001 From: martinRenou Date: Thu, 20 Jul 2023 16:15:26 +0200 Subject: [PATCH 03/12] Iterate --- docs/environment.yml | 3 ++- jupyterlite_xeus_python/build.py | 25 ++++++++++++++++++---- jupyterlite_xeus_python/env_build_addon.py | 1 + 3 files changed, 24 insertions(+), 5 deletions(-) diff --git a/docs/environment.yml b/docs/environment.yml index 5fc92dd..c336496 100644 --- a/docs/environment.yml +++ b/docs/environment.yml @@ -5,6 +5,7 @@ channels: dependencies: - numpy - matplotlib - - mpmath + - pillow + - ipywidgets - pip: - ipycanvas diff --git a/jupyterlite_xeus_python/build.py b/jupyterlite_xeus_python/build.py index 5c14ac8..e7f47d0 100644 --- a/jupyterlite_xeus_python/build.py +++ b/jupyterlite_xeus_python/build.py @@ -122,7 +122,23 @@ def _create_config(prefix_path): os.environ["CONDARC"] = str(prefix_path / ".condarc") -def _install_pip_dependencies(prefix_path, dependencies): +def _install_pip_dependencies(prefix_path, dependencies, log=None): + env = os.environ.copy() + + env["VIRTUAL_ENV"] = prefix_path + env["PYTHONPATH"] = ( + prefix_path / "lib" / f"python{PYTHON_VERSION}" / "site-packages" + ) + + if log is not None: + log.warning( + """ + Installing pip dependencies. Use this feature at your own risks. + Note that you can only install pure-python packages, pip is being run with the + --no-deps option to not pull undesired system-specific dependencies. + """ + ) + run( [ "pip", @@ -130,11 +146,11 @@ def _install_pip_dependencies(prefix_path, dependencies): *dependencies, "--prefix", prefix_path, - "--python-version", - PYTHON_VERSION, + "--no-deps", "--no-input", "--verbose", ], + env=env, check=True, ) @@ -150,6 +166,7 @@ def build_and_pack_emscripten_env( output_path: str = ".", build_worker: bool = False, force: bool = False, + log=None, ): """Build a conda environment for the emscripten platform and pack it with empack.""" channels = copy(CHANNELS) @@ -213,7 +230,7 @@ def build_and_pack_emscripten_env( # Install pip dependencies if pip_dependencies: - _install_pip_dependencies(prefix_path, pip_dependencies) + _install_pip_dependencies(prefix_path, pip_dependencies, log=log) pack_kwargs = {} diff --git a/jupyterlite_xeus_python/env_build_addon.py b/jupyterlite_xeus_python/env_build_addon.py index 6c65451..037350a 100644 --- a/jupyterlite_xeus_python/env_build_addon.py +++ b/jupyterlite_xeus_python/env_build_addon.py @@ -85,6 +85,7 @@ def post_build(self, manager): environment_file=Path(self.manager.lite_dir) / self.environment_file, empack_config=self.empack_config, output_path=self.cwd.name, + log=self.log, ) # Find the federated extensions in the emscripten-env and install them From 7d666fe261d7d9d8c39c16f0de1e8d4387e3b41d Mon Sep 17 00:00:00 2001 From: martinRenou Date: Thu, 20 Jul 2023 17:32:34 +0200 Subject: [PATCH 04/12] Iterate --- jupyterlite_xeus_python/build.py | 47 ++++++++++++++++++++++++-------- 1 file changed, 35 insertions(+), 12 deletions(-) diff --git a/jupyterlite_xeus_python/build.py b/jupyterlite_xeus_python/build.py index e7f47d0..0777223 100644 --- a/jupyterlite_xeus_python/build.py +++ b/jupyterlite_xeus_python/build.py @@ -1,9 +1,11 @@ +import csv import os from copy import copy from pathlib import Path import requests import shutil from subprocess import check_call, run, DEVNULL +from tempfile import TemporaryDirectory from typing import List from urllib.parse import urlparse import sys @@ -123,37 +125,58 @@ def _create_config(prefix_path): def _install_pip_dependencies(prefix_path, dependencies, log=None): - env = os.environ.copy() - - env["VIRTUAL_ENV"] = prefix_path - env["PYTHONPATH"] = ( - prefix_path / "lib" / f"python{PYTHON_VERSION}" / "site-packages" - ) + # Why is this so damn complicated? + # Isn't it easier to download the .whl ourselves? pip is hell if log is not None: log.warning( """ - Installing pip dependencies. Use this feature at your own risks. - Note that you can only install pure-python packages, pip is being run with the - --no-deps option to not pull undesired system-specific dependencies. + Installing pip dependencies. This is very much experimental so use this feature at your own risks. + Note that you can only install pure-python packages. + pip is being run with the --no-deps option to not pull undesired system-specific dependencies, so please + install your package dependencies from emscripten-forge or conda-forge. """ ) + # Installing with pip in another prefix that has a different Python version IS NOT POSSIBLE + # So we need to do this whole mess "manually" + pkg_dir = TemporaryDirectory() + run( [ "pip", "install", *dependencies, - "--prefix", - prefix_path, + # Install in a tmp directory while we process it + "--target", + pkg_dir.name, + # Specify the right Python version + "--python-version", + PYTHON_VERSION, + # No dependency installed "--no-deps", "--no-input", "--verbose", ], - env=env, check=True, ) + # We need to read the RECORD and try to be smart about what goes + # under site-packages and what goes where + package_dist_info = Path(pkg_dir.name).glob("*.dist-info")[0] + + with open(dist_info / "RECORD") as record: + files = csv.reader(record) + all_files = [_file[0] for _file in files] + + files_outside_site_packages = [ + _file for _file in all_files if _file.startswith("../../") + ] + + # COPY files that are outside site packages under `prefix_path` + # COPY files that are inside site packages (including the dist-info) under `prefix_path / "lib" / f"python{PYTHON_VERSION} / "site-packages" + # PATCH the dist-info/RECORD with the new paths to assets outside site packages + def build_and_pack_emscripten_env( python_version: str = PYTHON_VERSION, From ebb0964eef62deffc959a36fbb2e92a651992cd9 Mon Sep 17 00:00:00 2001 From: martinRenou Date: Mon, 24 Jul 2023 10:11:52 +0200 Subject: [PATCH 05/12] Iterate --- jupyterlite_xeus_python/build.py | 45 +++++++++++++++++++++++++------- 1 file changed, 35 insertions(+), 10 deletions(-) diff --git a/jupyterlite_xeus_python/build.py b/jupyterlite_xeus_python/build.py index 0777223..5a1f167 100644 --- a/jupyterlite_xeus_python/build.py +++ b/jupyterlite_xeus_python/build.py @@ -163,19 +163,44 @@ def _install_pip_dependencies(prefix_path, dependencies, log=None): # We need to read the RECORD and try to be smart about what goes # under site-packages and what goes where - package_dist_info = Path(pkg_dir.name).glob("*.dist-info")[0] + packages_dist_info = Path(pkg_dir.name).glob("*.dist-info") - with open(dist_info / "RECORD") as record: - files = csv.reader(record) - all_files = [_file[0] for _file in files] + for package_dist_info in packages_dist_info: + with open(package_dist_info / "RECORD", "r") as record: + record_csv = csv.reader(record) + all_files = [_file[0] for _file in record_csv] - files_outside_site_packages = [ - _file for _file in all_files if _file.startswith("../../") - ] + non_supported_files = [".so", ".a", ".dylib", ".lib", ".exe" ".dll"] - # COPY files that are outside site packages under `prefix_path` - # COPY files that are inside site packages (including the dist-info) under `prefix_path / "lib" / f"python{PYTHON_VERSION} / "site-packages" - # PATCH the dist-info/RECORD with the new paths to assets outside site packages + # List of tuples: (path: str, inside_site_packages: bool) + files = [ + (_file, not _file.startswith("../../")) for _file in all_files + ] + + # Why? + record_data = record.read().replace("../../", "../../../") + + # OVERWRITE RECORD file + with open(package_dist_info / "RECORD", "w") as record: + record.write(record_data) + + # COPY files under `prefix_path` + for (_file, inside_site_packages) in files: + path = Path(_file) + + # FAIL if .so / .a / .dylib / .lib / .exe / .dll + if path.suffix in non_supported_files: + raise RuntimeError("Cannot install binary PyPi package, only pure Python packages are supported") + + file_path = _file[6:] if not inside_site_packages else _file + install_path = prefix_path if not inside_site_packages else prefix_path / "lib" / f"python{PYTHON_VERSION}" / "site-packages" + + src_path = Path(pkg_dir.name) / file_path + dest_path = install_path / file_path + + os.makedirs(dest_path.parent, exist_ok=True) + + shutil.copy(src_path, dest_path) def build_and_pack_emscripten_env( From d42cd450f2be6176f28639e5c173e70aadb9ca26 Mon Sep 17 00:00:00 2001 From: martinRenou Date: Mon, 24 Jul 2023 10:23:57 +0200 Subject: [PATCH 06/12] Fix RECORD --- jupyterlite_xeus_python/build.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/jupyterlite_xeus_python/build.py b/jupyterlite_xeus_python/build.py index 5a1f167..8a0e5ce 100644 --- a/jupyterlite_xeus_python/build.py +++ b/jupyterlite_xeus_python/build.py @@ -167,7 +167,8 @@ def _install_pip_dependencies(prefix_path, dependencies, log=None): for package_dist_info in packages_dist_info: with open(package_dist_info / "RECORD", "r") as record: - record_csv = csv.reader(record) + record_content = record.read() + record_csv = csv.reader(record_content.splitlines()) all_files = [_file[0] for _file in record_csv] non_supported_files = [".so", ".a", ".dylib", ".lib", ".exe" ".dll"] @@ -178,11 +179,11 @@ def _install_pip_dependencies(prefix_path, dependencies, log=None): ] # Why? - record_data = record.read().replace("../../", "../../../") + fixed_record_data = record_content.replace("../../", "../../../") # OVERWRITE RECORD file with open(package_dist_info / "RECORD", "w") as record: - record.write(record_data) + record.write(fixed_record_data) # COPY files under `prefix_path` for (_file, inside_site_packages) in files: From 8d1e03d72373b7a483bdf58ebf7d24de54e4df60 Mon Sep 17 00:00:00 2001 From: martinRenou Date: Mon, 24 Jul 2023 10:47:16 +0200 Subject: [PATCH 07/12] Run black --- jupyterlite_xeus_python/build.py | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/jupyterlite_xeus_python/build.py b/jupyterlite_xeus_python/build.py index 8a0e5ce..e8c8e4f 100644 --- a/jupyterlite_xeus_python/build.py +++ b/jupyterlite_xeus_python/build.py @@ -174,9 +174,7 @@ def _install_pip_dependencies(prefix_path, dependencies, log=None): non_supported_files = [".so", ".a", ".dylib", ".lib", ".exe" ".dll"] # List of tuples: (path: str, inside_site_packages: bool) - files = [ - (_file, not _file.startswith("../../")) for _file in all_files - ] + files = [(_file, not _file.startswith("../../")) for _file in all_files] # Why? fixed_record_data = record_content.replace("../../", "../../../") @@ -186,15 +184,21 @@ def _install_pip_dependencies(prefix_path, dependencies, log=None): record.write(fixed_record_data) # COPY files under `prefix_path` - for (_file, inside_site_packages) in files: + for _file, inside_site_packages in files: path = Path(_file) # FAIL if .so / .a / .dylib / .lib / .exe / .dll if path.suffix in non_supported_files: - raise RuntimeError("Cannot install binary PyPi package, only pure Python packages are supported") + raise RuntimeError( + "Cannot install binary PyPi package, only pure Python packages are supported" + ) file_path = _file[6:] if not inside_site_packages else _file - install_path = prefix_path if not inside_site_packages else prefix_path / "lib" / f"python{PYTHON_VERSION}" / "site-packages" + install_path = ( + prefix_path + if not inside_site_packages + else prefix_path / "lib" / f"python{PYTHON_VERSION}" / "site-packages" + ) src_path = Path(pkg_dir.name) / file_path dest_path = install_path / file_path From fb83cfa400eb0a3ca30ef16678b8a29cf64839bc Mon Sep 17 00:00:00 2001 From: martinRenou Date: Mon, 24 Jul 2023 11:13:08 +0200 Subject: [PATCH 08/12] Update comment Co-authored-by: Jeremy Tuloup --- jupyterlite_xeus_python/build.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/jupyterlite_xeus_python/build.py b/jupyterlite_xeus_python/build.py index e8c8e4f..e5973e9 100644 --- a/jupyterlite_xeus_python/build.py +++ b/jupyterlite_xeus_python/build.py @@ -190,7 +190,7 @@ def _install_pip_dependencies(prefix_path, dependencies, log=None): # FAIL if .so / .a / .dylib / .lib / .exe / .dll if path.suffix in non_supported_files: raise RuntimeError( - "Cannot install binary PyPi package, only pure Python packages are supported" + "Cannot install binary PyPI package, only pure Python packages are supported" ) file_path = _file[6:] if not inside_site_packages else _file From 0f0652c435703077996cbb3ea5cc387cf328df9b Mon Sep 17 00:00:00 2001 From: martinRenou Date: Mon, 24 Jul 2023 11:35:30 +0200 Subject: [PATCH 09/12] Install docs build dependencies from conda-forge --- docs/build-environment.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/build-environment.yml b/docs/build-environment.yml index ce9abcf..2cdcc72 100644 --- a/docs/build-environment.yml +++ b/docs/build-environment.yml @@ -14,7 +14,7 @@ dependencies: - yarn - jupyterlab >=3.5.3,<3.6 - jupyterlite-core >=0.1.0,<0.2.0 + - jupyterlite-sphinx + - empack >=3.1.0 - pip: - - jupyterlite-sphinx - - git+https://github.com/martinRenou/empack.git@pip - .. From 0c2fc94f93afdab90997ad9971604a39a942e5ca Mon Sep 17 00:00:00 2001 From: martinRenou Date: Mon, 24 Jul 2023 12:24:53 +0200 Subject: [PATCH 10/12] Update empack dependency --- setup.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/setup.py b/setup.py index 4b6d7f4..33e0454 100644 --- a/setup.py +++ b/setup.py @@ -61,7 +61,7 @@ "traitlets", "jupyterlite-core>=0.1.0", "requests", - "empack>=3,<4", + "empack>=3.1,<4", "typer", ], zip_safe=False, From 612832924060aa025142808b451497f38e3cac16 Mon Sep 17 00:00:00 2001 From: martinRenou Date: Mon, 24 Jul 2023 13:31:03 +0200 Subject: [PATCH 11/12] Use latest jupyterlite-sphinx in docs --- docs/build-environment.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/build-environment.yml b/docs/build-environment.yml index 2cdcc72..3befc5c 100644 --- a/docs/build-environment.yml +++ b/docs/build-environment.yml @@ -14,7 +14,7 @@ dependencies: - yarn - jupyterlab >=3.5.3,<3.6 - jupyterlite-core >=0.1.0,<0.2.0 - - jupyterlite-sphinx - empack >=3.1.0 - pip: + - jupyterlite-sphinx >=0.9.1 - .. From 10a8c4673acce791668a2e219de68fe10f47db76 Mon Sep 17 00:00:00 2001 From: martinRenou Date: Mon, 24 Jul 2023 14:15:53 +0200 Subject: [PATCH 12/12] Add some docs about the pip packages support --- README.md | 4 ---- docs/configuration.md | 39 ++++++++++++++++++++++++++++++++------- 2 files changed, 32 insertions(+), 11 deletions(-) diff --git a/README.md b/README.md index 1d3f1a3..89d535c 100644 --- a/README.md +++ b/README.md @@ -66,10 +66,6 @@ You can also pick another name for that environment file (*e.g.* `custom.yml`), jupyter lite build --XeusPythonEnv.environment_file=custom.yml ``` -#### About pip dependencies - -It is common to provide `pip` dependencies in a conda environment file, this is currently **not supported** by xeus-python. - ## Contributing ### Development install diff --git a/docs/configuration.md b/docs/configuration.md index 60512a9..4a7aa22 100644 --- a/docs/configuration.md +++ b/docs/configuration.md @@ -13,12 +13,12 @@ Say you want to install `NumPy`, `Matplotlib` and `ipycanvas`, it can be done by ``` name: xeus-python-kernel channels: -- https://repo.mamba.pm/emscripten-forge -- https://repo.mamba.pm/conda-forge + - https://repo.mamba.pm/emscripten-forge + - https://repo.mamba.pm/conda-forge dependencies: -- numpy -- matplotlib -- ipycanvas + - numpy + - matplotlib + - ipycanvas ``` Then you only need to build JupyterLite: @@ -33,8 +33,8 @@ You can also pick another name for that environment file (*e.g.* `custom.yml`), jupyter lite build --XeusPythonEnv.environment_file=custom.yml ``` -```{note} -It is common to provide `pip` dependencies in a conda environment file. This is currently **not supported** by xeus-python, but there is a [work-in-progress](https://github.com/jupyterlite/xeus-python-kernel/pull/102) to support it. +```{warning} +It is common to provide `pip` dependencies in a conda environment file. This is currently **partially supported** by xeus-python. See "pip packages" section. ``` Then those packages are usable directly: @@ -55,6 +55,31 @@ Then those packages are usable directly: plt.show(); ``` +### pip packages + +⚠ This feature is experimental. You won't have the same user-experience as when using conda/mamba in a "normal" setup ⚠ + +`xeus-python` provides a way to install packages with pip. + +There are a couple of limitations that you should be aware of: +- it can only install pure Python packages (Python code + data files) +- it does not install the package dependencies, you should make sure to install them yourself using conda-forge/emscripten-forge. + +For example, if you were to install `ipycanvas` from PyPI, you would need to install the ipycanvas dependencies for it to work (`pillow`, `numpy` and `ipywidgets`): + +``` +name: xeus-python-kernel +channels: + - https://repo.mamba.pm/emscripten-forge + - https://repo.mamba.pm/conda-forge +dependencies: + - numpy + - pillow + - ipywidgets + - pip: + - ipycanvas +``` + ## Advanced Configuration ```{warning}