Skip to content

Commit

Permalink
Fix this example application to make it work with SDK v0.6+
Browse files Browse the repository at this point in the history
Signed-off-by: M Q <mingmelvinq@nvidia.com>
  • Loading branch information
MMelQin committed Jun 4, 2024
1 parent 8f804c0 commit 234f640
Show file tree
Hide file tree
Showing 5 changed files with 49 additions and 21 deletions.
26 changes: 10 additions & 16 deletions examples/apps/breast_density_classifer_app/README.md
Original file line number Diff line number Diff line change
@@ -1,29 +1,23 @@
## A MONAI Application Package to deploy breast density classification algorithm
This MAP is based on the Breast Density Model in MONAI [Model-Zoo](https://github.com/Project-MONAI/model-zoo). This model is developed at the Center for Augmented Intelligence in Imaging at the Mayo Clinic, Florida.
## A MONAI Application Package to deploy breast density classification algorithm
This MAP is based on the Breast Density Model in MONAI [Model-Zoo](https://github.com/Project-MONAI/model-zoo). This model is developed at the Center for Augmented Intelligence in Imaging at the Mayo Clinic, Florida.
For any questions, feel free to contact Vikash Gupta (gupta.vikash@mayo.edu)
Sample data and a torchscript model can be downloaded from https://drive.google.com/drive/folders/1Dryozl2MwNunpsGaFPVoaKBLkNbVM3Hu?usp=sharing


## Run the application package
### Python CLI
## Run the application code with Python interpreter
```
python app.py -i <input_dir> -o <out_dir> -m <breast_density_model>
python app.py -i <input_dir> -o <out_dir> -m <breast_density_model>
```

### MONAI Deploy CLI
## Package the application as a MONAI Application Package (contianer image)
In order to build the MONAI App Package, go a level up and execute the following command.
```
monai-deploy exec app.py -i <input_dir> -o <out_dir> -m <breast_density_model>
```
Alternatively, you can go a level higher and execute
```
monai-deploy exec breast_density_classification_app -i <input_dir> -o <out_dir> -m <breast_density_model>
monai-deploy package breast_density_classification_app -m <breast_density_model> -c breast_density_classifer_app/app.yaml --tag breast_density:0.1.0 --platform x64-workstation -l DEBUG
```


### Packaging the monai app
In order to build the monai app, Go a level up and execute the following command.
## Run the MONAI Application Package using MONAI Deploy CLI
```
monai-deploy package -b nvcr.io/nvidia/pytorch:21.12-py3 breast_density_classification_app --tag breast_density:0.1.0 -m $breast_density_model
monai-deploy run breast_density-x64-workstation-dgpu-linux-amd64:0.1.0 -i <input_dir> -o <output_dir>
```


Once the container exits successfully, check the results in the output directory. There should be a newly creeated DICOM instance file and a `output.json` file containing the classification results.
4 changes: 3 additions & 1 deletion examples/apps/breast_density_classifer_app/app.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,14 +26,16 @@ def __init__(self, *args, **kwargs):

def compose(self):
"""Creates the app specific operators and chain them up in the processing DAG."""
logging.info(f"Begin {self.compose.__name__}")
self._logger.info(f"Begin {self.compose.__name__}")

# Use command line options over environment variables to init context.
app_context: AppContext = Application.init_app_context(self.argv)
app_input_path = Path(app_context.input_path)
app_output_path = Path(app_context.output_path)
model_path = Path(app_context.model_path)

self._logger.info(f"App input, output path, & model path: {app_input_path}, {app_output_path}, {model_path}")

model_info = ModelInfo(
"MONAI Model for Breast Density",
"BreastDensity",
Expand Down
27 changes: 27 additions & 0 deletions examples/apps/breast_density_classifer_app/app.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
%YAML 1.2
# SPDX-FileCopyrightText: Copyright (c) 2022-2023 MONAI. All rights reserved.
# SPDX-License-Identifier: Apache-2.0
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
---
application:
title: MONAI Deploy App Package - Spleen Seg Inference
version: 1.0
inputFormats: ["file"]
outputFormats: ["file"]

resources:
cpu: 1
gpu: 1
memory: 1Gi
gpuMemory: 2Gi
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import json
import logging
import os
from pathlib import Path
from typing import Dict, Optional
Expand Down Expand Up @@ -94,7 +95,9 @@ def _get_model(self, app_context: AppContext, model_path: Path, model_name: str)
# `app_context.models.get(model_name)` returns a model instance if exists.
# If model_name is not specified and only one model exists, it returns that model.
model = app_context.models.get(model_name)
logging.info("Got the model network from the app context.")
else:
logging.info("Model network not in context. JIT loading from file...")
model = torch.jit.load(
ClassifierOperator.MODEL_LOCAL_PATH,
map_location=torch.device("cuda" if torch.cuda.is_available() else "cpu"),
Expand Down Expand Up @@ -149,9 +152,7 @@ def compute(self, op_input, op_output, context):

device = torch.device("cuda" if torch.cuda.is_available() else "cpu")

# Need to get the model from context, when it is re-implemented, and for now, load it directly here.
# model = context.models.get()
model = torch.jit.load(self.model_path, map_location=device)
# Model network loading has been handled during init.

pre_transforms = self.pre_process(_reader)
post_transforms = self.post_process()
Expand All @@ -162,7 +163,7 @@ def compute(self, op_input, op_output, context):
with torch.no_grad():
for d in dataloader:
image = d[0].to(device)
outputs = model(image)
outputs = self.model(image)
out = post_transforms(outputs).data.cpu().numpy()[0]
print(out)

Expand Down
4 changes: 4 additions & 0 deletions examples/apps/breast_density_classifer_app/requirements.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
highdicom>=0.18.2
monai>=1.2.0
pydicom>=2.3.0
torch>=1.12.0

0 comments on commit 234f640

Please sign in to comment.