Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
42 commits
Select commit Hold shift + click to select a range
3580668
chore(python): upgrade python version to 3.12, update deps, fix tests…
vtaskow Nov 17, 2025
a3d792d
chore(wrappers): Use Python 3.12 and move to Miniforge Conda in Docke…
vtaskow Nov 17, 2025
adf8fea
Miniforge 24.3.0-0 with Python 3.10.14 + install of Python 3.10.18 in…
vtaskow Oct 10, 2025
f41930d
Remove install of latest 3.10.X python inside the conda dockerfile
vtaskow Oct 10, 2025
75e5236
Reduce image size to 366 MB
vtaskow Oct 10, 2025
214431b
Python - 3.10, updated licences, deps, fmt, tests all good. Wrappers …
vtaskow Oct 23, 2025
abb209d
Working version for Python 3.12
vtaskow Oct 23, 2025
bbb294f
Update dev-reqs in testing/scripts; alibi requires numpy < 2.0.0 so f…
vtaskow Oct 23, 2025
8c4e3a1
Updated versions of numpy, protobuf and similar allow for tests insid…
vtaskow Oct 29, 2025
1522410
Fix `get_local_repo` to make it work on macOS
tyndria Oct 30, 2025
7a896e6
Update python and lock
tyndria Oct 30, 2025
0fec978
Update numpy to "1.26.4"
tyndria Oct 30, 2025
e859069
remove `extras=["all"]` from alibi-detect dependency definition and p…
tyndria Oct 30, 2025
7ed954f
Fix build seldonio/conda-ubi9 image
tyndria Oct 30, 2025
e6fd2bf
Upgrade pip-licenses = "5.5.0"
tyndria Oct 30, 2025
07af8ab
Fix building `alibi-detect-server` image
tyndria Oct 30, 2025
1a6df75
Fix invoking `make test`
tyndria Oct 30, 2025
e2c7ffd
Upgrade tensorflow to fix some tests
tyndria Oct 30, 2025
230e689
skip if rclone is unavailable
tyndria Oct 30, 2025
3bd3c0f
Updated poetry.lock
tyndria Oct 30, 2025
e8d091b
Update GH action for alibi detect tests
tyndria Oct 30, 2025
d1a5bf7
Minor packages upgrades
tyndria Nov 5, 2025
9919062
Fix minor image warnings
tyndria Nov 5, 2025
8bb442a
Remove fix for the solved `pystan` issue
tyndria Nov 6, 2025
2fba5b3
Added missing "tensorflow-probability" and "tf-keras" dependencies to…
tyndria Nov 6, 2025
65f8db9
Upgrade rclone to v1.71.2 to fix CVEs
tyndria Nov 6, 2025
813f61e
alibi-explain-server component compatibility with python 3.12: tests …
vtaskow Nov 5, 2025
a646e1c
alibi-explain-server: fix mypy and run make fmt and make lint
vtaskow Nov 6, 2025
4df935c
wrappers:s2i:python - fix several vulnerabilities in Dockerfile.conda…
vtaskow Nov 6, 2025
6dcf96d
wrappers:s2i:python - replace the ensurepip package in conda env with…
vtaskow Nov 7, 2025
3123263
alibi-explain-server - install poetry with conda pip, replace pip wit…
vtaskow Nov 7, 2025
8cf40fa
Fix poetry installation after conda base image is changed; Introduced…
tyndria Nov 7, 2025
0c17444
Fix alibidetect_tests workflow
tyndria Nov 7, 2025
afc2008
Try to run workflow in a fork (expect to be failing)
tyndria Nov 7, 2025
ba7cb78
Upgrade `black` to fix lint job
tyndria Nov 7, 2025
c6d80b3
Change base image tag for the mlflowserver
tyndria Nov 10, 2025
ecc4ab7
Use seldon-core-s2i-python312 for mean_classifier image
tyndria Nov 10, 2025
e2a1452
Use seldon-core-s2i-python312 as base image for examples/models/testing
tyndria Nov 10, 2025
025f37d
Use seldon-core-s2i-python312 for the fixed model
tyndria Nov 10, 2025
cce0e91
Use seldonio/seldon-core-s2i-python312 for echo-model
tyndria Nov 10, 2025
29eb608
Upgrade tensorflow from 2.17.1 to 2.18.1 because of upgrade of protob…
vtaskow Nov 10, 2025
28d48e9
upgrade protobuf, tf, tf-keras, grpcio-tools
tyndria Nov 12, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 15 additions & 16 deletions .github/workflows/alibidetect_tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,28 +2,27 @@ name: V1 Alibi Detect Tests

on:
push:
branches: [ master ]
branches: "*" # TODO: return [master]
pull_request:
# TODO revert before merge to master
branches: [ fix/core-1-CVEs ]
branches: "*" # TODO: return [master]

jobs:
lint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Set up Python 3.8
- uses: actions/checkout@v4
- name: Set up Python 3.12
uses: actions/setup-python@v4
with:
python-version: 3.8
python-version: '3.12'
- name: Install Poetry
uses: snok/install-poetry@v1
with:
version: 1.1.15
version: 2.1.2
virtualenvs-create: false
- name: Install dependencies
run: |
pip install --upgrade pip setuptools
python -m pip install --upgrade pip setuptools
make -C components/alibi-detect-server dev_install
- name: Lint
run: |
Expand All @@ -32,24 +31,24 @@ jobs:
python-tests:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v4
- name: Install Rclone
run: |
wget https://downloads.rclone.org/v1.62.2/rclone-v1.62.2-linux-amd64.zip
unzip rclone-v1.62.2-linux-amd64.zip
mv rclone-v1.62.2-linux-amd64/rclone /usr/local/bin/rclone
- name: Set up Python 3.8
wget https://downloads.rclone.org/v1.71.2/rclone-v1.71.2-linux-amd64.zip
unzip rclone-v1.71.2-linux-amd64.zip
mv rclone-v1.71.2-linux-amd64/rclone /usr/local/bin/rclone
- name: Set up Python 3.12
uses: actions/setup-python@v4
with:
version: 1.1.15
python-version: 3.8
python-version: '3.12'
- name: Install Poetry
uses: snok/install-poetry@v1
with:
version: 2.1.2
virtualenvs-create: false
- name: Install dependencies
run: |
pip install --upgrade pip setuptools
python -m pip install --upgrade pip setuptools
make -C components/alibi-detect-server dev_install
- name: Test
run: |
Expand Down
1 change: 1 addition & 0 deletions components/alibi-detect-server/.dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
_seldon_core/.tox
1 change: 1 addition & 0 deletions components/alibi-detect-server/.tool-versions
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
poetry 1.8.0
70 changes: 34 additions & 36 deletions components/alibi-detect-server/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,63 +1,58 @@
ARG VERSION
ARG BASE_IMAGE
FROM ${BASE_IMAGE}:${VERSION} as base
FROM ${BASE_IMAGE}:${VERSION} AS base

ARG VERSION
LABEL name="Seldon Alibi Detect Server" \
vendor="Seldon Technologies" \
version="1.19.0-dev" \
release="1" \
summary="Alibi Detect Server for Seldon Core" \
description="The Alibi Detect Server provides outlier, drift and adversarial detection services for Seldon Core"
vendor="Seldon Technologies" \
version="1.19.0-dev" \
release="1" \
summary="Alibi Detect Server for Seldon Core" \
description="The Alibi Detect Server provides outlier, drift and adversarial detection services for Seldon Core"

FROM base as builder
FROM base AS builder

USER root

RUN microdnf update -y && \
microdnf install -y \
unzip \
make \
automake \
gcc \
gcc-c++
unzip \
make \
automake \
gcc \
gcc-c++

# Install Rclone Binary to be present in the image
RUN wget https://downloads.rclone.org/v1.64.2/rclone-v1.64.2-linux-amd64.zip && \
unzip rclone-v1.64.2-linux-amd64.zip && \
mv rclone-v1.64.2-linux-amd64/rclone /usr/bin/rclone && \
rm -rf rclone-v1.64.2-linux-amd64.zip rclone-v1.64.2-linux-amd64

# Note that we need to force Conda to use the system's std-c++ library, as
# otherwise PyStan won't compile with Conda's older stdc++ library:
# https://github.com/stan-dev/pystan/issues/294#issuecomment-870711100
RUN pip install --upgrade pip setuptools wheel && \
cd /opt/conda/lib && \
rm libstdc++.so libstdc++.so.6 && \
ln -s /usr/lib64/libstdc++.so.6.0.29 libstdc++.so && \
ln -s /usr/lib64/libstdc++.so.6.0.29 libstdc++.so.6
RUN wget https://downloads.rclone.org/v1.71.2/rclone-v1.71.2-linux-amd64.zip && \
unzip rclone-v1.71.2-linux-amd64.zip && \
mv rclone-v1.71.2-linux-amd64/rclone /usr/bin/rclone && \
rm -rf rclone-v1.71.2-linux-amd64.zip rclone-v1.71.2-linux-amd64

# Make home dir
RUN mkdir microservice
WORKDIR /microservice

# Install Poetry
ENV POETRY_HOME /microservice/.poetry
RUN curl -sSL https://install.python-poetry.org | python3 - --version 1.1.15
ENV POETRY_HOME=/microservice/.poetry
RUN /opt/conda/bin/pip install --no-cache-dir "poetry==2.1.2"

ENV PATH "$POETRY_HOME/bin:$PATH"
ENV POETRY_VIRTUALENVS_CREATE false
# Replace vulnerable pip wheel embedded inside virtualenv(CVE-2025-8869)
RUN find /opt/conda/lib/python3.12/site-packages/virtualenv/seed/wheels/embed/ -name "pip-*.whl" -delete && \
/opt/conda/bin/pip wheel pip==25.3.0 --wheel-dir /opt/conda/lib/python3.12/site-packages/virtualenv/seed/wheels/embed/

ENV PATH="$POETRY_HOME/bin:$PATH"
ENV POETRY_VIRTUALENVS_CREATE=false

# Install the server
## NOTE: Removing explicitly requirements.txt file from subdeps test
## dependencies causing false positives in Snyk.
COPY poetry.lock pyproject.toml ./
COPY _seldon_core ./_seldon_core
RUN poetry install --no-dev && \
RUN poetry install --no-root && \
rm ~/.cache/pip -rf && \
rm -f /opt/conda/lib/python3.8/site-packages/gslib/vendored/boto/requirements.txt \
/opt/conda/lib/python3.8/site-packages/gslib/vendored/oauth2client/docs/requirements.txt \
/opt/conda/lib/python3.8/site-packages/tests/conda_env/support/requirements.txt
rm -f /opt/conda/lib/python3.12/site-packages/gslib/vendored/boto/requirements.txt \
/opt/conda/lib/python3.12/site-packages/gslib/vendored/oauth2client/docs/requirements.txt \
/opt/conda/lib/python3.12/site-packages/tests/conda_env/support/requirements.txt

# Add licences
RUN mkdir /licenses
Expand All @@ -70,7 +65,10 @@ COPY adserver adserver
COPY README.md README.md
COPY version.txt version.txt

FROM base as final
# Install the project code
RUN poetry install

FROM base AS final
WORKDIR /microservice

USER root
Expand All @@ -89,8 +87,8 @@ COPY --from=builder /usr/bin/rclone /usr/bin/rclone
COPY --from=builder /licenses /licenses

# This is to have writable numba and keops cache directories
ENV NUMBA_CACHE_DIR /tmp/numba-cache
RUN mkdir -p /.cache && \
ENV NUMBA_CACHE_DIR=/tmp/numba-cache
RUN mkdir /.cache && \
chown -R 8888:0 /.cache && \
chmod -R 776 /.cache

Expand Down
10 changes: 5 additions & 5 deletions components/alibi-detect-server/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ SHELL := /bin/bash
VERSION ?= $(shell cat ../../version.txt)
DOCKER_REGISTRY ?= seldonio

BASE_IMAGE ?= ${DOCKER_REGISTRY}/conda-ubi8
BASE_IMAGE ?= ${DOCKER_REGISTRY}/conda-ubi9
IMAGE ?= ${DOCKER_REGISTRY}/alibi-detect-server
KIND_NAME ?= kind

Expand All @@ -12,7 +12,7 @@ SELDON_CORE_DIR=../..

get_local_repo: clean
cp $(SELDON_CORE_DIR)/version.txt version.txt
cp -rT $(SELDON_CORE_DIR)/python/ _seldon_core/
cp -R "$(SELDON_CORE_DIR)/python/." _seldon_core/

clean:
rm version.txt || true
Expand All @@ -27,8 +27,8 @@ type_check:
mypy --ignore-missing-imports adserver

.PHONY: test
test: type_check
pytest -W ignore adserver
test:
poetry run pytest -W ignore adserver

.PHONY: lint
lint:
Expand Down Expand Up @@ -99,7 +99,7 @@ curl-metrics-server-metrics:
# image building logic

docker-build: get_local_repo
docker build -f Dockerfile --build-arg BASE_IMAGE=${BASE_IMAGE} --build-arg VERSION=${VERSION} -t ${IMAGE}:${VERSION} .
docker build --platform linux/amd64 -f Dockerfile --build-arg BASE_IMAGE=${BASE_IMAGE} --build-arg VERSION=${VERSION} -t ${IMAGE}:${VERSION} .

docker-build-gpu:
docker build -f Dockerfile.gpu -t ${IMAGE}-gpu:${VERSION} .
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ def test_basic(self):
req = [1, 2]
headers = {}
res = ad_model.process_event(req, headers)
self.assert_(res is not None)
self.assertIsNotNone(res)
self.assertEqual(res.data["data"]["is_adversarial"], 1)

def test_no_return_instance_score(self):
Expand All @@ -55,5 +55,5 @@ def test_no_return_instance_score(self):
req = [1, 2]
headers = {HEADER_RETURN_INSTANCE_SCORE: "false"}
res = ad_model.process_event(req, headers)
self.assert_(res is not None)
self.assertIsNotNone(res)
self.assertEqual(res.data["data"]["is_adversarial"], expected_is_adversarial)
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
from alibi_detect.base import BaseDetector, concept_drift_dict
import numpy as np
from unittest import TestCase
from unittest import TestCase, skipUnless
from adserver.cd_model import AlibiDetectConceptDriftModel
from typing import Dict
from adserver.base.storage import rclone


class DummyCDModel(BaseDetector):
Expand Down Expand Up @@ -55,6 +56,7 @@ def test_batch(self):
self.assertEqual(res, None)


@skipUnless(rclone is not None, "rclone binary not available")
class TestTextDriftModel(TestCase):
def test_basic(self):
model = DummyCDModel()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ def test_basic(self):
req = [1, 2]
headers = {}
res: ModelResponse = od_model.process_event(req, headers)
self.assert_(res is not None)
self.assertIsNotNone(res)
self.assertEqual(res.data["data"]["is_outlier"], 0)

def test_no_return_instance_score(self):
Expand All @@ -58,5 +58,5 @@ def test_no_return_instance_score(self):
req = [1, 2]
headers = {HEADER_RETURN_INSTANCE_SCORE: "false"}
res: ModelResponse = ad_model.process_event(req, headers)
self.assert_(res is not None)
self.assertIsNotNone(res)
self.assertEqual(res.data["data"]["is_outlier"], expect_return_is_outlier)
Loading