diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000000000000000000000000000000000000..f087b429e2f81a9f37b28a8308e2210f84df6c9b --- /dev/null +++ b/.gitattributes @@ -0,0 +1 @@ +*.tar.gz filter=lfs diff=lfs merge=lfs -text diff --git a/.lfsconfig b/.lfsconfig new file mode 100644 index 0000000000000000000000000000000000000000..464b9f9ff9ee7b75f7218a60674a362bf38fbe5e --- /dev/null +++ b/.lfsconfig @@ -0,0 +1,2 @@ +[lfs] + url = https://openeuler-bigfiles.test.osinfra.cn/Zherphy/software-package-server \ No newline at end of file diff --git a/0001-modify-the-version-limit-for-jupyter-core.patch b/0001-modify-the-version-limit-for-jupyter-core.patch new file mode 100644 index 0000000000000000000000000000000000000000..4ee40a52eb76a493ed9bce36edca7dd36f1caca9 --- /dev/null +++ b/0001-modify-the-version-limit-for-jupyter-core.patch @@ -0,0 +1,25 @@ +From efa4942f71b6234a3bdff56bb843b8decdb378ad Mon Sep 17 00:00:00 2001 +From: desert-sailor +Date: Wed, 6 Mar 2024 11:21:16 +0800 +Subject: [PATCH] modify the version limit for jupyter_core + +--- + pyproject.toml | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/pyproject.toml b/pyproject.toml +index a89f887..9ba4eca 100644 +--- a/pyproject.toml ++++ b/pyproject.toml +@@ -27,7 +27,7 @@ dependencies = [ + "argon2-cffi", + "jinja2", + "jupyter_client>=7.4.4", +- "jupyter_core>=4.12,!=5.0.*", ++ "jupyter_core>=5.3.0", + "jupyter_server_terminals", + "nbconvert>=6.4.4", + "nbformat>=5.3.0", +-- +2.43.0 + diff --git a/README.en.md b/README.en.md index 9b6d8f3afd5925e38efb522bf0955d947b983912..c9fc9a1439bb1b42752e0e5fbf30fb1604963c26 100644 --- a/README.en.md +++ b/README.en.md @@ -1,7 +1,10 @@ # software-package-server +# python-jupyter-server + #### Description Software package server is a unified component for openeuler community developer which try to simplify the source package contribution process. +The backend—i.e. core services, APIs, and REST endpoints—to Jupyter web applications. #### Software Architecture Software architecture description diff --git a/README.md b/README.md index f59aaf18a315e7ab8bb859534b20235ddafe2a82..df3bce43ba35e53eb09e412174429d3033d40a45 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,10 @@ # software-package-server +# python-jupyter-server + #### 介绍 Software package server is a unified component for openeuler community developer which try to simplify the source package contribution process. +The backend—i.e. core services, APIs, and REST endpoints—to Jupyter web applications. #### 软件架构 软件架构说明 diff --git a/backport-CVE-2024-35178-GHSA-hrw6-wg82-cm62.patch b/backport-CVE-2024-35178-GHSA-hrw6-wg82-cm62.patch new file mode 100644 index 0000000000000000000000000000000000000000..073e823a53f87bb387147f9f5c26202e08ae7fcb --- /dev/null +++ b/backport-CVE-2024-35178-GHSA-hrw6-wg82-cm62.patch @@ -0,0 +1,227 @@ +From 79fbf801c5908f4d1d9bc90004b74cfaaeeed2df Mon Sep 17 00:00:00 2001 +From: Min RK +Date: Fri, 31 May 2024 03:27:40 +0200 +Subject: [PATCH] Merge pull request from GHSA-hrw6-wg82-cm62 + +* filefind: avoid handling absolute paths + +we don't need or want absolute path support, +which we inherited from generic ipython_genutils + +only supporting relative paths lets us avoid attempting to accessing files we know we won't accept + +* Apply suggestions from code review + +Co-authored-by: M Bussonnier + +* filefind: only accept Sequence[str] + +we only call it one place, might as well be simple about it + +* version_info gate for is_relative_to + +* clarify docstring + +Co-authored-by: Carol Willing + +--------- + +Co-authored-by: M Bussonnier +Co-authored-by: Carol Willing +--- + jupyter_server/utils.py | 99 +++++++++++++++++------------------------ + tests/test_utils.py | 39 ++++++++++++++++ + 2 files changed, 81 insertions(+), 57 deletions(-) + +diff --git a/jupyter_server/utils.py b/jupyter_server/utils.py +index e9225b746..9a1bd89af 100644 +--- a/jupyter_server/utils.py ++++ b/jupyter_server/utils.py +@@ -11,6 +11,7 @@ import socket + import sys + import warnings + from contextlib import contextmanager ++from pathlib import Path + from typing import Any, Generator, NewType, Sequence + from urllib.parse import ( + SplitResult, +@@ -338,81 +339,65 @@ def is_namespace_package(namespace: str) -> bool | None: + return isinstance(spec.submodule_search_locations, _NamespacePath) + + +-def filefind(filename: str, path_dirs: Sequence[str] | str | None = None) -> str: ++def filefind(filename: str, path_dirs: Sequence[str]) -> str: + """Find a file by looking through a sequence of paths. +- This iterates through a sequence of paths looking for a file and returns +- the full, absolute path of the first occurrence of the file. If no set of +- path dirs is given, the filename is tested as is, after running through +- :func:`expandvars` and :func:`expanduser`. Thus a simple call:: + +- filefind("myfile.txt") ++ For use in FileFindHandler. + +- will find the file in the current working dir, but:: ++ Iterates through a sequence of paths looking for a file and returns ++ the full, absolute path of the first occurrence of the file. + +- filefind("~/myfile.txt") ++ Absolute paths are not accepted for inputs. + +- Will find the file in the users home directory. This function does not +- automatically try any paths, such as the cwd or the user's home directory. ++ This function does not automatically try any paths, ++ such as the cwd or the user's home directory. + + Parameters + ---------- + filename : str +- The filename to look for. +- path_dirs : str, None or sequence of str +- The sequence of paths to look for the file in. If None, the filename +- need to be absolute or be in the cwd. If a string, the string is +- put into a sequence and the searched. If a sequence, walk through +- each element and join with ``filename``, calling :func:`expandvars` +- and :func:`expanduser` before testing for existence. ++ The filename to look for. Must be a relative path. ++ path_dirs : sequence of str ++ The sequence of paths to look in for the file. ++ Walk through each element and join with ``filename``. ++ Only after ensuring the path resolves within the directory is it checked for existence. + + Returns + ------- +- Raises :exc:`IOError` or returns absolute path to file. ++ Raises :exc:`OSError` or returns absolute path to file. + """ +- +- # If paths are quoted, abspath gets confused, strip them... +- filename = filename.strip('"').strip("'") +- # If the input is an absolute path, just check it exists +- if os.path.isabs(filename) and os.path.isfile(filename): +- return filename +- +- if path_dirs is None: +- path_dirs = ("",) +- elif isinstance(path_dirs, str): +- path_dirs = (path_dirs,) +- +- for path in path_dirs: +- if path == ".": +- path = os.getcwd() # noqa: PLW2901 +- testname = expand_path(os.path.join(path, filename)) +- if os.path.isfile(testname): +- return os.path.abspath(testname) ++ file_path = Path(filename) ++ ++ # If the input is an absolute path, reject it ++ if file_path.is_absolute(): ++ msg = f"{filename} is absolute, filefind only accepts relative paths." ++ raise OSError(msg) ++ ++ for path_str in path_dirs: ++ path = Path(path_str).absolute() ++ test_path = path / file_path ++ # os.path.abspath resolves '..', but Path.absolute() doesn't ++ # Path.resolve() does, but traverses symlinks, which we don't want ++ test_path = Path(os.path.abspath(test_path)) ++ if sys.version_info >= (3, 9): ++ if not test_path.is_relative_to(path): ++ # points outside root, e.g. via `filename='../foo'` ++ continue ++ else: ++ # is_relative_to is new in 3.9 ++ try: ++ test_path.relative_to(path) ++ except ValueError: ++ # points outside root, e.g. via `filename='../foo'` ++ continue ++ # make sure we don't call is_file before we know it's a file within a prefix ++ # GHSA-hrw6-wg82-cm62 - can leak password hash on windows. ++ if test_path.is_file(): ++ return os.path.abspath(test_path) + + msg = f"File {filename!r} does not exist in any of the search paths: {path_dirs!r}" + raise OSError(msg) + + +-def expand_path(s: str) -> str: +- """Expand $VARS and ~names in a string, like a shell +- +- :Examples: +- In [2]: os.environ['FOO']='test' +- In [3]: expand_path('variable FOO is $FOO') +- Out[3]: 'variable FOO is test' +- """ +- # This is a pretty subtle hack. When expand user is given a UNC path +- # on Windows (\\server\share$\%username%), os.path.expandvars, removes +- # the $ to get (\\server\share\%username%). I think it considered $ +- # alone an empty var. But, we need the $ to remains there (it indicates +- # a hidden share). +- if os.name == "nt": +- s = s.replace("$\\", "IPYTHON_TEMP") +- s = os.path.expandvars(os.path.expanduser(s)) +- if os.name == "nt": +- s = s.replace("IPYTHON_TEMP", "$\\") +- return s +- +- + def import_item(name: str) -> Any: + """Import and return ``bar`` given the string ``foo.bar``. + Calling ``bar = import_item("foo.bar")`` is the functional equivalent of +diff --git a/tests/test_utils.py b/tests/test_utils.py +index 83d2a1d92..fdbfd6058 100644 +--- a/tests/test_utils.py ++++ b/tests/test_utils.py +@@ -13,6 +13,7 @@ from traitlets.tests.utils import check_help_all_output + from jupyter_server.utils import ( + check_pid, + check_version, ++ filefind, + is_namespace_package, + path2url, + run_sync_in_loop, +@@ -125,3 +126,41 @@ def test_unix_socket_in_use(tmp_path): + sock.listen(0) + assert unix_socket_in_use(server_address) + sock.close() ++ ++ ++@pytest.mark.parametrize( ++ "filename, result", ++ [ ++ ("/foo", OSError), ++ ("../c/in-c", OSError), ++ ("in-a", "a/in-a"), ++ ("in-b", "b/in-b"), ++ ("in-both", "a/in-both"), ++ (r"\in-a", OSError), ++ ("not-found", OSError), ++ ], ++) ++def test_filefind(tmp_path, filename, result): ++ a = tmp_path / "a" ++ a.mkdir() ++ b = tmp_path / "b" ++ b.mkdir() ++ c = tmp_path / "c" ++ c.mkdir() ++ for parent in (a, b): ++ with parent.joinpath("in-both").open("w"): ++ pass ++ with a.joinpath("in-a").open("w"): ++ pass ++ with b.joinpath("in-b").open("w"): ++ pass ++ with c.joinpath("in-c").open("w"): ++ pass ++ ++ if isinstance(result, str): ++ found = filefind(filename, [str(a), str(b)]) ++ found_relative = Path(found).relative_to(tmp_path) ++ assert str(found_relative) == result ++ else: ++ with pytest.raises(result): ++ filefind(filename, [str(a), str(b)]) +-- +2.42.0.windows.2 + diff --git a/jupyter_server-2.13.0.tar.gz b/jupyter_server-2.13.0.tar.gz new file mode 100644 index 0000000000000000000000000000000000000000..d7e412bf04fbb0b25a286f308526b45629bb48d5 --- /dev/null +++ b/jupyter_server-2.13.0.tar.gz @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:c80bfb049ea20053c3d9641c2add4848b38073bf79f1729cea1faed32fc1c78e +size 718244 diff --git a/python-jupyter-server.spec b/python-jupyter-server.spec new file mode 100644 index 0000000000000000000000000000000000000000..20d9db61dd21f05fb8907872571213643e8743ec --- /dev/null +++ b/python-jupyter-server.spec @@ -0,0 +1,67 @@ +Name: python-jupyter-server +Version: 2.13.0 +Release: 3 +Summary: The backend for Jupyter web applications + +License: BSD-3-Clause +URL: https://pypi.org/project/jupyter-server/#files +Source0: %{url}/archive/%{version}/jupyter_server-%{version}.tar.gz +Patch1: 0001-modify-the-version-limit-for-jupyter-core.patch +Patch3000: backport-CVE-2024-35178-GHSA-hrw6-wg82-cm62.patch +BuildArch: noarch + +%global _description %{expand: +The Jupyter Server provides the backend (i.e. the core services, +APIs, and REST endpoints) for Jupyter web applications like +Jupyter notebook, JupyterLab, and Voila.} + +%description %_description + +%package -n python3-jupyter-server + +Summary: %{summary} +BuildRequires: python3-devel +BuildRequires: python3-setuptools +BuildRequires: python3-setuptools_scm +BuildRequires: python3-pip +BuildRequires: python3-wheel +BuildRequires: python3-hatchling +BuildRequires: python3-hatch-jupyter-builder + +%description -n python3-jupyter-server %_description + +%prep +%autosetup -p1 -n jupyter_server-%{version} + +%build +%pyproject_build + +%install +%pyproject_install + +%files -n python3-jupyter-server +%license LICENSE +%doc README.md +%{_bindir}/jupyter-server +%{python3_sitelib}/jupyter_server-*.dist-info/ +%{python3_sitelib}/jupyter_server/ + +%changelog +* Fri Oct 25 2024 zhouyi - 2.13.0-3 +- add lfs server config + +* Fri Oct 25 2024 liningjie - 2.13.0-2 +- Fix CVE-2024-35178 + +* Wed Mar 6 2024 Dongxing Wang - 2.13.0-1 +- Update package with version 2.13.0 + Add an option to have authentication enabled for all endpoints by default + Websockets: add configurations for ping interval and timeout + Log extension import time at debug level unless it's actually slow + Add support for async Authorizers + Support get file(notebook) md5 + Update kernel env to reflect changes in session + Support external kernels + +* Mon Jul 31 2023 mengzhaoa - 2.7.0-1 +- Init package python3-jupyter-server of version 2.7.0