diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index d47a5407..650a42c1 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -46,11 +46,24 @@ jobs: # Test each backend that requires a python client against a modern # version of python to ensure clients are compatible. + # + # - About redis versions: + # redis can be installed from source, as an ubuntu distribution, or + # snap package. To avoid complexity we don't build from source, but we + # test against the ubuntu and snap package, where the ubuntu package + # typically is behind the snap package. + # + # redis-test-version is provided as a matrix input only to provide + # visibility via github's web UI. + # - python: "3.12" backend: redis - # redis-test-version is tied to ubuntu's package, so we only test - # redis 6 currently while redis 7 is out, see - # https://packages.ubuntu.com/jammy/redis-server + install-via: apt # version 6.0.16 in ubuntu 22.04, https://packages.ubuntu.com/jammy/redis-server + redis-test-version: "6.0.16?" + - python: "3.12" + backend: redis + install-via: snap # version 7.2.4 or higher, https://snapcraft.io/redis + redis-test-version: ">=7.2.4" - python: "3.12" backend: etcd etcd-test-version: "v3.4.29" # https://github.com/etcd-io/etcd/releases @@ -103,10 +116,18 @@ jobs: etcdctl version - - name: Install redis + - name: Install redis via ${{ matrix.install-via }} if: matrix.backend == 'redis' run: | - sudo apt-get -y install redis-server + if [[ "${{ matrix.install-via }}" == "apt" ]]; then + sudo apt-get -y install redis-server + + redis-server --version + else + sudo snap install redis + + redis.sentinel --version + fi - name: Run tests run: | diff --git a/docs/source/install.md b/docs/source/install.md index 8d97ba3b..08c08f3b 100644 --- a/docs/source/install.md +++ b/docs/source/install.md @@ -63,7 +63,7 @@ If you want to use a key-value store to mediate configuration (mainly for use in distributed deployments, such as containers), you can get the key-value stores via their respective installation pages: -- Install [`redis-server`](https://redis.io/docs/install/install-redis/) +- Install [`redis`](https://redis.io/docs/install/install-redis/) - Install [`etcd`](https://github.com/etcd-io/etcd/releases) diff --git a/docs/source/redis.md b/docs/source/redis.md index 0d06921b..ca66bfd6 100644 --- a/docs/source/redis.md +++ b/docs/source/redis.md @@ -189,7 +189,12 @@ This is an example setup for using JupyterHub and TraefikRedisProxy managed by a 2. Start a single-node Redis cluster on the default port on localhost. e.g.: ```bash - $ redis-server + # for redis installed via apt + redis-server + + # for redis installed via snap + touch /tmp/redis.conf + redis.sentinel /tmp/redis.conf ``` 3. Create a traefik static configuration file, _traefik.toml_, e.g:. diff --git a/performance/perf_utils.py b/performance/perf_utils.py index 393d107e..ab5ac687 100644 --- a/performance/perf_utils.py +++ b/performance/perf_utils.py @@ -1,6 +1,7 @@ import argparse import asyncio import logging +import shutil import sys import textwrap import time @@ -9,7 +10,7 @@ from multiprocessing import cpu_count from pathlib import Path from subprocess import Popen -from tempfile import TemporaryDirectory +from tempfile import NamedTemporaryFile, TemporaryDirectory import aiohttp import numpy as np @@ -176,8 +177,18 @@ def redis(): """Context manager for running redis-server""" from redis import Redis - with TemporaryDirectory() as td: - p = Popen(['redis-server'], cwd=td) + with TemporaryDirectory() as td, NamedTemporaryFile as config_file: + if shutil.which("redis-server"): + # redis-server is available when installed via an apt package + redis_server_command = ['redis-server'] + elif shutil.which("redis.sentinel"): + # redis.sentinel is available when installed via an snap package + # here we need to provide a config file explicitly + redis_server_command = ['redis.sentinel', config_file.name] + else: + raise ValueError("redis-server or redis.sentinel binaries not on path") + + p = Popen(redis_server_command, cwd=td) for i in range(5): try: r = Redis() diff --git a/tests/conftest.py b/tests/conftest.py index 6c59c0d6..ded3aa84 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -9,7 +9,7 @@ import subprocess import sys from pathlib import Path -from tempfile import TemporaryDirectory +from tempfile import NamedTemporaryFile, TemporaryDirectory from urllib.parse import urlparse import pytest @@ -770,11 +770,21 @@ async def _check_consul(): @pytest.fixture(scope="module") def launch_redis(): - with TemporaryDirectory() as path: + with TemporaryDirectory() as path, NamedTemporaryFile as config_file: + if shutil.which("redis-server"): + # redis-server is available when installed via an apt package + redis_server_command = ['redis-server'] + elif shutil.which("redis.sentinel"): + # redis.sentinel is available when installed via an snap package + # here we need to provide a config file explicitly + redis_server_command = ['redis.sentinel', config_file.name] + else: + raise ValueError("redis-server or redis.sentinel binaries not on path") + print(f"Launching redis in {path}") redis_proc = subprocess.Popen( - [ - "redis-server", + redis_server_command + + [ "--port", str(Config.redis_port), "--",