I am fairly expert in R and other languages, but I am admittedly relatively novice with python (though I am working to improve).
I think I am conceptually unclear on what it means to run Slicer/Slicer modules from the command line. Should running Slicer from the command-line be conceptually viewed as a running code/scripts inside a complete python environment (like a conda environment), whereby it contains a python interpreter and all necessary dependencies/modules? Could someone perhaps provide a high-level conceptual overview that might clarify what it actually means to run Slicer modules at the command-line?
I feel like connecting some of these dots may lead to a “eureka” moment for me, and I can begin to further appreciate using Slicer from the command-line. If it helps to place this into a more specific context, I am interested in learning how to perform batch pyradiomics feature extraction using the SlicerRadiomicsCLI module.
I have had no issues running the stand-alone pyradiomics CLI-tool, however, learning how to run effectively run Slicer modules from the command-line has broader benefit, given the large number of useful modules for other important image processing tasks.
It sounds like you are on the right track - we try to support many different ways of accessing Slicer functionality but sometimes you do need to investigate a bit to decide what’s the most streamlined way to accomplish what you need. Some of these practices are changing a bit now that we have Python3 support.
For streamlined batch processing and command line use, the python interpreter (PythonSlicer) can be used to access all the packages installed in Slicer, but won’t have the application context so many things won’t be available (e.g. rendering etc). You can use slicer.util.pip_install() to add custom packages.
From a shell, you can run many of the CLI modules as commands, using Slicer’s launcher (e.g. Slicer --launch BRAINSFit), which is a very lightweight way to access the ITK based C++ code.
Or if you need a full environment where you can access any of the code you can use the full Slicer application and pass it whatever startup script you want (the expense is a little extra startup overhead).
Thanks for the detailed reply. Could you perhaps clarify what you mean when you say I could use the PythonSlicer python interpreter? I know what a python interpreter is, in general, is the PythonSlicer interpreter just the python interpreter that is available to use inside the Slicer GUI (i.e. View > Python Interactor)? Or is this something different entirely?
PythonSlicer is an executable provided in the bin directory of the Slicer binaries. It’s the same version of python that’s included with the app, but it acts like a normal python (or python3) executable in terms of running scripts. So you can use it in place of regular python to make use of the Slicer environment for batch / cli operations.
Oh, okay, I did not know that was provided with the Slicer binary. I was able to locate this PythonSlicer executable and run it with success. Thank you very much for clarifying.
Is PythonSlicer the interpreter that is used when one uses the Slicer kernel in a Jupyter Notebook? Or is this different yet again?
It’s basically the same python code and environment, but where PythonSlicer is a headless interpreter, SlicerJupyter allows you to control a running Slicer application via the notebook. So Jupyter is basically doing the same thing as the python console in Slicer.
So, I tried to run pyradiomics from a shell using Slicer by locating what I thought was the correct python script (SlicerRadiomics.py) located in Slicer > Contents > Extensions > SlicerRadiomics > lib > Slicer-4.10 > qt-scripted-modules and ran the following code:
Note that here you might want to launch PythonSlicer so that you are sure to have the same python and pyradiomics installation as you have in the Slicer application. (SlicerRadiomics extension is the GUI wrapper that bundles pyradiomics into Slicer).
Which uses the python interpreter found in my $PATH (/anaconda3/bin/python), but not when I do:
PythonSlicer pyradiomics image.nrrd mask.nrrd
Traceback (most recent call last):
File “pyradiomics”, line 7, in
from radiomics.scripts.init import parse_args
ImportError: No module named radiomics.scripts.init
Right, that makes sense. You need to run it like: ./Slicer --launch PythonSlicer so it has the right environment (paths to the python libraries).
The first form you tried uses the Slicer application as the interpreter, which is why you need the extra options to turn off the main window and run the script - this uses the same basic python environment, but with the extra overhead of the GUI app. The second form uses your anaconda install, which might work too but also might have different packages or versions than the Slicer python.
Thank you for your patience. I don’t think I am clear on what exactly Slicer --launch PythonSlicer is really doing. When I run that code, a Slicer GUI is opened and nothing else appears to happen; so I don’t see the clear difference between using Slicer --python-script and Slicer --launch SlicerPython.
PythonSlicer inherits all the settings from the Slicer launcher, so it should not be necessary to run it using . /Slicer. Have you experienced issues running when simply running PythonSlicer?
Yes, I did test that. Running PythonSlicer without the launcher I cannot import radiomics but with the launcher I can (on linux nightly from 2019-08-22).
I anticipated when running Slicer --launch PythonSlicer that it would just open a python interpreter in the shell; but it seems to also open the Slicer GUI. Is this the expected behaviour?
Because calling PythonSlicer alone of course just opens a python interpreter.
Ah, are you on mac? The launcher is part of the mac build tree but not the official entrypoint for the app in the binaries now that I think about it. On linux Slicer --launch PythonSlicer does just bring up the interpreter.
Yes, for that case maybe you need to stick with the --no-main-window --python-script approach - it’s a bit more overhead but maybe it doesn’t matter.
@lassoan Yes, I can try these more recent versions. I won’t have the chance to test them for maybe two weeks as I am travelling for work. But I promise to test things out when I get back home and I will report back.
@pieper Good to know. Thank you very much for your help.
One last question – I am under the impression that some Slicer functionality/modules rely on using plastimatch. Does this mean the plastimatch binary is buried somewhere inside the Slicer file tree? I’m wondering if by installing Slicer, one now has the plastimatch binary behind-the-scenes which can be exposed at the command-line.