Skip to content

Commit

Permalink
Merge pull request #1 from flywheel-apps/v0.1.1
Browse files Browse the repository at this point in the history
V0.1.1
  • Loading branch information
lmperry authored Jun 27, 2018
2 parents 07b15e1 + 1dab184 commit 3a39068
Show file tree
Hide file tree
Showing 3 changed files with 47 additions and 35 deletions.
10 changes: 6 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
[![Docker Pulls](https://img.shields.io/docker/pulls/flywheel/hcp-icafix.svg)](https://hub.docker.com/r/flywheel/hcp-icafix/)
[![Docker Stars](https://img.shields.io/docker/stars/flywheel/hcp-icafix.svg)](https://hub.docker.com/r/flywheel/hcp-icafix/)
# flywheel/hcp-icafix
[Flywheel Gear](https://github.com/flywheel-io/gears/tree/master/spec) that runs [ICA-FIX denoising](https://fsl.fmrib.ox.ac.uk/fsl/fslwiki/FIX) on functional data preprocessed according to the [Human Connectome Project](http://www.humanconnectome.org) Minimal Preprocessing Pipeline (MPP). This is based on scripts from the v4.0-alpha release of the ICAFIX, PostFix, and RestingStateStats pipelines. For more info on the pipelines, see [HCP Pipelines](https://github.com/Washington-University/Pipelines). For more info on FSL FIX, including available classifiers, see [FSL FIX User Guide](https://fsl.fmrib.ox.ac.uk/fsl/fslwiki/FIX/UserGuide).
[Flywheel Gear](https://github.com/flywheel-io/gears/tree/master/spec) that runs [ICA-FIX denoising](https://fsl.fmrib.ox.ac.uk/fsl/fslwiki/FIX) on functional data preprocessed according to the [Human Connectome Project](http://www.humanconnectome.org) Minimal Preprocessing Pipeline (MPP). This is based on scripts from the v4.0-alpha release of the ICAFIX, PostFix, and RestingStateStats pipelines. For more info on the pipelines, see [HCP Pipelines](https://github.com/Washington-University/Pipelines). For more info on FSL FIX, including available classifiers, see [FSL FIX User Guide](https://fsl.fmrib.ox.ac.uk/fsl/fslwiki/FIX/UserGuide).

## Important notes
* ICA-FIX works best when applied to time series with many volumes. Original HCP rfMRI scans were 15 minutes TR=720ms each (1200 volumes). If data was collected in shorter scans within the same session, it's recommended to concatenate these before running ICA. For this gear, you can provide multiple FuncZip inputs and the pipeline will handle the concatenation and split the outputs once it completes.
* ICA-FIX works best when applied to time series with many volumes. Original HCP rfMRI scans were 15 minutes TR=720ms each (1200 volumes). If data was collected in shorter scans within the same session, it's recommended to concatenate these before running ICA. For this gear, you can provide multiple FuncZip inputs and the pipeline will handle the concatenation and split the outputs once it completes.
* If providing multiple FuncZip inputs, **make sure each HCP-Func gear was run with a unique fMRIName!** Otherwise, scans will be overwritten!

## Required inputs
Expand All @@ -16,7 +18,7 @@

## Outputs
* <code>\<subject\>\_\<fMRIName\>\_hcpicafix.zip</code>: Zipped output directory.
* <code>\<subject\>\_\<fMRIName\>\_RestingStateStats.zip</code>: Zipped RestingStateStats directory containing
* <code>\<subject\>\_\<fMRIName\>\_RestingStateStats.zip</code>: Zipped RestingStateStats directory containing
* <code>\<fMRIName\>\_Atlas\_stats.dscalar.nii</code>: spatial maps of SNR, CNR, etc...
* <code>\<fMRIName\>\_Atlas\_stats.txt</code>: whole-brain summary of SNR, CNR, etc...
* <code>RestingStateStats/*.png</code>: gray-plot images depicting impact of ICAFIX and other denoising strategies on time series and global signal.
Expand All @@ -26,4 +28,4 @@

## Optional inputs
1. FuncZip2, FuncZip3, etc... HCP-Functional output zips from additional scans.
2. CustomClassifier: Supply your own .RData file containing training weights.
2. CustomClassifier: Supply your own .RData file containing training weights.
9 changes: 6 additions & 3 deletions manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,16 @@
"description": "Runs ICA-FIX denoising on functional data preprocessed according to the HCP Minimal Preprocessing Pipeline. This Gear is based on scripts from the v4.0-alpha release of the ICAFIX, PostFix, and RestingStateStats pipelines.",
"author": "Human Connectome Project",
"maintainer": "Flywheel <[email protected]>",
"license": "Apache-2.0",
"license": "Other",
"url": "https://github.com/Washington-University/Pipelines",
"source": "https://github.com/flywheel-apps/hcp-icafix",
"cite": "(1) G. Salimi-Khorshidi, G. Douaud, C.F. Beckmann, M.F. Glasser, L. Griffanti S.M. Smith. Automatic denoising of functional MRI data: Combining independent component analysis and hierarchical fusion of classifiers. NeuroImage, 90:449-68, 2014 (2) L. Griffanti, G. Salimi-Khorshidi, C.F. Beckmann, E.J. Auerbach, G. Douaud, C.E. Sexton, E. Zsoldos, K. Ebmeier, N. Filippini, C.E. Mackay, S. Moeller, J.G. Xu, E. Yacoub, G. Baselli, K. Ugurbil, K.L. Miller, and S.M. Smith. ICA-based artefact removal and accelerated fMRI acquisition for improved resting state network imaging. NeuroImage, 95:232-47, 2014",
"version": "0.1.0",
"version": "0.1.1",
"custom": {
"docker-image": "flywheel/hcp-icafix:0.1.0"
"docker-image": "flywheel/hcp-icafix:0.1.1"
},
"flywheel": {
"suite": "Human Connectome Project"
},
"config": {
"FIXClassifier": {
Expand Down
63 changes: 35 additions & 28 deletions run
Original file line number Diff line number Diff line change
Expand Up @@ -21,20 +21,27 @@ source ${FLYWHEEL_BASE}/docker-env.sh
source ${SCRIPT_DIR}/bash_functions.sh # some useful tools

##############################################################################
# Parse configuration options
# Parse configuration

# If config.json exists, then we parse config file and cast vals to ENV Vars
# (Flywheel gear run). Otherwise we parse manifest.json and cast the values to
# ENV Vars from manifest (Docker run) Note value.default is used to grab the
# configured defaults.
# If the config file does not exist (i.e., local run) then parse the config
# options and values from the manifest. Those variables can be found in the
# manifest.json file within the `config` map.

if [[ -f $CONFIG_FILE ]]; then
eval $(jq -r '.config | to_entries[] | "FW_CONFIG_\(.key)=\(.value)"' $CONFIG_FILE)
eval $(jq -r '.inputs | to_entries[] | "FW_INPUT_\(.key)=\(.value.location.path)"' $CONFIG_FILE)
else
CONFIG_FILE=$FLYWHEEL_BASE/manifest.json
eval $(jq -r '.config | to_entries[] | "FW_CONFIG_\(.key)=\(.value.default)"' $CONFIG_FILE)
fi
function parse_config {
CONFIG_FILE=$FLYWHEEL_BASE/config.json
MANIFEST_FILE=$FLYWHEEL_BASE/manifest.json

if [[ -f $CONFIG_FILE ]]; then
echo -e "$(cat $CONFIG_FILE | jq -r '.config.'$1)"
else
CONFIG_FILE=$MANIFEST_FILE
echo -e "$(cat $MANIFEST_FILE | jq -r '.config.'$1'.default')"
fi
}

FW_CONFIG_Subject="$(parse_config 'FIXClassifier')"
FW_CONFIG_RegName="$(parse_config 'RegName')"
FW_CONFIG_HighPassFilter="$(parse_config 'HighPassFilter')"

##############################################################################
# use "echo" for testing arguments without running scripts
Expand Down Expand Up @@ -175,16 +182,16 @@ for i in 1 2 3 4 5 6 7 8 9 10; do
fi
FuncZip="${tmpv}"
fi

FuncZipList+=" ${FuncZip}"

echo -e "${CONTAINER} [$(timestamp)] Unzipping HCP-Functional input #${i}:" $(basename ${FuncZip})

tmp_FuncConfigFile=`mktemp -d`"/hcpfunc_config.json"
unzip -p ${FuncZip} '*hcpfunc_config.json' > ${tmp_FuncConfigFile}
tmp_fMRIName=$(jq -r '.config.fMRIName // empty' ${tmp_FuncConfigFile})
rm -f ${tmp_FuncConfigFile}

#check for fMRIName conflicts (eg: entered the same FuncZip twice)
if [ -z "${tmp_fMRIName}" ]; then
echo -e "${CONTAINER} [$(timestamp)] $(basename ${FuncZip}) did not contain config.json!"
Expand All @@ -194,7 +201,7 @@ for i in 1 2 3 4 5 6 7 8 9 10; do
exit 1
fi
fMRINameList+=" ${tmp_fMRIName}"

#only need to unzip MNINonLinear/Results for ICAFIX
unzip -o -q ${FuncZip} "${Subject}/MNINonLinear/Results/*" -d ${StudyFolder}
done
Expand Down Expand Up @@ -238,7 +245,7 @@ if [[ "$fMRIFileCount" == "1" ]]; then

# patched version is copied into here
FixScript=${HCPPIPEDIR}/ICAFIX/hcp_fix

pipeline_status_code=0
set -x
${RUN_FIX} ${FSLDIR}/bin/fsl_sub ${QUEUE} ${FSLSUBOPTIONS} \
Expand All @@ -248,14 +255,14 @@ if [[ "$fMRIFileCount" == "1" ]]; then
${ClassifierFile}
set +x
pipeline_status_code=$?

PostFixName=${fMRINameList}
PostFixHP="NO"
RSSBC="REVERT"

else
echo -e "${CONTAINER} [$(timestamp)] Starting: Multi-Run ICA-FIX Pipeline"

FixScript=${HCPPIPEDIR}/ICAFIX/hcp_fix_multi_run

ConcatName="ICAFIX_multi"
Expand Down Expand Up @@ -406,7 +413,7 @@ if [ -e "${rss_statsfile}" ]; then
echo -e "${CONTAINER} [$(timestamp)] Copying RestingStateStats images to output"
${RUN_RSS} cp -f ${StudyFolder}/${Subject}/MNINonLinear/Results/${PostFixName}/RestingStateStats/*_OrigTCS_QC_Summary_Plot.png ${StudyFolder}/
${RUN_RSS} cp -f ${StudyFolder}/${Subject}/MNINonLinear/Results/${PostFixName}/RestingStateStats/*_CleanedTCS_QC_Summary_Plot.png ${StudyFolder}/

rss_zipfile=${Subject}_${PostFixName}_RestingStateStats.zip
echo -e "${CONTAINER} [$(timestamp)] Zipping RestingStateStats results: ${rss_zipfile}"

Expand All @@ -415,8 +422,8 @@ if [ -e "${rss_statsfile}" ]; then
# <current directory>/${fMRIName}_Atlas_stats.txt
# <current directory>/RestingStateStats/*.png
(
cd ${StudyFolder}/${Subject}/MNINonLinear/Results/${PostFixName};
${RUN_RSS} rm -f ${OUTPUT_DIR}/${rss_zipfile};
cd ${StudyFolder}/${Subject}/MNINonLinear/Results/${PostFixName};
${RUN_RSS} rm -f ${OUTPUT_DIR}/${rss_zipfile};
${RUN_RSS} zip -r ${OUTPUT_DIR}/${rss_zipfile} \
*_stats.dscalar.nii \
*_stats.txt \
Expand Down Expand Up @@ -460,17 +467,17 @@ rm -f ${FilesToRemove} ${OrigFiles} ${FinalFiles}
# - add/update .config.Subject since it might later be pulled from other session metadata
# - add/update .config.fMRINameList so we have a record of which scans went into this
# TODO: fMRINameList should be stored somewhere more appropriate!
# - This jq call does the value replacement, then selects just .config but stores it back into a
# - This jq call does the value replacement, then selects just .config but stores it back into a
# new element called ".config" so the new file can be read as though it was flywheel config.json
OUTPUT_CONFIG_FILE=${StudyFolder}/${Subject}/${Subject}_${fMRIName}_hcpicafix_config.json
OUTPUT_CONFIG_FILE=${StudyFolder}/${Subject}/${Subject}_${fMRIName}_hcpicafix_config.json
jq -r '.config.RegName = "'$RegName'" | .config.Subject = "'$Subject'" | .config | {config: .}' $CONFIG_FILE \
| jq -r '.config.fMRINameList = "'"${fMRINameList}"'"' > ${OUTPUT_CONFIG_FILE}

# If pipeline successful, zip outputs and clean up
outputzipname=${Subject}_${PostFixName}_hcpicafix.zip
outputzipname=${Subject}_${PostFixName}_hcpicafix.zip
echo -e "${CONTAINER} [$(timestamp)] Zipping output file ${outputzipname}"
ziplistfile=${OUTPUT_DIR}/${outputzipname}.list.txt
rm -f ${ziplistfile}
rm -f ${ziplistfile}
rm -f ${OUTPUT_DIR}/${outputzipname}
cd ${StudyFolder}
# include all remaining files in functional output zip
Expand Down

0 comments on commit 3a39068

Please sign in to comment.