Skip to content
This repository was archived by the owner on Sep 8, 2025. It is now read-only.

Commit 83ab780

Browse files
authored
Merge pull request #6 from flywheel-apps/exitstatus
v0.2
2 parents 7fab2bf + 776f5d6 commit 83ab780

File tree

6 files changed

+177
-145
lines changed

6 files changed

+177
-145
lines changed

Dockerfile

Lines changed: 20 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,30 +1,36 @@
11
# flywheel/mri-deface
2+
#
3+
# Authorship: Jennifer Reiter
4+
#
25

3-
# start with ubuntu
46
FROM ubuntu:trusty
5-
MAINTAINER Jennifer Reiter <[email protected]>
7+
MAINTAINER Flywheel <[email protected]>
68

7-
# Install gzip and wget
9+
# Install dependencies
810
RUN apt-get update && apt-get -y install \
911
unzip \
1012
gzip \
11-
wget
13+
wget \
14+
jq
1215

13-
# Make directory for flywheel spec (v0)
16+
# Make directories for Flywheel v0 Spec
1417
ENV FLYWHEEL /flywheel/v0
1518
RUN mkdir -p ${FLYWHEEL}
1619
COPY run ${FLYWHEEL}/run
1720
COPY manifest.json ${FLYWHEEL}/manifest.json
1821

19-
# Install jq to parse the JSON config file
20-
RUN wget -N -qO- -O /usr/bin/jq http://stedolan.github.io/jq/download/linux64/jq
21-
RUN chmod +x /usr/bin/jq
22+
# Download mri_deface nd additional files from MGH
23+
RUN wget -N -qO- -O ${FLYWHEEL}/mri_deface.gz \
24+
ftp://surfer.nmr.mgh.harvard.edu/pub/dist/mri_deface/mri_deface-v1.22-Linux64.gz && \
25+
gunzip ${FLYWHEEL}/mri_deface.gz && \
26+
chmod +x /flywheel/v0/mri_deface
2227

23-
# Download Free Surfer Deface from MGH and additional files needed for Defacing algorithm
24-
RUN wget -N -qO- -O ${FLYWHEEL}/mri_deface.gz ftp://surfer.nmr.mgh.harvard.edu/pub/dist/mri_deface/mri_deface-v1.22-Linux64.gz && gunzip ${FLYWHEEL}/mri_deface.gz
25-
RUN wget -N -qO- -O ${FLYWHEEL}/face.gca.gz ftp://surfer.nmr.mgh.harvard.edu/pub/dist/mri_deface/face.gca.gz && gunzip ${FLYWHEEL}/face.gca.gz
26-
RUN wget -N -qO- -O ${FLYWHEEL}/talairach_mixed_with_skull.gca.gz ftp://surfer.nmr.mgh.harvard.edu/pub/dist/mri_deface/talairach_mixed_with_skull.gca.gz && gunzip ${FLYWHEEL}/talairach_mixed_with_skull.gca.gz
27-
RUN chmod +x /flywheel/v0/mri_deface
28+
RUN wget -N -qO- -O ${FLYWHEEL}/face.gca.gz \
29+
ftp://surfer.nmr.mgh.harvard.edu/pub/dist/mri_deface/face.gca.gz && \
30+
gunzip ${FLYWHEEL}/face.gca.gz
31+
32+
RUN wget -N -qO- -O ${FLYWHEEL}/talairach_mixed_with_skull.gca.gz \
33+
ftp://surfer.nmr.mgh.harvard.edu/pub/dist/mri_deface/talairach_mixed_with_skull.gca.gz && \
34+
gunzip ${FLYWHEEL}/talairach_mixed_with_skull.gca.gz
2835

29-
# Set the entrypoint
3036
ENTRYPOINT ["/flywheel/v0/run"]

README.md

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2,30 +2,30 @@
22
[![Docker Stars](https://img.shields.io/docker/stars/flywheel/mri-deface.svg)](https://hub.docker.com/r/flywheel/mri-deface/)
33
# flywheel/mri-deface
44

5-
Build context for a [Flywheel Gear](https://github.com/flywheel-io/gears/tree/master/spec) which runs the MBIRN `mri_deface` tool (v1.22) from FreeSurfer.
5+
Build context for a [Flywheel Gear](https://github.com/flywheel-io/gears/tree/master/spec) which runs the [MBIRN `mri_deface` tool](https://surfer.nmr.mgh.harvard.edu/fswiki/mri_deface) (v1.22) from FreeSurfer.
66

77
* No other FreeSurfer tools are installed within this Docker image
8-
* Unlike the full FreeSurfer software, a license file is not necessary to use these tools
9-
* You can change ```build.sh``` to edit the repository name for the image (default=`flywheel/mri-deface`).
8+
* Unlike the full FreeSurfer software, a license file is not necessary to use this tool
109
* The resulting image is ~0.5GB
1110

1211
### Build the Image
1312
To build the image:
1413
```
1514
git clone https://github.com/flywheel-apps/mri-deface
16-
./build.sh
15+
cd mri-deface
16+
docker build -t flywheel/mri-deface .
1717
```
1818

1919
### Example Local Usage ###
20-
To run the `mri_deface` command in this image on your local instance, do the following:
20+
To run the `mri_deface` Gear your local instance with Docker, do the following:
2121
```
2222
docker run --rm -ti \
2323
-v </path/to/input/data>:/flywheel/v0/input/anatomical \
2424
-v </path/for/output/data>:/flywheel/v0/output \
2525
flywheel/mri-deface
2626
```
2727
Usage notes:
28-
* You are mounting the directory (using the ```-v``` flag) which contains the input data in the container at ```/flywheel/v0/input/anatomical``` and mounting the directory where you want your output data within the container at ```/flywheel/v0/output```.
29-
* The "input" directory (mounted within the container at ```/flywheel/v0/input/anatomical```) should contain only the file you wish to 'deface'.
30-
* Only the first file found in the input directory will be run through the algorithm.
28+
* You are mounting the directory (using the ```-v``` flag) which contains the input data in the container at ```/flywheel/v0/input/anatomical``` and mounting the directory where you want your output data within the container at ```/flywheel/v0/output```
29+
* The "input" directory (mounted within the container at ```/flywheel/v0/input/anatomical```) should contain only the file you wish to 'deface'
30+
* Only the first file found in the input directory will be run through the algorithm
3131
* No input arguments are required for the container to be executed

build.sh

Lines changed: 0 additions & 7 deletions
This file was deleted.

export.sh

Lines changed: 0 additions & 17 deletions
This file was deleted.

manifest.json

Lines changed: 34 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -1,33 +1,38 @@
11
{
2-
"author": "Amanda Bischoff-Grethe, et al.",
3-
"maintainer": "Jennifer Reiter <[email protected]>",
4-
"config": {
5-
"output_extension": {
6-
"description": "Desired extension of output file format. Can be either '.mgz' or '.nii.gz' (default='.nii.gz').",
7-
"default": ".nii.gz",
8-
"type": "string"
9-
}
2+
"author": "Amanda Bischoff-Grethe, et al.",
3+
"maintainer": "Flywheel <[email protected]>",
4+
"config": {
5+
"output_nifti": {
6+
"description": "Write output as compressed NIfTI (default=true)",
7+
"default": true,
8+
"type": "boolean"
109
},
11-
"description": "This Gear contains an algorithm (mri-deface, from FreeSurfer) for removing identifiable facial features (eyes, nose, and mouth). This algorithm locates the subject's facial features and removes them without disturbing brain tissue. The algorithm was devised to work on T1-weighted structural MRI; it produces a defaced structural image, and an image of the applied mask. Please cite http://www.ncbi.nlm.nih.gov/pmc/articles/PMC2408762/ if using this gear in your work.",
12-
"inputs": {
13-
"anatomical": {
14-
"base": "file",
15-
"type": {
16-
"enum": [
17-
"nifti",
18-
"mgh",
19-
"dicom"
20-
]
21-
}
22-
}
23-
},
24-
"label": "FreeSurfer: MBIRN Defacer for structural MRI (mri-deface v1.22)",
25-
"license": "GPL-2.0",
26-
"name": "mri-deface",
27-
"source": "https://github.com/flywheel-apps/mri-deface",
28-
"url": "https://surfer.nmr.mgh.harvard.edu/fswiki/mri_deface",
29-
"version": "0.1.2",
30-
"custom": {
31-
"docker-image": "flywheel/mri-deface:v0.1.2"
10+
"output_mgh": {
11+
"description": "Write the output file as compressed MGH file (.mgz) (default=false)",
12+
"default": false,
13+
"type": "boolean"
14+
}
15+
},
16+
"description": "MBIRN Defacer for structural MRI (mri-deface v1.22). MRI_DEFACE (v1.22) from FreeSurfer is a tool for removing identifiable facial features (eyes, nose, and mouth). This algorithm locates the subject's facial features and removes them without disturbing brain tissue. The algorithm was devised to work on T1-weighted anatomical MR data; it consumes NIfTI, DICOM, or MGH formats and produces a defaced anatomical image in either NIfTI or MGH format. Please cite http://www.ncbi.nlm.nih.gov/pmc/articles/PMC2408762/ if using this tool in your work.",
17+
"inputs": {
18+
"anatomical": {
19+
"base": "file",
20+
"type": {
21+
"enum": [
22+
"nifti",
23+
"mgh",
24+
"dicom"
25+
]
26+
}
3227
}
28+
},
29+
"label": "FreeSurfer: MBIRN Defacer for structural MRI (mri-deface v1.22)",
30+
"license": "GPL-2.0",
31+
"name": "mri-deface",
32+
"source": "https://github.com/flywheel-apps/mri-deface",
33+
"url": "https://surfer.nmr.mgh.harvard.edu/fswiki/mri_deface",
34+
"version": "0.2",
35+
"custom": {
36+
"docker-image": "flywheel/mri-deface:v0.2"
37+
}
3338
}

run

Lines changed: 115 additions & 70 deletions
Original file line numberDiff line numberDiff line change
@@ -1,78 +1,123 @@
11
#! /bin/bash
2-
# This script is meant to evoke the algorithm without requiring any input arguments
32
#
4-
LOG_FILE=/flywheel/v0/output/mri-deface.log
5-
6-
(
7-
# Define directory names and containers
8-
FLYWHEEL_BASE=/flywheel/v0
9-
INPUT_DIR=$FLYWHEEL_BASE/input/anatomical
10-
OUTPUT_DIR=$FLYWHEEL_BASE/output
11-
CONFIG_FILE=$FLYWHEEL_BASE/config.json
12-
CONTAINER='[flywheel/mri-deface]'
13-
14-
# Define brain and face templates
15-
brain_template=$FLYWHEEL_BASE/talairach_mixed_with_skull.gca
16-
face_template=$FLYWHEEL_BASE/face.gca
17-
18-
# Check if the input directory is not empty
19-
if [[ "$(ls -A $INPUT_DIR)" ]] ; then
20-
echo "$CONTAINER Starting..."
21-
else
22-
echo "Input directory is empty: $INPUT_DIR"
23-
exit 1
24-
fi
3+
# Run script for flywheel/mri-deface Gear.
4+
#
5+
# Authorship: Jennifer Reiter, Michael Perry
6+
#
7+
8+
##############################################################################
9+
# Define directory names and containers
10+
11+
FLYWHEEL_BASE=/flywheel/v0
12+
INPUT_DIR=$FLYWHEEL_BASE/input/anatomical
13+
OUTPUT_DIR=$FLYWHEEL_BASE/output
14+
CONFIG_FILE=$FLYWHEEL_BASE/config.json
15+
CONTAINER='[flywheel/mri-deface]'
16+
17+
18+
##############################################################################
19+
# Parse configuration options
20+
21+
# If config.json exists, then we parse config file and cast vals to ENV Vars
22+
# (Flywheel gear run). Otherwise we parse manifest.json and cast the values to
23+
# ENV Vars from manifest (Docker run) Note value.default is used to grab the
24+
# configured defaults.
25+
26+
if [[ -f $CONFIG_FILE ]]; then
27+
eval $(jq -r '.config | to_entries[] | "config_\(.key)=\(.value)"' $CONFIG_FILE)
28+
else
29+
CONFIG_FILE=$FLYWHEEL_BASE/manifest.json
30+
eval $(jq -r '.config | to_entries[] | "config_\(.key)=\(.value.default)"' $CONFIG_FILE)
31+
fi
32+
33+
34+
##############################################################################
35+
# Define brain and face templates
36+
37+
brain_template=$FLYWHEEL_BASE/talairach_mixed_with_skull.gca
38+
face_template=$FLYWHEEL_BASE/face.gca
39+
2540

26-
# Find input file in input directory with the extension .nii, .nii.gz, .mgz or .mgh.gz or a .zip dicom file
27-
input_file=`find $INPUT_DIR -iname '*.nii' -o -iname '*.nii.gz' -o -iname '*.mgz' -o -iname '*.mgh.gz' -o -iname '*.zip'`
28-
29-
# Check if input file exists
30-
if [[ -e $input_file ]]
31-
then
32-
## Define extension of the input file
33-
bni=`basename "$input_file"`
34-
filename="${bni%%.*}"
35-
inextension="${bni#*.}"
36-
# If input extension is .zip, then unzip the files (assuming they are DICOM files)
37-
if [[ $inextension == "zip" ]]
38-
then
39-
echo "Unzipping DICOM files"
40-
unzip $input_file -d $INPUT_DIR
41-
# Now that the DICOM files are unzipped, need to find one filename to pass to the mri deface software
42-
input_file=`find $INPUT_DIR -iname '*.dcm' | head -n 1`
43-
fi
44-
## Define extension of the output file
45-
# Get output file extension from config file, if it exists
46-
if [[ -e $CONFIG_FILE ]]
47-
then
48-
echo "Config file is present"
49-
outextension=`cat $CONFIG_FILE | jq -r '.config.output_extension'`
50-
echo "The extension read from the config file: $outextension"
51-
# Otherwise, define output file extension as nifti (.nii.gz)
52-
else
53-
outextension=".nii.gz"
54-
echo "No config file found, so default extension ($outextension) is being used for output"
55-
fi
56-
# Define output file to be passed to mri_deface
57-
output_file=$OUTPUT_DIR/$filename'_deface'$outextension
58-
/flywheel/v0/mri_deface $input_file $brain_template $face_template $output_file
59-
else
60-
echo "No Nifti, DICOM or MGZ inputs were found within input directory $INPUT_DIR"
61-
exit 1
41+
##############################################################################
42+
# Handle INPUT file
43+
44+
# Find input file In input directory with the extension
45+
# .nii, .nii.gz, .mgz or .mgh.gz or a .zip DICOM file
46+
input_file=`find $INPUT_DIR -iname '*.nii' -o -iname '*.nii.gz' -o -iname '*.mgz' -o -iname '*.mgh.gz' -o -iname '*.zip'`
47+
48+
# Check that input file exists
49+
if [[ -e $input_file ]]; then
50+
echo "${CONTAINER} Input file found: ${input_file}"
51+
52+
# Determine the type of the input file
53+
if [[ "$input_file" == *.zip ]]; then
54+
type=".zip"
55+
elif [[ "$input_file" == *.nii ]]; then
56+
type=".nii"
57+
elif [[ "$input_file" == *.nii.gz ]]; then
58+
type=".nii.gz"
59+
elif [[ "$input_file" == *.mgz ]]; then
60+
type=".mgz"
61+
elif [[ "$input_file" == *.mgz.gz ]]; then
62+
type=".mgz.gz"
6263
fi
6364

64-
# Get a list of the files in the output directory
65-
outputs=`find $OUTPUT_DIR -type f -name "*"`
66-
67-
# If outputs exist, then go on...
68-
if [[ -z $outputs ]]
69-
then
70-
echo "No results found in output directory... Exiting"
71-
exit 1
72-
else
73-
chmod -R 777 $OUTPUT_DIR
74-
echo -e "Wrote: `ls $OUTPUT_DIR`"
65+
# Get the base filename
66+
base_filename=`basename "$input_file" $type`
67+
else
68+
echo "${CONTAINER} No Nifti, DICOM or MGZ inputs were found within input directory $INPUT_DIR"
69+
exit 1
70+
fi
71+
72+
# If input extension is .zip, then unzip the files (assuming they are DICOM files)
73+
if [[ "$type" == *.zip ]]; then
74+
echo "${CONTAINER} Unzipping DICOM files..."
75+
unzip_dir=/tmp/unzipped
76+
unzip $input_file -d $unzip_dir
77+
78+
# Now that the DICOM files are unzipped, need to find the full path to the
79+
# first file to pass mri_deface
80+
input_file=`find $unzip_dir/* -type f | head -n 1`
81+
if [[ -e $input_file ]]; then
82+
echo "$CONTAINER Input file set to: $input_file"
83+
base_filename=`basename "$base_filename" .dicom`
84+
else
85+
echo "${CONTAINER} No input file found in: ${input_file}"
86+
exit 1
7587
fi
88+
fi
89+
90+
91+
##############################################################################
92+
# Run MRI_DEFACE algorithm
93+
94+
# Set initial exit status
95+
mri_deface_exit_status_nifti=0
96+
mri_deface_exit_status_mgz=0
97+
98+
# Set base output_file name
99+
output_file=$OUTPUT_DIR/"$base_filename"'_deface'
100+
101+
# Check if user wanted NIfTI output
102+
if [[ $config_output_nifti == 'true' ]]; then
103+
/flywheel/v0/mri_deface "$input_file" "$brain_template" "$face_template" "$output_file"'.nii.gz'
104+
mri_deface_exit_status_nifti=$?
105+
fi
106+
107+
# Check if user wanted MGH output
108+
if [[ $config_output_mgh == 'true' ]]; then
109+
/flywheel/v0/mri_deface "$input_file" "$brain_template" "$face_template" "$output_file"'.mgz'
110+
mri_deface_exit_status_mgz=$?
111+
fi
112+
113+
114+
##############################################################################
115+
# Handle Exit status
76116

117+
if [[ $mri_deface_exit_status_nifti == 0 ]] && [[ $mri_deface_exit_status_mgz == 0 ]]; then
118+
echo -e "${CONTAINER} Success!"
77119
exit 0
78-
) 2>&1 | tee $LOG_FILE
120+
else
121+
echo "${CONTAINER} Something went wrong! mri_deface exited non-zero!"
122+
exit 1
123+
fi

0 commit comments

Comments
 (0)