Difference between revisions of "Documentation/Nightly/Developers/Tutorials/SelfTestModule"

From Slicer Wiki
Jump to: navigation, search
m (Text replacement - "\[http:\/\/www\.slicer\.org\/slicerWiki\/index\.php\/([^ ]+) ([^]]+)]" to "$2")
 
(7 intermediate revisions by 5 users not shown)
Line 1: Line 1:
 +
<noinclude>{{documentation/versioncheck}}</noinclude>
 
== Goal ==
 
== Goal ==
  
Line 5: Line 6:
 
Important features include:
 
Important features include:
 
* Tests are available as part of the binary distributions of slicer, so users can confirm correct behavior on their systems
 
* Tests are available as part of the binary distributions of slicer, so users can confirm correct behavior on their systems
* The same tests are run as part of the nightly test process and submitted to [http://slicer.cdash.org/index.php?project=Slicer4 the slicer dashboard].
+
* The same tests are run as part of the nightly test process and submitted to [http://slicer.cdash.org/index.php?project=SlicerPreview the slicer dashboard].
 
* Developers can efficiently develop the tests by reloading python scripts without needing to exit slicer.
 
* Developers can efficiently develop the tests by reloading python scripts without needing to exit slicer.
  
Line 13: Line 14:
 
* When developing a new scripted module, you can create a test script at the same time.  This way you can use the script to help you test the code as you develop it (by reloading and testing as you write the code without even exiting slicer) and also verify that your code still works as you refactor and improve the code.  Plus, you can easily test the code on multiple platforms without a lot of tedious clicking to reload data.
 
* When developing a new scripted module, you can create a test script at the same time.  This way you can use the script to help you test the code as you develop it (by reloading and testing as you write the code without even exiting slicer) and also verify that your code still works as you refactor and improve the code.  Plus, you can easily test the code on multiple platforms without a lot of tedious clicking to reload data.
 
* Self Tests of the core slicer functionality can be used equally in build-time and run-time scenarios.
 
* Self Tests of the core slicer functionality can be used equally in build-time and run-time scenarios.
* [[Documentation/4.1/Developers/Modules|Any type of module or extension]] can also include self tests (and should!).
+
* [[Documentation/{{documentation/version}}/Developers/Modules|Any type of module or extension]] can also include self tests (and should!).
  
 
== Caveats ==
 
== Caveats ==
Line 23: Line 24:
  
 
=== Use the ModuleWizard ===
 
=== Use the ModuleWizard ===
Start by using the [[Documentation/{{documentation/version}}/Developers/ModuleWizard|module wizard]] to create a new scripted module.   
+
Start by using the [[Documentation/{{documentation/version}}/Developers/ExtensionWizard|extension wizard]] to create a new scripted module.   
  
 
Give the module a descriptive name based on the functionality you intend to test.  If the module is created to recreated the steps described in a bug report, append the bug report name to the end of the test.  For example, one test is [http://viewvc.slicer.org/viewvc.cgi/Slicer4/trunk/Applications/SlicerApp/Testing/Python/sceneImport2428.py?view=markup sceneImport2428.py] which tests [http://www.na-mic.org/Bug/view.php?id=2428 issue #2428].
 
Give the module a descriptive name based on the functionality you intend to test.  If the module is created to recreated the steps described in a bug report, append the bug report name to the end of the test.  For example, one test is [http://viewvc.slicer.org/viewvc.cgi/Slicer4/trunk/Applications/SlicerApp/Testing/Python/sceneImport2428.py?view=markup sceneImport2428.py] which tests [http://www.na-mic.org/Bug/view.php?id=2428 issue #2428].
 
At first, put the new module in a dedicated directory:
 
 
cd <Slicer source dir>
 
./Utilities/Scripts/ModuleWizard.py --template ./Extensions/Testing/ScriptedLoadableExtensionTemplate --target ../NeurosurgeryTutorial NeurosurgeryTutorial
 
 
This will create a new extension directory with a skeleton NeurosurgeryTutorial.py file ready to work on.
 
  
 
=== Edit the new module ===
 
=== Edit the new module ===
Line 66: Line 60:
  
 
[http://viewvc.slicer.org/viewvc.cgi/Slicer4/trunk/Applications/SlicerApp/Testing/Python/ other self test scripts] load multiple datasets and/or scene files.
 
[http://viewvc.slicer.org/viewvc.cgi/Slicer4/trunk/Applications/SlicerApp/Testing/Python/ other self test scripts] load multiple datasets and/or scene files.
 +
 +
Note that the current test template will re-use any existing file in the temp directory that has non-zero size.  If you change the test data, give it a new name for the download.
  
 
=== Accessing Test Data Through A Firewall ===
 
=== Accessing Test Data Through A Firewall ===
Line 85: Line 81:
 
Save the file and click Reload and Test.  You should see your new message as a dialog and you should also see it printed in the console.
 
Save the file and click Reload and Test.  You should see your new message as a dialog and you should also see it printed in the console.
  
From here, you "only" need to implement the python code that performs your test.  For that, you can rely on the python wrappings of Qt, VTK, numpy, etc. [http://www.slicer.org/slicerWiki/index.php/Slicer4:Python Python in Slicer4]
+
From here, you "only" need to implement the python code that performs your test.  For that, you can rely on the python wrappings of Qt, VTK, numpy, etc. [[Slicer4:Python|Python in Slicer4]]
  
 
To open up the GUI for a specific module, for instance the Volumes modules, you can use:
 
To open up the GUI for a specific module, for instance the Volumes modules, you can use:
Line 92: Line 88:
 
     m.moduleSelector().selectModule('Volumes')
 
     m.moduleSelector().selectModule('Volumes')
 
     self.delayDisplay("Entered Volumes module")
 
     self.delayDisplay("Entered Volumes module")
 +
 +
=== Screen shots ===
 +
 +
To capture screen shots, when the Enable Screenshots button in the GUI is clicked, or the default setting is changed in your code , then add this line after parts of your code that sets up the GUI into configurations that you want to capture:
 +
 +
  self.takeScreenshot('TestName-ScreenshotName','Screenshot description',-1)
 +
 +
The last argument defines what parts of Slicer to capture, -1 is for the whole window, you can also use these options:
 +
 +
  slicer.qMRMLScreenShotDialog().FullLayout
 +
  slicer.qMRMLScreenShotDialog().ThreeD
 +
  slicer.qMRMLScreenShotDialog().Red
 +
  slicer.qMRMLScreenShotDialog().Yellow
 +
  slicer.qMRMLScreenShotDialog().Green
 +
 +
To enable screen shots by default, change this line:
 +
 +
  self.enableScreenshotsFlagCheckBox.checked = 0
 +
 +
to:
 +
 +
  self.enableScreenshotsFlagCheckBox.checked = 1
  
 
== Adding the Result to Slicer ==
 
== Adding the Result to Slicer ==

Latest revision as of 02:30, 27 November 2019

Home < Documentation < Nightly < Developers < Tutorials < SelfTestModule


For the latest Slicer documentation, visit the read-the-docs.


Goal

After review and work by the slicer community, a framework is in place that supports Built In Self Tests for slicer.

Important features include:

  • Tests are available as part of the binary distributions of slicer, so users can confirm correct behavior on their systems
  • The same tests are run as part of the nightly test process and submitted to the slicer dashboard.
  • Developers can efficiently develop the tests by reloading python scripts without needing to exit slicer.

This page provides an overview of the implementation and use of these scripts.

The approach described here can be used in a number of ways:

  • When developing a new scripted module, you can create a test script at the same time. This way you can use the script to help you test the code as you develop it (by reloading and testing as you write the code without even exiting slicer) and also verify that your code still works as you refactor and improve the code. Plus, you can easily test the code on multiple platforms without a lot of tedious clicking to reload data.
  • Self Tests of the core slicer functionality can be used equally in build-time and run-time scenarios.
  • Any type of module or extension can also include self tests (and should!).

Caveats

This project is actively evolving and is being worked on and some of the implementation details will change in future versions.

These instructions assume you are working with a local build of slicer.

Creating the Skeleton

Use the ModuleWizard

Start by using the extension wizard to create a new scripted module.

Give the module a descriptive name based on the functionality you intend to test. If the module is created to recreated the steps described in a bug report, append the bug report name to the end of the test. For example, one test is sceneImport2428.py which tests issue #2428.

Edit the new module

In the editor, change a few of the fields:

Change:

   parent.categories = ["Examples"]

to:

   parent.categories = ["Testing.TestCases"]

Also change the contributor names, the acknowledgement text, and any other general fields to customize the module.

Configure Slicer

In slicer, go into the Application Settings->Module Settings and add a path to the NeurosurgeryTutorial directory and restart slicer.

Restart Slicer and Test

When slicer comes back up you should find your module in the Modules->Testing->TestCases menu.

If you click the Reload and Test button, a default test will run and it should pass.

You are now ready to customize this test for your own use.

Test Data

Test data should be uploaded slicer's midas instance. If you need to upload new data, consult the midas documentation to get an account and request access to the NA-MIC community.

Toward the bottom of your python script (in the method test_NeurosurgeryTutorial1) you can see how data is downloaded from midas and loaded into slicer. In the template, a single volume file is downloaded:

   downloads = (
       ('http://slicer.kitware.com/midas3/download?items=5767', 'FA.nrrd', slicer.util.loadVolume),
       )

other self test scripts load multiple datasets and/or scene files.

Note that the current test template will re-use any existing file in the temp directory that has non-zero size. If you change the test data, give it a new name for the download.

Accessing Test Data Through A Firewall

The SelfTest modules use python urllib to download data. If you are behind a firewall, you can configure urllib to use a proxy server by setting the environment variable

 export http_proxy=http://proxyhost:proxyport

Note the use of "http://" at the start of the url. The environment variable http_proxy is also used by git and wget but they do not require the "http://" but will accept it if there.

Writing/Refining the Code

Note that you can click the Reload and Test button as many times as you want and to re-run the test.

Now, you can experiment with changing the code. Add another line to the beginning of the test_NeurosurgeryTutorial1 method like:

self.delayDisplay("My modified test")

Save the file and click Reload and Test. You should see your new message as a dialog and you should also see it printed in the console.

From here, you "only" need to implement the python code that performs your test. For that, you can rely on the python wrappings of Qt, VTK, numpy, etc. Python in Slicer4

To open up the GUI for a specific module, for instance the Volumes modules, you can use:

   m = slicer.util.mainWindow()
   m.moduleSelector().selectModule('Volumes')
   self.delayDisplay("Entered Volumes module")

Screen shots

To capture screen shots, when the Enable Screenshots button in the GUI is clicked, or the default setting is changed in your code , then add this line after parts of your code that sets up the GUI into configurations that you want to capture:

 self.takeScreenshot('TestName-ScreenshotName','Screenshot description',-1)

The last argument defines what parts of Slicer to capture, -1 is for the whole window, you can also use these options:

 slicer.qMRMLScreenShotDialog().FullLayout
 slicer.qMRMLScreenShotDialog().ThreeD
 slicer.qMRMLScreenShotDialog().Red
 slicer.qMRMLScreenShotDialog().Yellow
 slicer.qMRMLScreenShotDialog().Green

To enable screen shots by default, change this line:

 self.enableScreenshotsFlagCheckBox.checked = 0

to:

 self.enableScreenshotsFlagCheckBox.checked = 1

Adding the Result to Slicer

When you are satisfied that your test captures the intended functionality, you can add it to the main repository (or, if you don't have write access, coordinate with a developer who does have write access).

To make this a self test, copy the NeurosurgeryTutorial.py into Applications/SlicerApp/Testing/Python/ and edit the Applications/SlicerApp/Testing/Python/CMakeLists.txt file.

In the SelfTests section, add a line like:

slicer_add_python_unittest(SCRIPT NeurosurgeryTutorial.py)

and add NeurosurgeryTutorial.py to the KIT_PYTHON_SCRIPTS list.

That's it!

Now your test will be run as part of the nightly dashboard process and will be available to users so they can verify that your code is operating as designed on their platform.