From c82bd9078f39c19de1f856f958cf6af6df10fa58 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Thu, 11 May 2023 15:56:17 +0100 Subject: [PATCH 01/14] Create publish_map.yml --- .github/workflows/publish_map.yml | 43 +++++++++++++++++++++++++++++++ 1 file changed, 43 insertions(+) create mode 100644 .github/workflows/publish_map.yml diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml new file mode 100644 index 0000000..00e2acc --- /dev/null +++ b/.github/workflows/publish_map.yml @@ -0,0 +1,43 @@ +# Workflow to publish TotalSegmentator-AIDE MAP on GHCR + +name: Create and publish MAP + +on: + push: + branches: ['24_publish_map'] + +env: + REGISTRY: ghcr.io + IMAGE_NAME: ${{ github.repository }} + +jobs: + build-and-push-image: + runs-on: ubuntu-latest + permissions: + contents: read + packages: write + + steps: + - name: Checkout repository + uses: actions/checkout@v3 + + - name: Log in to the Container registry + uses: docker/login-action@65b78e6e13532edd9afa3aa52ac7964289d1a9c1 + with: + registry: ${{ env.REGISTRY }} + username: ${{ github.actor }} + password: ${{ secrets.GITHUB_TOKEN }} + + - name: Extract metadata (tags, labels) for Docker + id: meta + uses: docker/metadata-action@9ec57ed1fcdbf14dcef7dfbe97b2010124a938b7 + with: + images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }} + + - name: Build and push Docker image + uses: docker/build-push-action@f2a1d5e99d037542a71f64918e516c093c6f3fc4 + with: + context: . + push: true + tags: ${{ steps.meta.outputs.tags }} + labels: ${{ steps.meta.outputs.labels }} \ No newline at end of file From 3a86f16a409daae4b49d5d401c3012ec65f08a23 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Thu, 11 May 2023 16:43:02 +0100 Subject: [PATCH 02/14] Change to build and package MAP using command line --- .github/workflows/publish_map.yml | 76 +++++++++++++++++-------------- 1 file changed, 43 insertions(+), 33 deletions(-) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index 00e2acc..951aae7 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -1,43 +1,53 @@ # Workflow to publish TotalSegmentator-AIDE MAP on GHCR -name: Create and publish MAP +name: Build and package MAP on: push: branches: ['24_publish_map'] -env: - REGISTRY: ghcr.io - IMAGE_NAME: ${{ github.repository }} - jobs: - build-and-push-image: - runs-on: ubuntu-latest - permissions: - contents: read - packages: write + build: + + runs-on: ${{ matrix.os }} + + strategy: + fail-fast: false + matrix: + os: [ ubuntu-latest ] + python-version: [ '3.10' ] + + defaults: + run: + shell: bash -l {0} steps: - - name: Checkout repository - uses: actions/checkout@v3 - - - name: Log in to the Container registry - uses: docker/login-action@65b78e6e13532edd9afa3aa52ac7964289d1a9c1 - with: - registry: ${{ env.REGISTRY }} - username: ${{ github.actor }} - password: ${{ secrets.GITHUB_TOKEN }} - - - name: Extract metadata (tags, labels) for Docker - id: meta - uses: docker/metadata-action@9ec57ed1fcdbf14dcef7dfbe97b2010124a938b7 - with: - images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }} - - - name: Build and push Docker image - uses: docker/build-push-action@f2a1d5e99d037542a71f64918e516c093c6f3fc4 - with: - context: . - push: true - tags: ${{ steps.meta.outputs.tags }} - labels: ${{ steps.meta.outputs.labels }} \ No newline at end of file + - uses: actions/checkout@v3 + + - name: Set up Python + uses: actions/setup-python@v4 + with: + python-version: ${{ matrix.python-version }} + + - name: Install Python packages + run: | + python -m pip install --upgrade pip + pip install flake8 pytest pytest-cov + if [ -f requirements.txt ]; then pip install -r requirements.txt; fi + + - name: Display installed pip packages + run: | + pip list + + - name: Initial packaging of MAP-init + run: | + monai-deploy package app --tag map-init -l DEBUG + + - name: Package 3rd-party software into MAP + run: | + docker build -t map app/ + +# # TODO: add step to run the MAP using test data +# - name: Test MAP end-to-end +# run: | +# monai-deploy run map input-test-data-in-repo/ output/ \ No newline at end of file From b214bc45e8d667d8b70e7852850bfdb2dc8a113c Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 12 May 2023 13:50:46 +0100 Subject: [PATCH 03/14] Updates GitHub Action to use map-init in build process / adds output file check --- .github/workflows/publish_map.yml | 14 +++++++++----- app/Dockerfile | 4 +++- tests/data/output/.gitkeep | 0 3 files changed, 12 insertions(+), 6 deletions(-) create mode 100644 tests/data/output/.gitkeep diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index 951aae7..cc26c84 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -45,9 +45,13 @@ jobs: - name: Package 3rd-party software into MAP run: | - docker build -t map app/ + docker build --build-arg INIT_CONTAINER=map-init -t map app -# # TODO: add step to run the MAP using test data -# - name: Test MAP end-to-end -# run: | -# monai-deploy run map input-test-data-in-repo/ output/ \ No newline at end of file + - name: Test MAP end-to-end + run: | + monai-deploy run map tests/data/rtstructwriter/dcm tests/data/output + + - name: Confirm output generated + run: | + ls tests/data/output + if test -f "tests/data/output/output-rt-struct.dcm"; then echo "Output RT Struct exists."; fi \ No newline at end of file diff --git a/app/Dockerfile b/app/Dockerfile index 1a270e4..71a7b71 100644 --- a/app/Dockerfile +++ b/app/Dockerfile @@ -1,5 +1,7 @@ +ARG INIT_CONTAINER + # Use initial MAP for build -FROM ghcr.io/gstt-csc/totalsegmentator-aide/map-init:0.1.2 AS build +FROM $INIT_CONTAINER AS build # Add dcm2niix to MAP WORKDIR /bin diff --git a/tests/data/output/.gitkeep b/tests/data/output/.gitkeep new file mode 100644 index 0000000..e69de29 From 8ff68eb2122e547d3ed3a38aa76c3a2b9a2156b1 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 12 May 2023 14:51:04 +0100 Subject: [PATCH 04/14] Test GitHub Action with updated Docker image name --- .github/workflows/publish_map.yml | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index cc26c84..cad78a5 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -41,11 +41,15 @@ jobs: - name: Initial packaging of MAP-init run: | - monai-deploy package app --tag map-init -l DEBUG + monai-deploy package app --tag map/init:temp -l DEBUG - name: Package 3rd-party software into MAP run: | - docker build --build-arg INIT_CONTAINER=map-init -t map app + docker build --build-arg INIT_CONTAINER=map-init -t map/final:temp app + + - name: Show Docker images + run: | + docker images - name: Test MAP end-to-end run: | From d4f53fc616bc819a67a117a34dbb22370e2408cd Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 12 May 2023 15:21:52 +0100 Subject: [PATCH 05/14] =?UTF-8?q?Typo=20=E2=80=93=20re-test=20GHA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .github/workflows/publish_map.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index cad78a5..d2ab8e9 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -45,7 +45,7 @@ jobs: - name: Package 3rd-party software into MAP run: | - docker build --build-arg INIT_CONTAINER=map-init -t map/final:temp app + docker build --build-arg INIT_CONTAINER=map/init:temp -t map/final:temp app - name: Show Docker images run: | From 963706fc636a88c2a820195bbf78ca9d84047dc8 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Tue, 30 May 2023 11:56:15 +0100 Subject: [PATCH 06/14] WIP: test publish_map.yml using one step for all MAP commands --- .github/workflows/publish_map.yml | 15 ++------------- 1 file changed, 2 insertions(+), 13 deletions(-) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index d2ab8e9..e836b5d 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -39,23 +39,12 @@ jobs: run: | pip list - - name: Initial packaging of MAP-init + - name: Package MAP & test MAP end-to-end run: | monai-deploy package app --tag map/init:temp -l DEBUG - - - name: Package 3rd-party software into MAP - run: | + docker images docker build --build-arg INIT_CONTAINER=map/init:temp -t map/final:temp app - - - name: Show Docker images - run: | docker images - - - name: Test MAP end-to-end - run: | monai-deploy run map tests/data/rtstructwriter/dcm tests/data/output - - - name: Confirm output generated - run: | ls tests/data/output if test -f "tests/data/output/output-rt-struct.dcm"; then echo "Output RT Struct exists."; fi \ No newline at end of file From 1f201dc92bd281be6a5eb66e85039f1647ed4f08 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Wed, 5 Jul 2023 14:16:14 +0100 Subject: [PATCH 07/14] Test GHA with 22.08 Nvidia PyTorch base image --- .github/workflows/publish_map.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index e836b5d..faed7e3 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -41,7 +41,7 @@ jobs: - name: Package MAP & test MAP end-to-end run: | - monai-deploy package app --tag map/init:temp -l DEBUG + monai-deploy package app --base nvcr.io/nvidia/pytorch:22.08-py3 --tag map/init:temp -l DEBUG docker images docker build --build-arg INIT_CONTAINER=map/init:temp -t map/final:temp app docker images From 6f35dd89ddfe46433fbf3802ee568f5cb2ac33c6 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Wed, 5 Jul 2023 16:07:06 +0100 Subject: [PATCH 08/14] Test monai-deploy package with custom -r flag Use requirements-map-init.txt to force Python package versions compatible with scipy==1.6.3 which is default version in Nvidia PyTorch containers. Alternatively, could use -r flag to install newer version of scipy. --- .github/workflows/publish_map.yml | 2 +- requirements-map-init.txt | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) create mode 100644 requirements-map-init.txt diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index faed7e3..bb14d99 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -41,7 +41,7 @@ jobs: - name: Package MAP & test MAP end-to-end run: | - monai-deploy package app --base nvcr.io/nvidia/pytorch:22.08-py3 --tag map/init:temp -l DEBUG + monai-deploy package app --base nvcr.io/nvidia/pytorch:22.08-py3 -r requirements-map-init.txt --tag map/init:temp -l DEBUG docker images docker build --build-arg INIT_CONTAINER=map/init:temp -t map/final:temp app docker images diff --git a/requirements-map-init.txt b/requirements-map-init.txt new file mode 100644 index 0000000..50ad4e7 --- /dev/null +++ b/requirements-map-init.txt @@ -0,0 +1,2 @@ +numpy<1.21.0 +protobuf<3.20 \ No newline at end of file From 6aa53aad2b85056d740accdab2e9b493996ed0ea Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 7 Jul 2023 11:08:02 +0100 Subject: [PATCH 09/14] Test GHA: adds in free disk space step --- .github/workflows/publish_map.yml | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index bb14d99..e6e5f60 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -39,6 +39,15 @@ jobs: run: | pip list + - name: Free disk space + run: | + df -h + sudo swapoff -a + sudo rm -rf /swapfile /usr/share/dotnet /usr/local/lib/android /opt/ghc + sudo apt clean + docker rmi $(docker image ls -aq) + df -h + - name: Package MAP & test MAP end-to-end run: | monai-deploy package app --base nvcr.io/nvidia/pytorch:22.08-py3 -r requirements-map-init.txt --tag map/init:temp -l DEBUG From fc91ab30a604229a0f01682eae04e8a4783ed68d Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 7 Jul 2023 11:53:09 +0100 Subject: [PATCH 10/14] Test GHA: adds --working-dir option and remove slashes from image names --- .github/workflows/publish_map.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index e6e5f60..2a91710 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -50,9 +50,9 @@ jobs: - name: Package MAP & test MAP end-to-end run: | - monai-deploy package app --base nvcr.io/nvidia/pytorch:22.08-py3 -r requirements-map-init.txt --tag map/init:temp -l DEBUG + monai-deploy package app --base nvcr.io/nvidia/pytorch:22.08-py3 -r requirements-map-init.txt --working-dir app --tag map-init:temp -l DEBUG docker images - docker build --build-arg INIT_CONTAINER=map/init:temp -t map/final:temp app + docker build --build-arg INIT_CONTAINER=map-init:temp -t map-final:temp app docker images monai-deploy run map tests/data/rtstructwriter/dcm tests/data/output ls tests/data/output From bae5cc797951861d45a82aaff9bb8f81027bcad4 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 7 Jul 2023 12:59:13 +0100 Subject: [PATCH 11/14] Test GHA: specify requirements.txt via md decorator --- .github/workflows/publish_map.yml | 2 +- app/app.py | 6 ++++++ 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index 2a91710..9a44e78 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -50,7 +50,7 @@ jobs: - name: Package MAP & test MAP end-to-end run: | - monai-deploy package app --base nvcr.io/nvidia/pytorch:22.08-py3 -r requirements-map-init.txt --working-dir app --tag map-init:temp -l DEBUG + monai-deploy package app --base nvcr.io/nvidia/pytorch:22.08-py3 --tag map-init:temp -l DEBUG docker images docker build --build-arg INIT_CONTAINER=map-init:temp -t map-final:temp app docker images diff --git a/app/app.py b/app/app.py index be6f9cf..26662fc 100644 --- a/app/app.py +++ b/app/app.py @@ -9,15 +9,21 @@ # Tom Roberts (tom.roberts@gstt.nhs.uk / t.roberts@kcl.ac.uk) import logging +from pathlib import Path +import monai.deploy.core as md from monai.deploy.core import Application, resource from operators.dcm2nii_operator import Dcm2NiiOperator from operators.rtstructwriter_operator import RTStructWriterOperator from operators.totalsegmentator_operator import TotalSegmentatorOperator +requirements_file = ( + Path(__file__).resolve().parent / ".." / "requirements.txt" +) @resource(cpu=1, gpu=1, memory="32Gi") +@md.env(pip_packages=requirements_file.as_posix()) class TotalSegmentatorApp(Application): """ TotalSegmentator - segmentation of 104 anatomical structures in CT images. From 98b7c07f80c795e86be2162c0f38777c6aaf82c4 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 7 Jul 2023 13:28:05 +0100 Subject: [PATCH 12/14] Test GHA: create app_requirements.txt within app/ dir --- app/app.py | 2 +- app/app_requirements.txt | 68 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 69 insertions(+), 1 deletion(-) create mode 100644 app/app_requirements.txt diff --git a/app/app.py b/app/app.py index 26662fc..14f0055 100644 --- a/app/app.py +++ b/app/app.py @@ -19,7 +19,7 @@ from operators.totalsegmentator_operator import TotalSegmentatorOperator requirements_file = ( - Path(__file__).resolve().parent / ".." / "requirements.txt" + Path(__file__).resolve().parent / "app_requirements.txt" ) @resource(cpu=1, gpu=1, memory="32Gi") diff --git a/app/app_requirements.txt b/app/app_requirements.txt new file mode 100644 index 0000000..1ac94ed --- /dev/null +++ b/app/app_requirements.txt @@ -0,0 +1,68 @@ +aiohttp==3.8.3 +aiosignal==1.3.1 +async-timeout==4.0.2 +attrs==22.2.0 +batchgenerators==0.21 +certifi==2022.12.7 +charset-normalizer==2.1.1 +colorama==0.4.6 +contourpy==1.0.6 +cycler==0.11.0 +dataclasses==0.6 +dicom2nifti==2.4.7 +dill==0.3.6 +fonttools==4.38.0 +frozenlist==1.3.3 +fury==0.8.0 +future==0.18.3 +idna==3.4 +imageio==2.23.0 +joblib==1.2.0 +kiwisolver==1.4.4 +linecache2==1.0.0 +matplotlib==3.6.2 +MedPy==0.4.0 +monai-deploy-app-sdk==0.5.0 +multidict==6.0.4 +multiprocess==0.70.14 +networkx==2.8.8 +nibabel==4.0.2 +nnunet-customized==1.2 +numpy==1.24.1 +opencv-python==4.7.0.68 +p-tqdm==1.4.0 +packaging==22.0 +pandas==1.5.2 +pathos==0.3.0 +Pillow==9.3.0 +pox==0.3.2 +ppft==1.7.6.6 +psutil==5.9.4 +pydicom==2.3.1 +pytest==7.2.1 +pyparsing==3.0.9 +python-dateutil==2.8.2 +python-gdcm==3.0.20 +pytz==2022.7 +PyWavelets==1.4.1 +requests==2.28.1 +rt-utils==1.2.7 +scikit-image==0.19.3 +scikit-learn==1.2.0 +scipy==1.9.3 +SimpleITK==2.2.1 +six==1.16.0 +threadpoolctl==3.1.0 +tifffile==2022.10.10 +torch==1.13.1 +TotalSegmentator==1.5.5 +tqdm==4.64.1 +traceback2==1.4.0 +typeguard==2.13.3 +typing_extensions==4.4.0 +unittest2==1.1.0 +urllib3==1.26.13 +vtk==9.2.2 +wslink==1.10.0 +xvfbwrapper==0.2.9 +yarl==1.8.2 From 4a31b0c4a0000cfeb2bff1b77896f142b32e8690 Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 7 Jul 2023 13:52:13 +0100 Subject: [PATCH 13/14] Test GHA: pip Python packages without specifying versions --- app/app_requirements.txt | 75 ++++------------------------------------ 1 file changed, 7 insertions(+), 68 deletions(-) diff --git a/app/app_requirements.txt b/app/app_requirements.txt index 1ac94ed..949c349 100644 --- a/app/app_requirements.txt +++ b/app/app_requirements.txt @@ -1,68 +1,7 @@ -aiohttp==3.8.3 -aiosignal==1.3.1 -async-timeout==4.0.2 -attrs==22.2.0 -batchgenerators==0.21 -certifi==2022.12.7 -charset-normalizer==2.1.1 -colorama==0.4.6 -contourpy==1.0.6 -cycler==0.11.0 -dataclasses==0.6 -dicom2nifti==2.4.7 -dill==0.3.6 -fonttools==4.38.0 -frozenlist==1.3.3 -fury==0.8.0 -future==0.18.3 -idna==3.4 -imageio==2.23.0 -joblib==1.2.0 -kiwisolver==1.4.4 -linecache2==1.0.0 -matplotlib==3.6.2 -MedPy==0.4.0 -monai-deploy-app-sdk==0.5.0 -multidict==6.0.4 -multiprocess==0.70.14 -networkx==2.8.8 -nibabel==4.0.2 -nnunet-customized==1.2 -numpy==1.24.1 -opencv-python==4.7.0.68 -p-tqdm==1.4.0 -packaging==22.0 -pandas==1.5.2 -pathos==0.3.0 -Pillow==9.3.0 -pox==0.3.2 -ppft==1.7.6.6 -psutil==5.9.4 -pydicom==2.3.1 -pytest==7.2.1 -pyparsing==3.0.9 -python-dateutil==2.8.2 -python-gdcm==3.0.20 -pytz==2022.7 -PyWavelets==1.4.1 -requests==2.28.1 -rt-utils==1.2.7 -scikit-image==0.19.3 -scikit-learn==1.2.0 -scipy==1.9.3 -SimpleITK==2.2.1 -six==1.16.0 -threadpoolctl==3.1.0 -tifffile==2022.10.10 -torch==1.13.1 -TotalSegmentator==1.5.5 -tqdm==4.64.1 -traceback2==1.4.0 -typeguard==2.13.3 -typing_extensions==4.4.0 -unittest2==1.1.0 -urllib3==1.26.13 -vtk==9.2.2 -wslink==1.10.0 -xvfbwrapper==0.2.9 -yarl==1.8.2 +torch +monai-deploy-app-sdk +highdicom +nibabel +monai +rt_utils +typeguard~=2.12.1 # known issue in monai-deploy-app-sdk https://github.com/Project-MONAI/monai-deploy-app-sdk/issues/410 From 56f6074dd8bd666a7152e7ef827b2087506573de Mon Sep 17 00:00:00 2001 From: Tom Roberts Date: Fri, 7 Jul 2023 14:56:00 +0100 Subject: [PATCH 14/14] Test GHA: only pip install app_requirements.txt i.e. minimal amount of packages --- .github/workflows/publish_map.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/publish_map.yml b/.github/workflows/publish_map.yml index 9a44e78..5fc67d6 100644 --- a/.github/workflows/publish_map.yml +++ b/.github/workflows/publish_map.yml @@ -33,7 +33,7 @@ jobs: run: | python -m pip install --upgrade pip pip install flake8 pytest pytest-cov - if [ -f requirements.txt ]; then pip install -r requirements.txt; fi + pip install -r app/app_requirements.txt - name: Display installed pip packages run: |