#!/bin/sh
# Testing the installation of the dev tools
# cepgenerator and devtools
# 
# echo $? get the last returned value of the script
#
# TODO add complete library tests using cepgenerator
# This can be done using exampleLibraryAction.xml 
# + adding a real action in there 
# + adding a component
# + adding a test file
# + adding source code files :
#   ActionDoSomething.cpp in 
#   EmptyComponent.cpp to use the library
#   EmptyLibrary.h EmptyLibrary.cpp
# + add "echo "#include "ActionDoSomething.cpp"" >> actions/emptyaction/Action.cpp"
# and compile only then
# @see the shaker lib turorial
#
# TODO add a complete example with all the possible Property types
# @see the property tutorial
#
# TODO add another family of tests using testaction and testcomponent on cepgenerated action/components
#
# TODO distribute all the files from the ./sdk/applications/cepgenerator/testdata directory 
# in the package $(pkg-dev) so that they are installed in /usr/share/camitk-$(VER_SHORT)/testdata/cepgenerator/*
# In this script, just copy all files from /usr/share/camitk-$(VER_SHORT)/testdata/cepgenerator/* to the tmpdir
# and run a foreach on each .xml files

set -e

#DEBUG
#set -x

#DEBUG
#To test with different library versions, you can use different install path, for instance:
# CMAKE_OPTIONS="-DVTK_DIR:PATH=/opt/vtk6/lib/cmake/vtk-6.3 -DITK_DIR:PATH=/opt/vtk6/lib/cmake/ITK-4.9 -DGDCM_DIR:PATH=/opt/vtk6/lib/gdcm-2.6"

# cleanup on exit
cleanup() {
    # backup the current exit status
    currentExitValue=$?
    if [ "$currentExitValue" -ne "0" ]; then
        # output all possible files
        cd $workingDir
        echo
        echo "===== ABORTED ====="
        echo
        echo "===== ABORTED wizard-$testDirName ====="
        cat ./wizard-$testDirName
        cd $testDirName/build
        echo "===== ABORTED cmake-log ====="
        cat ../cmake-log
        echo "===== ABORTED cmake-error ====="  
        cat ../cmake-error
        echo "===== ABORTED make-log ====="
        cat ../make-log
        echo "===== ABORTED make-error ====="  
        cat ../make-error
        cd
    fi
    # cleanup current dir
    rm -rf $workingDir
    # use the backup value (otherwise the result of the "rm -rf" command above will
    # be used, and that's probably always 0 !)
    exit $currentExitValue
}

# if a problem occurs, call the clean method
trap "cleanup" 0 INT QUIT ABRT PIPE TERM EXIT

# --------------------------------------------------------------------------
#
# Get ready
#
# --------------------------------------------------------------------------

echo "Checking camitk-dev installation..."
exitStatus=0 # nothing bad. By convention exit 0 indicates success
checkValueId=1 # test id starts at 1

# create working directory
workingDir=$(mktemp --tmpdir -d camitk-test-tmp.XXXXXXXXXX)

getWorkingDirExtensionCount() {
  echo $(xvfb-run --auto-servernum --server-num=1 camitk-config --config | grep "\[W\]" | wc -l)
}


# --------------------------------------------------------------------------

cd $workingDir


# ---------------------- exampleComponents.xml ----------------------
# Example taken from distributed source ./sdk/applications/cepgenerator/testdata/exampleComponents.xml
cat <<EOF > exampleComponents.xml
<?xml version="1.0" encoding="UTF-8"?>
<cep
    xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance'
    xmlns='http://camitk.imag.fr/cepcoreschema'
    xsi:schemaLocation='http://camitk.imag.fr/cepcoreschema ../Cep.xsd'>
    <name>Example Of Tinman With Components</name>
    <contact>
        <email>Celine.Fouard@imag.fr</email>
    </contact>
    <description>Tinman Test file containing several kinds of Component Extensions.</description>
    <copyright><![CDATA[/* ****************************************************************************
$USERDEF_LICENCE_BEGIN$
CamiTK - Computer Assisted Medical Intervention ToolKit
(c) 2001-2016 Univ. Grenoble Alpes, CNRS, TIMC-IMAG UMR 5525 (GMCAO)
        
Visit http://camitk.imag.fr for more information
        
This file is part of CamiTK.
        
$CEP_NAME$ is under the following licence:
A specific private licence, just to test Tinman licence managing
        
$USERDEF_LICENCE_END$
*************************************************************************** */
    ]]></copyright>
    
    <componentExtensions>
        <componentExtension>
            <name>Example with no file suffix</name>
            <description>
                This component tests the ability of Tinman to create and make 
                compilable and executable component extensions which do not
                handle any file suffix (components should then be created from actions).
            </description>
            <components>
                <component>
                    <name>my own cube</name>
                    <description>A Mesh Cube</description>
                    <representation>Mesh</representation>
                    <properties>
                        <parameter name="size"  type="int" defaultValue="5" description="An integer."/>
                        <parameter name="color" type="QColor" description="A QColor."/>
                    </properties>
                </component>
            </components>
        </componentExtension>
        <componentExtension>
            <name>Example with one file suffix</name>
            <description>Simple Mixed component extension handling .example files</description>
            <components>
                <component>
                    <name>Tinman Example File</name>
                    <description>
                        Simple component handling .example files with no representation.
                    </description>
                    <representation>None</representation>
                    <fileSuffix>example</fileSuffix>
                </component>
            </components>
        </componentExtension>

        <componentExtension>
            <name>Example with several file suffixes</name>
            <description>Simple Mixed component extension handling .example files</description>
            <components>
                <component>
                    <name>Tinman A File</name>
                    <description>
                        Simple component handling .a files with an image representation.
                    </description>
                    <representation>Image</representation>
                    <properties>
                        <parameter name="aa"  type="int" defaultValue="2" description="An integer."/>
                    </properties>
                    <fileSuffix>a</fileSuffix>
                </component>
                <component>
                    <name>Tinman B File</name>
                    <description>
                        Simple component handling .b files with a Mesh representation.
                    </description>
                    <representation>Image</representation>
                    <properties>
                        <parameter name="bb"  type="bool" description="A boolean."/>
                    </properties>
                    <fileSuffix>b</fileSuffix>
                </component>
                <component>
                    <name>Tinman C File</name>
                    <description>
                        Simple component handling .c files with no representation.
                    </description>
                    <representation>None</representation>
                    <properties>
                        <parameter name="cc"  type="double" defaultValue="3.8" description="A double."/>
                    </properties>
                    <fileSuffix>c</fileSuffix>
                </component>
            </components>
        </componentExtension>
    </componentExtensions>
</cep>
EOF


# ---------------------- actionsExamplesLicence.xml ----------------------
# Example taken from distributed source ./sdk/applications/cepgenerator/testdata/actionsExamplesLicence.xml
cat <<EOF > actionsExamplesLicence.xml
<?xml version="1.0" encoding="UTF-8"?>
<cep    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns="http://camitk.imag.fr/cepcoreschema"
        xsi:schemaLocation="http://camitk.imag.fr/cepcoreschema ../cep.xsd">
    <name>CEP created by Wizard</name>
    <contact>
        <email>Celine.Fouard@imag.fr</email> 
    </contact>
    <description>Example of empty CEP</description>
    <copyright><![CDATA[/*****************************************************************************
$USERDEF_LICENCE_BEGIN$
CamiTK - Computer Assisted Medical Intervention ToolKit
(c) 2001-2016 Univ. Grenoble Alpes, CNRS, TIMC-IMAG UMR 5525 (GMCAO)
        
Visit http://camitk.imag.fr for more information
        
This file is part of CamiTK.
        
$CEP_NAME$ is under the following licence:
A specific private licence
$USERDEF_LICENCE_END$
****************************************************************************/
    ]]></copyright>
    <actionExtensions>
        <actionExtension>
            <name>Wizard created image actions</name>
            <description>This action extension proposes several actions on image components</description>
            <!-- <directoryName>imagewizardactions</directoryName> -->
            <actions>
                <action>
                    <name>Example of Image Action</name>
                    <description>Example of simple action on image component.</description>
                    <component>ImageComponent</component>
                    <classification>
                        <family>CreatedByWizard</family>
                        <tag>Image</tag>
                    </classification>
                    <parameters>
                        <parameter name="alpha" type="int" description="An integer."/>
                        <parameter name="beta"  type="bool" description="A boolean."/>
                    </parameters>
                </action>
                <action>
                    <name>Example of Image ITK Filter</name>
                    <description>Example of an itk image action.</description>
                    <component>ImageComponent</component>
                    <classification>
                        <family>CreatedByWizard</family>
                        <tag>Image</tag>
                        <tag>itk</tag>
                        <itkFilter outputType="Same as Input"/>
                    </classification>
                    <parameters>
                        <parameter name="gamma" type="QDate" description="A QDate."/>
                        <parameter name="phi"  type="double" description="A double."/>
                    </parameters>
                </action>
            </actions>
            <dependencies>
                <dependency type="library" name="itk"/>
            </dependencies>
        </actionExtension>
        <actionExtension>
            <name>Wizard created mesh actions</name>
            <description>This action extension proposes an action on mesh components</description>
            <actions>
                <action>
                    <name>Example of Mesh Action</name>
                    <description>Example of action on a mesh.</description>
                    <component>MeshComponent</component>
                    <classification>
                        <family>CreatedByWizard</family>
                        <tag>Mesh</tag>
                        <tag>Example</tag>
                    </classification>
                    <parameters>
                        <parameter name="A long parameter name" type="QColor" description="A QColor."/>
                    </parameters>
                </action>
            </actions>
        </actionExtension>
    </actionExtensions>
    
</cep>
EOF


# ---------------------- actionsExamplesNoLicence.xml ----------------------
# Example taken from distributed source ./sdk/applications/cepgenerator/testdata/actionsExamplesNoLicence.xml
cat <<EOF > actionsExamplesNoLicence.xml
<?xml version="1.0" encoding="UTF-8"?>
<cep xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns="http://camitk.imag.fr/cepcoreschema"
    xsi:schemaLocation="http://camitk.imag.fr/cepcoreschema ../cep.xsd">
    <name>CEP created by Wizard</name>
    <contact>
        <email>Celine.Fouard@imag.fr</email> 
    </contact>
    <description>Example of empty CEP</description>
    <actionExtensions>
        <actionExtension>
            <name>Wizard created image actions</name>
            <description>This action extension proposes several actions on image components</description>
            <!-- <directoryName>imagewizardactions</directoryName> -->
            <actions>
                <action>
                    <name>Example of Image Action</name>
                    <description>Example of simple action on image component.</description>
                    <component>ImageComponent</component>
                    <classification>
                        <family>CreatedByWizard</family>
                        <tag>Image</tag>
                    </classification>
                    <parameters>
                        <parameter name="alpha" type="int" description="An integer."/>
                        <parameter name="beta"  type="bool" description="A boolean parameter."/>
                    </parameters>
                </action>
                <action>
                    <name>Example of Image ITK Filter</name>
                    <description>Example of an itk image action.</description>
                    <component>ImageComponent</component>
                    <classification>
                        <family>CreatedByWizard</family>
                        <tag>Image</tag>
                        <tag>itk</tag>
                        <itkFilter outputType="Same as Input"/>
                    </classification>
                    <parameters>
                        <parameter name="gamma" type="QDate" description="Using class QDate as parameter type"/>
                        <parameter name="phi"  type="double" description="Phi is &lt;i>another parameter&lt;/i>" />
                    </parameters>
                </action>
            </actions>
            <dependencies>
                <dependency type="library" name="itk"/>
            </dependencies>
        </actionExtension>
        <actionExtension>
            <name>Wizard created mesh actions</name>
            <description>This action extension proposes an action on mesh components</description>
            <actions>
                <action>
                    <name>Example of Mesh Action</name>
                    <description>Example of action on a mesh.</description>
                    <component>MeshComponent</component>
                    <classification>
                        <family>CreatedByWizard</family>
                        <tag>Mesh</tag>
                        <tag>Example</tag>
                    </classification>
                    <parameters>
                        <parameter name="A long parameter name" type="QColor" description="This is a very long description&lt;br/>(for a very long parameter name)"/>
                    </parameters>
                </action>
            </actions>
        </actionExtension>
    </actionExtensions>
    
</cep>
EOF


# ---------------------- actionAndComponent.xml ----------------------
# Example taken from distributed source ./sdk/applications/cepgenerator/testdata/actionAndComponent.xml
cat <<EOF > actionAndComponent.xml
<?xml version="1.0" encoding="UTF-8" standalone="no" ?>
<cep xmlns="http://camitk.imag.fr/cepcoreschema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://camitk.imag.fr/cepcoreschema Cep.xsd">
  <name>Yet another example of CEP</name>
  <contact>
    <email>Emmanuel.Promayon@imag.fr</email>
  </contact>
  <description>This CEP contains a new type of component and an action that can do something with it.
This test the link between an action and a component defined in the same CEP.</description>
  <actionExtensions>
    <actionExtension>
      <name>Another Example Of An Action Extension</name>
      <description>This extension description is really useless.</description>
      <actions>
        <action>
          <name>DoSomethingOnSpecific</name>
          <description>This description is void.</description>
          <component>SpecificMeshBasedComponent</component>
          <classification>
            <family>Testing CepGenerator</family>
          </classification>
          <parameters>
            <parameter defaultValue="100.0" description="Testing double" editable="true" name="testDouble" type="double" unit=""/>
          </parameters>
        </action>
      </actions>
      <dependencies>
        <dependency name="specificcomponent" type="component"/>
      </dependencies>
    </actionExtension>
  </actionExtensions>
  <componentExtensions>
    <componentExtension>
      <name>Specific component</name>
      <description>This extension description a new / specific component</description>
      <components>
        <component>
          <name>SpecificMeshBasedComponent</name>
          <description>My description is useless...</description>
          <representation>Mesh</representation>
          <properties>
            <parameter defaultValue="false" description="Testing bools" editable="true" name="testBool" type="bool" unit=""/>
            <parameter defaultValue="QColor(255, 255, 255, 255)" description="Testing color" editable="true" name="testColor" type="QColor" unit=""/>
            <parameter defaultValue="QVector3D(0.0, 0.0, 0.0)" description="test 3D vector" editable="true" name="testVector3D" type="QVector3D" unit=""/>
          </properties>
          <fileSuffix>specific</fileSuffix>
        </component>
      </components>
    </componentExtension>
  </componentExtensions>
</cep>
EOF

# ---------------------- empty.xml ----------------------
# Example taken from distributed source ./sdk/applications/cepgenerator/testdata/empty.xml
cat <<EOF > empty.xml
<?xml version="1.0" encoding="UTF-8"?>
<cep xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns="http://camitk.imag.fr/cepcoreschema"
        xsi:schemaLocation="http://camitk.imag.fr/cepcoreschema ../cep.xsd">
    <name>empty</name>
    <contact>
        <email>Celine.Fouard@imag.fr</email> 
        <email>Emmanuel.Promayon@imag.fr</email>
    </contact>
    <description>Example of empty CEP</description>    
</cep>
EOF

# ---------------------- generateConfigureAndMake ----------------------
generateConfigureAndMake() {
  # generate
  testDirName=$(basename $1 .xml)
  echo "========== configure and make $testDirName =========="
  cd $workingDir
  rm -rf $testDirName
  mkdir $testDirName
  camitk-cepgenerator -f $1 -d $testDirName > ./wizard-$testDirName
  echo "===== wizard-$testDirName ====="
  cat ./wizard-$testDirName
  cd $testDirName
  # get the created dir name
  srcDirName=$(ls)
  # configure
  mkdir build
  cd build
  xvfb-run --auto-servernum --server-num=1 cmake $CMAKE_OPTIONS ../$srcDirName > ../cmake-log 2> ../cmake-error
  echo "===== cmake-log ====="
  cat ../cmake-log
  echo "===== cmake-error ====="  
  cat ../cmake-error
  # build (parallel)
  make -j9 > ../make-log 2> ../make-error
  echo "===== make-log ====="
  cat ../make-log
  echo "===== make-error ====="  
  cat ../make-error
}

# ---------------------- testcepfile ----------------------
# @param xmlfile
# @param expected number of created extensions
testcepfile() {
  generateConfigureAndMake $1
  expectedValue="$2"

  echo "========== check $1 =========="
  
  # check if everything is compiled and can be loaded
  value=$(getWorkingDirExtensionCount)
  echo "$checkValueId- Check Number of extensions for $1: $value"
  echo "$(xvfb-run --auto-servernum --server-num=1 camitk-config --config | grep "\[W\]")"
  if [ "$value" -ne "$expectedValue" ]; then
    echo "Error: unexpected number of extensions installed in the working directory ($value != $expectedValue)"
    exitStatus=$checkValueId
  else
    echo "OK"
  fi
  # increase id
  checkValueId=$((checkValueId+1))
}

# --------------------------------------------------------------------------
#
# All tests are here
#
# --------------------------------------------------------------------------

# --------------------------------------------------------------------------

# testcepfile cep.xml nrOfExcpectedNewExtensions
testcepfile exampleComponents.xml 2
testcepfile actionsExamplesLicence.xml 2
testcepfile actionsExamplesNoLicence.xml 2
testcepfile actionAndComponent.xml 2
testcepfile empty.xml 0

exit $exitStatus