Add basic Yangman robot test 41/50141/27
authorDaša Šimková <dasa.simkova@pantheon.sk>
Fri, 24 Mar 2017 11:24:38 +0000 (12:24 +0100)
committerVratko Polák <vrpolak@cisco.com>
Wed, 12 Apr 2017 14:19:42 +0000 (14:19 +0000)
- add Yangman basic test
- add Dlux testing keywords
- add Yangman testing keywords
- add Yangman gui variables
- add Yangman testplan
- browser chrome

Change-Id: Ide1e593a972887df942a30dfbca115989961c9ee
Signed-off-by: Daša Šimková <dasa.simkova@pantheon.tech>
Signed-off-by: Daša Šimková <dasa.simkova@pantheon.sk>
Signed-off-by: Dasa Simkova -X (dsimkova - PANTHEON TECHNOLOGIES at Cisco) <dsimkova@cisco.com>
csit/libraries/GUIKeywords.robot [new file with mode: 0644]
csit/libraries/YangmanKeywords.robot [new file with mode: 0644]
csit/suites/dluxapps/yangman/502__yangman.robot [new file with mode: 0644]
csit/testplans/dluxapps-yangman.txt [new file with mode: 0644]
csit/variables/YangmanGUIVariables.robot [new file with mode: 0644]

diff --git a/csit/libraries/GUIKeywords.robot b/csit/libraries/GUIKeywords.robot
new file mode 100644 (file)
index 0000000..591e6cb
--- /dev/null
@@ -0,0 +1,202 @@
+*** Settings ***
+Documentation     A resource file containing all global
+...               elements (Variables, keywords) to help
+...               DLUX csit testing.
+Library           OperatingSystem
+Library           Process
+Library           Selenium2Library    timeout=30    implicit_wait=30    run_on_failure=Selenium2Library.Log Source
+Resource          ../variables/Variables.robot
+Resource          Utils.robot
+
+*** Variables ***
+${BROWSER}        chrome
+${BASE_URL}       http://${ODL_SYSTEM_IP}:${RESTCONFPORT}/index.html
+${LOGIN_URL}      ${BASE_URL}#/login
+${XVFB_PORT}      99
+${LOGGED_URL}     ${BASE_URL}#/topology
+${LOGIN_USERNAME}    admin
+${LOGIN_PASSWORD}    admin
+${INVALID_USER}    invaliduser
+${INVALID_PWD}    invalidpwd
+# Login page
+${OPENDAYLIGHT_IMAGE}    //img[@alt='OpenDayLight']
+${LOGIN_USERNAME_INPUT_FIELD}    //form/fieldset/div/input[@name='username']
+${LOGIN_PASSWORD_INPUT_FIELD}    //form/fieldset/div[2]/input[@name='password']
+${REMEMBER_ME_CHECKBOX}    //div[@class="checkbox"]
+${LOGIN_BUTTON}    //fieldset/button
+${PLEASE_SIGN_IN_PANEL}    //div/h3[contains(text(),"${PLEASE_SIGN_IN_MSG}")]
+${PLEASE_SIGN_IN_MSG}    Please Sign In
+${LOGIN_ERROR_MSG}    Unable to login
+# DLUX Home page
+${TOPOLOGY_SUBMENU}    //a[@href='#/topology']
+${NODES_SUBMENU}    //a[@href='#/node/index')]
+${YANG_UI_SUBMENU}    //a[@href='#/yangui/index']
+${YANG_VISUALIZER_SUBMENU}    //a[@href='#/yangvisualizer/index']
+${YANGMAN_SUBMENU}    //a[@href='#/yangman/index']
+# Topology Submenu
+${TOPOLOGY_SUBMENU_URL}    ${BASE_URL}#/topology
+${RELOAD_BUTTON}    //button[@ng-click='createTopology()']
+${CONTROLS_TEXT}    //div[@class="col-md-2"]/h3
+# Nodes Submenu
+${NODES_SUBMENU_URL}    ${BASE_URL}#/node/index
+# Yang UI Submenu
+${YANG_UI_SUBMENU_URL}    ${BASE_URL}#/yangui/index
+# Yang Visualizer Submenu
+${YANG_VISUALIZER_SUBMENU_URL}    ${BASE_URL}#/yangvisualizer/index
+# Yangman Submenu
+${YANGMAN_SUBMENU_URL}    ${BASE_URL}#/yangman/index
+# Failback variables
+${USE_XVFB}       True
+${BROWSER_NAME}    phantomjs-1.9.8-linux-x86_64
+${BROWSER_EXT}    tar.bz2
+${BROWSER_FILE_NAME}    ${BROWSER_NAME}.${BROWSER_EXT}
+${BROWSER_URL}    https://bitbucket.org/ariya/phantomjs/downloads/${BROWSER_FILE_NAME}
+${BROWSER_PATH_EXECUTABLE}    ${BROWSER_NAME}/bin/phantomjs
+
+*** Keywords ***
+Check If Phantom Is Downloaded
+    [Documentation]    Checks if a folder named 'phantomjs' is found in the robot script directory.
+    ...    Checks if PhantomJS already been downloaded. This check is done by listing the directory and
+    ...    verification if there is one containing the word 'phantomjs'. Result is that the PhantomJS
+    ...    compressed file is downloaded and uncompressed locally related to the path of the running script.
+    ${installed}=    OperatingSystem.Run    ls -d */ | grep -m 1 phantomjs
+    [Return]    ${installed}
+
+Download PhantomJS
+    [Documentation]    Downloads and uncompress the headless browser PhantomJS.
+    Process.Run Process    wget    ${BROWSER_URL}
+    Process.Run Process    tar    -jxf    ${BROWSER_FILE_NAME}
+
+Get Headless Browser Path
+    [Documentation]    Returns the path of the executable headless browser.
+    ${is_downloaded}=    Check If Phantom Is Downloaded
+    BuiltIn.Run Keyword If    "${is_downloaded}"=="${EMPTY}"    Download PhantomJS
+    ${path}=    BuiltIn.Set Variable    ${EXECDIR}/${BROWSER_PATH_EXECUTABLE}
+    [Return]    ${path}
+
+Open Headless Browser
+    [Arguments]    ${url}
+    [Documentation]    Failback browser, download and use the WebKit headless browser PhantomJS.
+    BuiltIn.Log    \n Using failback browser    console=yes
+    BuiltIn.Set Global Variable    ${USE_XVFB}    False
+    ${executable_path}=    Get Headless Browser Path
+    Selenium2Library.Create Webdriver    PhantomJS    executable_path=${executable_path}
+    Selenium2Library.Go To    ${url}
+
+Set Display Port
+    [Arguments]    ${port}=${XVFB_PORT}
+    [Documentation]    Sets the environment variable used by xvfb and the browser.
+    OperatingSystem.Set Environment Variable    DISPLAY    :${port}
+
+Open Virtual Display
+    [Documentation]    Starts xvfb, a kind-ish x-server on RAM.
+    Process.Start Process    Xvfb    :${XVFB_PORT}    -ac    -screen    0    1280x1024x16
+    ...    alias=xvfb
+    ${display}=    OperatingSystem.Get Environment Variable    DISPLAY    ${EMPTY}
+    BuiltIn.Run Keyword Unless    "${display}"==":${XVFB_PORT}"    Set Display Port
+
+Close DLUX And Terminate XVFB Process If Running
+    [Documentation]    Closes all browser instances and terminates Xvfb if the process is running.
+    Selenium2Library.Close All Browsers
+    BuiltIn.Run Keyword If    ${USE_XVFB}    Terminate Process    xvfb
+
+Launch DLUX
+    [Documentation]    Launches with a delay to let the page load. If it cannot run the default browser, it will download
+    ...    PhantomJS and use it instead. Steps of Launch DLUX are the following:
+    ...    1. Trying to start Xvfb and load the browser defined by the variable ${BROWSER}.
+    ...    2. If failed to start one of those task:
+    ...    2.1 Download and extract PhantomJS if not already done
+    ...    2.2 Create a custom PhantomJS webdriver based on the downloaded one
+    ...    3. Go to DLUX login URL and wait until the HTML page contains a specific element.
+    ${status}=    BuiltIn.Run Keyword And Return Status    Run Keywords    Open Virtual Display
+    ...    AND    Selenium2Library.Open Browser    ${LOGIN_URL}    ${BROWSER}
+    BuiltIn.Run Keyword Unless    ${status}    Open Headless Browser    ${LOGIN_URL}
+    Selenium2Library.Wait Until Page Contains Element    css=div.container
+
+Open DLUX Login Page
+    [Arguments]    ${LOGIN URL}
+    [Documentation]    Loads DLUX login page.
+    Selenium2Library.Open Browser    ${LOGIN_URL}    ${BROWSER}
+    Selenium2Library.Maximize Browser Window
+    Selenium2Library.Wait Until Page Contains Element    ${PLEASE_SIGN_IN_PANEL}
+
+Verify Elements Of DLUX Login Page
+    [Documentation]    Verifies elements presence in DLUX login page.
+    Selenium2Library.Page Should Contain Image    ${OPENDAYLIGHT_IMAGE}
+    Selenium2Library.Page Should Contain Element    ${LOGIN_USERNAME_INPUT_FIELD}
+    Selenium2Library.Page Should Contain Element    ${LOGIN_PASSWORD_INPUT_FIELD}
+    Selenium2Library.Page Should Contain Element    ${REMEMBER_ME_CHECKBOX}
+    Selenium2Library.Page Should Contain Element    ${LOGIN_BUTTON}
+
+Log In To DLUX
+    [Arguments]    ${username}    ${password}
+    [Documentation]    Inserts username and password and logs in DLUX.
+    Selenium2Library.Focus    ${LOGIN_USERNAME_INPUT_FIELD}
+    Selenium2Library.Input Text    ${LOGIN_USERNAME_INPUT_FIELD}    ${username}
+    Selenium2Library.Focus    ${LOGIN_PASSWORD_INPUT_FIELD}
+    Selenium2Library.Input Text    ${LOGIN_PASSWORD_INPUT_FIELD}    ${password}
+    Focus And Click Element    ${LOGIN_BUTTON}
+
+Log In To DLUX With Invalid Credentials
+    [Arguments]    ${username}    ${password}
+    [Documentation]    Tries to log in to DLUX with invalid credentials and verifies occurence of the error message.
+    Selenium2Library.Focus    ${LOGIN_USERNAME_INPUT_FIELD}
+    Selenium2Library.Input Text    ${LOGIN_USERNAME_INPUT_FIELD}    ${username}
+    Selenium2Library.Focus    ${LOGIN_PASSWORD_INPUT_FIELD}
+    Selenium2Library.Input Text    ${LOGIN_PASSWORD_INPUT_FIELD}    ${password}
+    Focus And Click Element    ${LOGIN_BUTTON}
+    Selenium2Library.Location Should Be    ${LOGIN_URL}
+    Selenium2Library.Wait Until Page Contains    ${LOGIN_ERROR_MSG}
+
+Open Or Launch DLUX
+    [Documentation]    Tries to open Dlux login page. If it fails, then launches Dlux using xvfb or headless browser.
+    ${status}=    BuiltIn.Run Keyword And Return Status    Open DLUX Login Page    ${LOGIN_URL}
+    BuiltIn.Run Keyword If    "${status}"=="False"    Launch DLUX
+    Verify Elements Of DLUX Login Page
+
+Open Or Launch DLUX Page And Log In To DLUX
+    [Documentation]    Opens or launches Dlux and then logs in to Dlux.
+    Open Or Launch DLUX
+    Log In To DLUX    ${LOGIN_USERNAME}    ${LOGIN_PASSWORD}
+
+Navigate To URL
+    [Arguments]    ${url}
+    [Documentation]    Goes to the defined URL provided in an argument.
+    ${status}=    BuiltIn.Run Keyword And Return Status    Selenium2Library.Location Should Be    ${url}
+    BuiltIn.Run Keyword Unless    ${status}    Selenium2Library.Go To    ${url}
+
+Focus And Click Element
+    [Arguments]    ${element}
+    [Documentation]    Clicks the element with previous element visibility check and element focus.
+    Selenium2Library.Wait Until Element Is Visible    ${element}
+    Selenium2Library.Focus    ${element}
+    Selenium2Library.Mouse Over    ${element}
+    Selenium2Library.Click Element    ${element}
+
+Mouse Down And Mouse Up Click Element
+    [Arguments]    ${element}
+    [Documentation]    Clicks the element by imitating mouse left button click down and click up.
+    Selenium2Library.Wait Until Page Contains Element    ${element}
+    Selenium2Library.Focus    ${element}
+    Selenium2Library.Mouse Over    ${element}
+    Selenium2Library.Mouse Down    ${element}
+    Selenium2Library.Mouse Up    ${element}
+
+Page Should Contain Element With Wait
+    [Arguments]    ${element}
+    [Documentation]    Similar to Selenium2Library.Wait Until Page Contains Element but returns web page source code when fails.
+    BuiltIn.Wait Until Keyword Succeeds    1 min    5 sec    Selenium2Library.Page Should Contain Element    ${element}
+
+Helper Click
+    [Arguments]    ${element_to_be_clicked}    ${element_to_be_checked}
+    [Documentation]    Clicks the ${element_to_be_clicked} and verifies that page contains ${element_to_be_checked}.
+    Selenium2Library.Focus    ${element_to_be_clicked}
+    Selenium2Library.Click Element    ${element_to_be_clicked}
+    Selenium2Library.Wait Until Page Contains Element    ${element_to_be_checked}
+
+Patient Click
+    [Arguments]    ${element_to_be_clicked}    ${element_to_be_checked}
+    [Documentation]    Combines clicking ${element_to_be_clicked} and checking that ${element_to_be_checked} is visible with
+    ...    BuiltIn.Wait Until Keyword Succeeds keyword in order to secure reliable execution of Selenium2Library.Click Element
+    ...    keyword in AngularJS webapp.
+    BuiltIn.Wait Until Keyword Succeeds    1 min    5 sec    Helper Click    ${element_to_be_clicked}    ${element_to_be_checked}
diff --git a/csit/libraries/YangmanKeywords.robot b/csit/libraries/YangmanKeywords.robot
new file mode 100644 (file)
index 0000000..f337405
--- /dev/null
@@ -0,0 +1,361 @@
+*** Settings ***
+Documentation     A resource file containing all global keywords to help
+...               Yangman GUI and functional testing.
+Library           Collections
+Library           Selenium2Library    timeout=30    implicit_wait=30    run_on_failure=Selenium2Library.Log Source
+Resource          ../variables/Variables.robot
+Resource          GUIKeywords.robot
+Resource          ../variables/YangmanGUIVariables.robot
+
+*** Keywords ***
+Open DLUX And Login And Navigate To Yangman URL
+    [Documentation]    Launches DLUX page using PhantomJS, or Xvfb, or real browser and navigates to yangman url.
+    GUIKeywords.Open Or Launch DLUX Page And Log In To DLUX
+    GUIKeywords.Navigate To URL    ${YANGMAN_SUBMENU_URL}
+
+Return List Of Operation IDs
+    [Documentation]    Returns list of IDs of Get, Put, Post and Delete options in expanded operation select menu.
+    ${list}=    BuiltIn.Create List    ${GET_OPTION}    ${PUT_OPTION}    ${POST_OPTION}    ${DELETE_OPTION}
+    [Return]    ${list}
+
+Return List Of Operation Names
+    [Documentation]    Returns list of operations names.
+    ${list}=    BuiltIn.Create List    GET    PUT    POST    DELETE
+    [Return]    ${list}
+
+Expand Operation Select Menu
+    [Documentation]    Clicks operation select menu to expand it.
+    GUIKeywords.Patient Click    ${OPERATION_SELECT_INPUT}    ${OPERATION_SELECT_MENU_EXPANDED}
+
+Exit Opened Application Dialog
+    [Documentation]    Closes opened/ expanded dialogs/ menus by clicking the backdrop.
+    Selenium2Library.Click Element    ${SELECT_BACKDROP}
+
+Select Operation
+    [Arguments]    ${operation_id}
+    [Documentation]    Selects chosen operation from expanded operation select menu.
+    ${status}=    BuiltIn.Run Keyword And Return Status    GUIKeywords.Page Should Contain Element With Wait    ${OPERATION_SELECT_MENU_EXPANDED}
+    BuiltIn.Run Keyword If    "${status}"=="False"    Expand Operation Select Menu    ${OPERATION_SELECT_INPUT}
+    GUIKeywords.Focus And Click Element    ${operation_id}
+
+Verify Selected Operation Is Displayed
+    [Arguments]    ${selected_operation_name}
+    [Documentation]    Verifies that the selected operation is now displayed in collapsed operation select menu.
+    ${selected_operation_xpath}=    BuiltIn.Set Variable    ${OPERATION_SELECT_INPUT}//span/div[contains(text(), "${selected_operation_name}")]
+    GUIKeywords.Page Should Contain Element With Wait    ${selected_operation_xpath}
+
+Select Operation And Verify Operation Has Been Selected
+    [Arguments]    ${operation_id}    ${selected_operation_name}
+    [Documentation]    Selects chosen operation from expanded operation select menu and verifies the operation has been selected.
+    ${status}=    BuiltIn.Run Keyword And Return Status    GUIKeywords.Page Should Contain Element With Wait    ${OPERATION_SELECT_MENU_EXPANDED}
+    BuiltIn.Run Keyword If    "${status}"=="False"    Expand Operation Select Menu    ${OPERATION_SELECT_INPUT}
+    ${selected_operation_xpath}=    BuiltIn.Set Variable    ${OPERATION_SELECT_INPUT}//span/div[contains(text(), "${selected_operation_name}")]
+    GUIKeywords.Patient Click    ${operation_id}    ${selected_operation_xpath}
+
+Expand Operation Select Menu And Select Operation
+    [Arguments]    ${operation_id}    ${selected_operation_name}
+    [Documentation]    Expands operation select menu and select operation provided as an argument.
+    Expand Operation Select Menu
+    Select Operation And Verify Operation Has Been Selected    ${operation_id}    ${selected_operation_name}
+
+Verify Yangman Home Page Elements
+    [Documentation]    Verifies presence of Yangman home page elements.
+    Selenium2Library.Wait Until Page Contains Element    ${YANGMAN_LOGO}
+    Selenium2Library.Log Location
+    Modules Tab Is Selected
+    Selenium2Library.Page Should Contain Element    ${TOGGLE_MENU_BUTTON}
+    Selenium2Library.Page Should Contain Element    ${LOGOUT_BUTTON}
+    Verify Selected Operation Is Displayed    GET
+    Selenium2Library.Page Should Contain Element    ${REQUEST_URL_INPUT}
+    Selenium2Library.Page Should Contain Element    ${SEND_BUTTON}
+    Selenium2Library.Page Should Contain Element    ${SAVE_BUTTON}
+    Selenium2Library.Page Should Contain Element    ${PARAMETERS_BUTTON}
+    Selenium2Library.Page Should Contain Element    ${FORM_RADIOBUTTON_UNSELECTED}
+    Selenium2Library.Page Should Contain Element    ${JSON_RADIOBUTTON_SELECTED}
+    Selenium2Library.Page Should Contain Element    ${SHOW_SENT_DATA_CHECKBOX_UNSELECTED}
+    Selenium2Library.Page Should Contain Element    ${SHOW_RECEIVED_DATA_CHECKBOX_SELECTED}
+    Selenium2Library.Page Should Contain Element    ${RECEIVED_DATA_CODE_MIRROR_DISPLAYED}
+    Selenium2Library.Page Should Contain Element    ${RECEIVED_DATA_ENLARGE_FONT_SIZE_BUTTON}
+    Selenium2Library.Page Should Contain Element    ${RECEIVED_DATA_REDUCE_FONT_SIZE_BUTTON}
+    Selenium2Library.Page Should Not Contain Element    ${SENT_DATA_CODE_MIRROR_DISPLAYED}
+
+Select Form View
+    [Documentation]    Click Form radiobutton to display form view.
+    ${status}=    BuiltIn.Run Keyword And Return Status    Selenium2Library.Page Should Contain Element    ${FORM_RADIOBUTTON_SELECTED}
+    BuiltIn.Run Keyword If    "${status}"=="False"    GUIKeywords.Patient Click    ${FORM_RADIOBUTTON_UNSELECTED}    ${FORM_RADIOBUTTON_SELECTED}
+
+Select Json View
+    [Documentation]    Click Json radiobutton to display json view.
+    ${status}=    BuiltIn.Run Keyword And Return Status    Selenium2Library.Page Should Contain Element    ${JSON_RADIOBUTTON_SELECTED}
+    BuiltIn.Run Keyword If    "${status}"=="False"    GUIKeywords.Patient Click    ${JSON_RADIOBUTTON_UNSELECTED}    ${JSON_RADIOBUTTON_SELECTED}
+
+Modules Tab Is Selected
+    [Documentation]    Verifies that module tab is selected and history and collection tabs are unselected.
+    Selenium2Library.Page Should Contain Element    ${MODULES_TAB_SELECTED}
+    Selenium2Library.Page Should Contain Element    ${MODULE_SEARCH_INPUT}
+    Selenium2Library.Page Should Contain Element    ${HISTORY_TAB_UNSELECTED}
+    Selenium2Library.Page Should Contain Element    ${COLLECTIONS_TAB_UNSELECTED}
+
+Return Number Of Modules Loaded
+    [Arguments]    ${module_xpath}
+    [Documentation]    Returns number of modules loaded in Modules tab.
+    ${number_of_modules}=    Selenium2Library.Get Matching Xpath Count    ${module_xpath}
+    [Return]    ${number_of_modules}
+
+Verify Any Module Is Loaded
+    [Documentation]    Verifies that at least one module has been loaded in Modules tab.
+    ${number_of__modules_loaded}=    Return Number Of Modules Loaded    ${MODULE_LIST_ITEM}
+    BuiltIn.Should Be True    ${number_of_modules_loaded}>0
+
+Return Module List Indexed Module
+    [Arguments]    ${index}
+    [Documentation]    Returns indexed Xpath of the module. ${index} is a number.
+    ${module_index}=    BuiltIn.Set Variable    ${MODULE_ID_LABEL}${index}
+    ${module_list_item_indexed}=    BuiltIn.Set Variable    ${MODULE_TAB_CONTENT}//md-list-item[@id="${module_index}"]//div[@class="pointer title layout-align-center-center layout-row"]
+    [Return]    ${module_list_item_indexed}
+
+Return Indexed Module Operations Label
+    [Arguments]    ${index}
+    [Documentation]    Returns Xpath of the indexed module's operations item in Modules tab.
+    ${module_list_item_indexed}=    Return Module List Indexed Module    ${index}
+    ${indexed_module_operations_label}=    BuiltIn.Set Variable    ${module_list_item_indexed}//following-sibling::md-list[@aria-hidden="false"]//p[contains(., "${OPERATIONS_LABEL}")]
+    [Return]    ${indexed_module_operations_label}
+
+Return Indexed Module Operational Label
+    [Arguments]    ${index}
+    [Documentation]    Returns Xpath of the indexed module`s operational in Modules tab.
+    ${module_list_item_indexed}=    Return Module List Indexed Module    ${index}
+    ${indexed_module_operational_label}=    BuiltIn.Set Variable    ${module_list_item_indexed}//following-sibling::md-list[@aria-hidden="false"]//p[contains(., "${OPERATIONAL_LABEL}")]
+    [Return]    ${indexed_module_operational_label}
+
+Return Indexed Module Config Label
+    [Arguments]    ${index}
+    [Documentation]    Returns Xpath of the indexed module`s config in Modules tab.
+    ${module_list_item_indexed}=    Return Module List Indexed Module    ${index}
+    ${indexed_module_config_label}=    BuiltIn.Set Variable    ${module_list_item_indexed}//following-sibling::md-list[@aria-hidden="false"]//p[contains(., "${CONFIG_LABEL}")]
+    [Return]    ${indexed_module_config_label}
+
+Click Indexed Module Operations To Load Module Detail Operations Tab
+    [Arguments]    ${index}
+    [Documentation]    Clicks indexed module`s operations to load module detail operations tab.
+    ${indexed_module_operations}=    Return Indexed Module Operations Label    ${index}
+    Selenium2Library.Wait Until Page Contains Element    ${indexed_module_operations}
+    GUIKeywords.Focus And Click Element    ${indexed_module_operations}
+    Selenium2Library.Wait Until Page Contains Element    ${MODULE_DETAIL_OPERATIONS_TAB_SELECTED}
+
+Click Indexed Module Operational To Load Module Detail Operational Tab
+    [Arguments]    ${index}
+    [Documentation]    Clicks indexed module`s operational to load module detail operational tab.
+    ${indexed_module_operational}=    Return Indexed Module Operational Label    ${index}
+    Selenium2Library.Wait Until Page Contains Element    ${indexed_module_operational}
+    GUIKeywords.Focus And Click Element    ${indexed_module_operational}
+    Selenium2Library.Wait Until Page Contains Element    ${MODULE_DETAIL_OPERATIONAL_TAB_SELECTED}
+
+Click Indexed Module Config To Load Module Detail Config Tab
+    [Arguments]    ${index}
+    [Documentation]    Clicks indexed module`s config to load module detail config tab.
+    ${indexed_module_config}=    Return Indexed Module Config Label    ${index}
+    Selenium2Library.Wait Until Page Contains Element    ${indexed_module_config}
+    GUIKeywords.Focus And Click Element    ${indexed_module_config}
+    Selenium2Library.Wait Until Page Contains Element    ${MODULE_DETAIL_CONFIG_TAB_SELECTED}
+
+Return Module ID Index From Module Name
+    [Arguments]    ${module_name}
+    [Documentation]    Returns number - module id index from module name.
+    ${testing_module_xpath}=    BuiltIn.Set Variable    ${MODULE_TAB_CONTENT}//p[contains(., "${module_name}")]//ancestor::md-list-item[contains(@id, "${MODULE_ID_LABEL}")]
+    ${module_id}=    Selenium2Library.Get Element Attribute    ${testing_module_xpath}@id
+    ${module_id_index}=    String.Fetch From Right    ${module_id}    ${MODULE_ID_LABEL}
+    [Return]    ${module_id_index}
+
+Return Indexed Module From Module Name
+    [Arguments]    ${module_name}
+    [Documentation]    Returns indexed Xpath of the module from the module`s name.
+    ${module_id_index}=    Return Module ID Index From Module Name    ${module_name}
+    ${module_list_item_indexed}=    Return Module List Indexed Module    ${module_id_index}
+    [Return]    ${module_list_item_indexed}
+
+Expand Module
+    [Arguments]    ${module_name}    ${module_id_index}
+    [Documentation]    Clicks module list item in modules tab to expand the item and display its operations/ operational/ config items.
+    ...    Arguments are either module name, or module id index, that is a number, or ${EMPTY}, if the option is not used.
+    ${module_list_item_indexed}=    BuiltIn.Run Keyword If    "${module_name}"!= "${EMPTY}"    Return Indexed Module From Module Name    ${module_name}
+    ${module_list_item_indexed}=    BuiltIn.Run Keyword If    "${module_id_index}"!= "${EMPTY}"    Return Module List Indexed Module    ${module_id_index}
+    Selenium2Library.Click Element    ${module_list_item_indexed}
+    ${module_list_item_collapsed_indexed}=    BuiltIn.Set Variable    ${module_list_item_indexed}//following-sibling::md-list[@aria-hidden="true"]
+    Selenium2Library.Page Should Not Contain Element    ${module_list_item_collapsed_indexed}
+
+Expand Module And Click Module Operational Item
+    [Arguments]    ${module_name}    ${module_id_index}
+    [Documentation]    Clicks module list item in modules tab and then clicks its operational item to load operational tab in module detail.
+    ...    Arguments are either module name, or module id index, that is a number, or ${EMPTY}, if the option is not used.
+    Expand Module    ${module_name}    ${module_id_index}
+    Click Indexed Module Operational To Load Module Detail Operational Tab    ${module_id_index}
+
+Expand Module And Click Module Config Item
+    [Arguments]    ${module_name}    ${module_id_index}
+    [Documentation]    Clicks module list item in modules tab and then clicks its config item to load operational tab in module detail.
+    ...    Arguments are either module name, or module id index, that is a number, or ${EMPTY}, if the option is not used.
+    Expand Module    ${module_name}    ${module_id_index}
+    Click Indexed Module Config To Load Module Detail Config Tab    ${module_id_index}
+
+Navigate From Yangman Submenu To Testing Module Operational Tab
+    [Arguments]    ${testing_module_name}
+    [Documentation]    Navigates from loaded Yangman URL to testing module detail operational tab.
+    ${module_id_index}=    YangmanKeywords.Return Module ID Index From Module Name    ${testing_module_name}
+    Selenium2Library.Wait Until Page Does Not Contain Element    ${MODULES_WERE_LOADED_ALERT}
+    Expand Module And Click Module Operational Item    ${EMPTY}    ${module_id_index}
+
+Navigate From Yangman Submenu To Testing Module Config Tab
+    [Arguments]    ${testing_module_name}
+    [Documentation]    Navigates from loaded Yangman URL to testing module detail config tab.
+    ${module_id_index}=    YangmanKeywords.Return Module ID Index From Module Name    ${testing_module_name}
+    Selenium2Library.Wait Until Page Does Not Contain Element    ${MODULES_WERE_LOADED_ALERT}
+    Expand Module And Click Module Config Item    ${EMPTY}    ${module_id_index}
+
+Compose Branch Id
+    [Arguments]    ${index}
+    [Documentation]    Composes and returns string - branch id in the format branch-${index}.
+    BuiltIn.Return From Keyword    ${BRANCH_ID_LABEL}${index}
+
+Toggle Module Detail To Modules Or History Or Collections Tab
+    [Documentation]    Click toggle module detail button to toggle from module detail to modules or history or collections tab.
+    Selenium2Library.Wait Until Element Is Visible    ${TOGGLE_MODULE_DETAIL_BUTTON_LEFT}
+    GUIKeywords.Focus And Click Element    ${TOGGLE_MODULE_DETAIL_BUTTON_LEFT}
+
+Select Module Detail Operational Tab
+    [Documentation]    Selects operational tab in module detail.
+    ${status}=    BuiltIn.Run Keyword And Return Status    Selenium2Library.Page Should Contain Element    ${MODULE_DETAIL_OPERATIONAL_TAB_SELECTED}
+    BuiltIn.Run Keyword If    "${status}"=="False"    Selenium2Library.Click Element    ${MODULE_DETAIL_OPERATIONAL_TAB_DESELECTED}
+    Selenium2Library.Wait Until Page Contains Element    ${MODULE_DETAIL_OPERATIONAL_TAB_SELECTED}
+
+Select Module Detail Config Tab
+    [Documentation]    Selects config tab in module detail.
+    ${status}=    BuiltIn.Run Keyword And Return Status    Selenium2Library.Page Should Contain Element    ${MODULE_DETAIL_CONFIG_TAB_SELECTED}
+    BuiltIn.Run Keyword If    "${status}"=="False"    Selenium2Library.Click Element    ${MODULE_DETAIL_CONFIG_TAB_DESELECTED}
+    Selenium2Library.Wait Until Page Contains Element    ${MODULE_DETAIL_CONFIG_TAB_SELECTED}
+
+Expand All Branches In Module Detail Content Active Tab
+    [Documentation]    Expands all branches in module detail active operations or operational or config tab.
+    Selenium2Library.Wait Until Element Is Visible    ${MODULE_DETAIL_EXPAND_BRANCH_BUTTON}
+    : FOR    ${i}    IN RANGE    1    1000
+    \    ${count}=    Selenium2Library.Get Matching Xpath Count    ${MODULE_DETAIL_EXPAND_BRANCH_BUTTON}
+    \    BuiltIn.Exit For Loop If    ${count}==0
+    \    BuiltIn.Wait Until Keyword Succeeds    30 s    5 s    GUIKeywords.Focus And Click Element    ${MODULE_DETAIL_EXPAND_BRANCH_BUTTON}
+    Selenium2Library.Wait Until Page Does Not Contain Element    ${MODULE_DETAIL_EXPAND_BRANCH_BUTTON}
+
+Collapse All Branches In Module Detail Content Active Tab
+    [Documentation]    Collapses all branches in module detail active operations or operational or config tab.
+    Selenium2Library.Wait Until Element Is Visible    ${MODULE_DETAIL_COLLAPSE_BRANCH_BUTTON}
+    : FOR    ${i}    IN RANGE    1    1000
+    \    ${count}=    Selenium2Library.Get Matching Xpath Count    ${MODULE_DETAIL_COLLAPSE_BRANCH_BUTTON}
+    \    BuiltIn.Exit For Loop If    ${count}==0
+    \    BuiltIn.Wait Until Keyword Succeeds    30 s    5 s    GUIKeywords.Focus And Click Element    ${MODULE_DETAIL_COLLAPSE_BRANCH_BUTTON}
+    Selenium2Library.Wait Until Page Does Not Contain Element    ${MODULE_DETAIL_COLLAPSE_BRANCH_BUTTON}
+
+Return Module Detail Labelled Branch Xpath
+    [Arguments]    ${branch_label}
+    [Documentation]    Returns xpath of module detail labelled branch.
+    ${labelled_branch_xpath}=    BuiltIn.Set Variable    ${MODULE_DETAIL_BRANCH}//span[contains(@class, "indented tree-label ng-binding flex") and contains(text(), "${branch_label}")]
+    [Return]    ${labelled_branch_xpath}
+
+Return Module Detail Branch ID From Branch Label
+    [Arguments]    ${branch_label}
+    [Documentation]    Returns string - module detail branch id in the format branch-${index}.
+    ${labelled_branch_xpath}=    Return Module Detail Labelled Branch Xpath    ${branch_label}
+    ${branch_id}=    Selenium2Library.Get Element Attribute    ${labelled_branch_xpath}//ancestor::md-list-item[contains(@id, "${BRANCH_ID_LABEL}")]@id
+    [Return]    ${branch_id}
+
+Return Module Detail Branch Indexed
+    [Arguments]    ${branch_id}
+    [Documentation]    Returns indexed Xpath of the module detail branch. Argument is ${branch_id} in the form "branch-"${index}"".
+    ${module_detail_branch_indexed}=    BuiltIn.Set Variable    ${MODULE_DETAIL_ACTIVE_TAB_CONTENT}//md-list-item[contains(@id, "${branch_id}")]
+    [Return]    ${module_detail_branch_indexed}
+
+Return Indexed Branch Label
+    [Arguments]    ${module_detail_branch_indexed}
+    [Documentation]    Returns string - label of indexed branch in module detail.
+    ${branch_label}=    Selenium2Library.Get Text    ${module_detail_branch_indexed}//span[@class="indented tree-label ng-binding flex"]
+    [Return]    ${branch_label}
+
+Return Branch Label Without Curly Braces Part
+    [Arguments]    ${branch_label}
+    [Documentation]    Returns string - part of label of indexed branch in module detail without curly braces part.
+    ${branch_label_without_curly_braces_part}=    String.Fetch From Left    ${branch_label}    ${SPACE}
+    [Return]    ${branch_label_without_curly_braces_part}
+
+Return Labelled Branch Toggle Button
+    [Arguments]    ${labelled_branch_xpath}
+    [Documentation]    Returns xpath of toggle button of labelled branch in module detail.
+    ${labelled_branch_toggle_button}=    BuiltIn.Set Variable    ${labelled_branch_xpath}//preceding-sibling::md-icon[contains(@id, "toggle-branch-")]
+    [Return]    ${labelled_branch_toggle_button}
+
+Return Branch Toggle Button From Branch Label And Click
+    [Arguments]    ${branch_label}
+    [Documentation]    Returns xpath toggle button of labelled branch in module detail and clicks it.
+    ${labelled_branch_xpath}=    Return Module Detail Labelled Branch Xpath    ${branch_label}
+    ${labelled_branch_toggle_button}=    Return Labelled Branch Toggle Button    ${labelled_branch_xpath}
+    Selenium2Library.Page Should Contain Element    ${labelled_branch_toggle_button}
+    Selenium2Library.Click Element    ${labelled_branch_toggle_button}
+
+Click Module Detail Branch Indexed
+    [Arguments]    ${module_detail_branch_indexed}
+    [Documentation]    Click indexed branch in module detail.
+    Selenium2Library.Page Should Contain Element    ${module_detail_branch_indexed}
+    GUIKeywords.Mouse Down And Mouse Up Click Element    ${module_detail_branch_indexed}
+
+Verify Module Detail Branch Is List Branch
+    [Arguments]    ${module_detail_branch_indexed}
+    [Documentation]    Returns status "True" if module detail branch is a list branch and "False" if module detail branch is not a list brnach.
+    ${branch_label}=    Return Indexed Branch Label    ${module_detail_branch_indexed}
+    ${branch_is_list_evaluation}=    BuiltIn.Run Keyword And Return Status    BuiltIn.Should Contain    ${branch_label}    {
+    [Return]    ${branch_is_list_evaluation}
+
+Return Form Top Element Label
+    [Documentation]    Returns string - form top element label.
+    ${form_top_element_label}=    Selenium2Library.Get Text    ${FORM_TOP_ELEMENT_LABEL_XPATH}
+    [Return]    ${form_top_element_label}
+
+Return Form Top Element Labelled
+    [Arguments]    ${label}
+    [Documentation]    Returns xpath of form top element with label.
+    ${form_top_element_labelled}=    BuiltIn.Set Variable    ${FORM_TOP_ELEMENT_POINTER}//span[contains(@class, "ng-binding ng-scope") and contains(text(), "${label}")]
+    [Return]    ${form_top_element_labelled}
+
+Return Form List Item With Index Or Key
+    [Arguments]    ${branch_label}    ${branch_label_curly_braces_part}    ${index_or_key}
+    [Documentation]    Returns string - catenated branch label and index, in the form "label [${index_or_key}]" or "label <${branch_label_curly_braces_part}:${index_or_key}>".
+    ${branch_label_without_curly_braces_part}=    Return Branch Label Without Curly Braces Part    ${branch_label}
+    ${key_part}=    BuiltIn.Set Variable    <${branch_label_curly_braces_part}:${index_or_key}>
+    ${list_item_with_index_or_key}=    BuiltIn.Set Variable If    "${branch_label_curly_braces_part}"=="${EMPTY}"    ${FORM_TOP_ELEMENT_LIST_ITEM_LABEL}[contains(text(), "${branch_label_without_curly_braces_part}") and contains(text(), "[${index_or_key}]")]    ${FORM_TOP_ELEMENT_LIST_ITEM_LABEL}[contains(text(), "${branch_label_without_curly_braces_part}") and contains(text(), "${key_part}")]
+    [Return]    ${list_item_with_index_or_key}
+
+Verify List Item With Index Or Key Is Visible
+    [Arguments]    ${branch_label}    ${branch_label_curly_braces_part}    ${index_or_key}
+    [Documentation]    Verifies that form list item with given index or key is visible.
+    ${list_item_with_index_or_key}=    Return Form List Item With Index Or Key    ${branch_label}    ${branch_label_curly_braces_part}    ${index_or_key}
+    Selenium2Library.Wait Until Element Is Visible    ${list_item_with_index_or_key}
+
+Load Topology Topology Id Node In Form
+    [Documentation]    Expands network-topology branch in testing module detail and clicks topology {topology-id} branch to load topology list node in form.
+    Select Form View
+    ${topology_topology_id_branch}=    Return Module Detail Labelled Branch Xpath    ${TOPOLOGY_TOPOLOGY_ID_LABEL}
+    ${status}=    BuiltIn.Run Keyword And Return Status    Selenium2Library.Element Should Be Visible    ${topology_topology_id_branch}
+    BuiltIn.Run Keyword If    "${status}"=="False"    Return Branch Toggle Button From Branch Label And Click    ${NETWORK_TOPOLOGY_LABEL}
+    YangmanKeywords.Return Branch Toggle Button From Branch Label And Click    ${TOPOLOGY_TOPOLOGY_ID_LABEL}
+    Verify List Item With Index Or Key Is Visible    ${TOPOLOGY_TOPOLOGY_ID_LABEL}    ${EMPTY}    0
+
+Verify Sent Data CM Is Displayed
+    [Documentation]    Verifies that sent data code mirror is displayed.
+    Selenium2Library.Wait Until Element Is Visible    ${SENT_DATA_CODE_MIRROR_DISPLAYED}
+
+Verify Sent Data CM Is Not Displayed
+    [Documentation]    Verifies that sent data code mirror is not displayed.
+    Selenium2Library.Wait Until Element Is Not Visible    ${SENT_DATA_CODE_MIRROR_DISPLAYED}
+
+Verify Received Data CM Is Displayed
+    [Documentation]    Verifies that received data code mirror is displayed.
+    Selenium2Library.Wait Until Element Is Visible    ${RECEIVED_DATA_CODE_MIRROR_DISPLAYED}
+
+Verify Received Data CM Is Not Displayed
+    [Documentation]    Verifies that received data code mirror is not displayed.
+    Selenium2Library.Wait Until Element Is Not Visible    ${RECEIVED_DATA_CODE_MIRROR_DISPLAYED}
diff --git a/csit/suites/dluxapps/yangman/502__yangman.robot b/csit/suites/dluxapps/yangman/502__yangman.robot
new file mode 100644 (file)
index 0000000..e3b3212
--- /dev/null
@@ -0,0 +1,57 @@
+*** Settings ***
+Documentation     Verification that DLUX cotains Yangman submenu when logged in.
+...               Verification that when Yangman submenu entered, there are certain elements displayed.
+...               Verification that the selected operation is displayed and relevant code mirror(s) is/are displayed.
+Suite Teardown    Close Browser
+Resource          ${CURDIR}/../../../libraries/YangmanKeywords.robot
+
+*** Variables ***
+
+*** Test Cases ***
+Open dlux and login and verify yangman submenu has been loaded
+    GUIKeywords.Open Or Launch DLUX Page And Log In To DLUX
+
+Verify yangman submenu elements
+    YangmanKeywords.Verify Yangman Home Page Elements
+    Verify Operations Presence In Operation Select Menu
+    YangmanKeywords.Exit Opened Application Dialog
+
+Verify operation selection and code mirror displaying works correctly
+    Select Each Operation And Verify That Code Mirrors Has Been Displayed Correctly
+
+Verify that selecting/deselecting show data checkboxes in json view results in displaying/hiding the corresponding code mirror
+    Verify Displaying And Hiding Of CMs When Selecting Show Data Checkboxes
+
+*** Keywords ***
+Verify Operations Presence In Operation Select Menu
+    YangmanKeywords.Expand Operation Select Menu
+    Selenium2Library.Wait Until Page Contains Element    ${GET_OPTION}
+    Selenium2Library.Wait Until Page Contains Element    ${PUT_OPTION}
+    Selenium2Library.Wait Until Page Contains Element    ${POST_OPTION}
+    Selenium2Library.Wait Until Page Contains Element    ${DELETE_OPTION}
+
+Select Each Operation And Verify That Code Mirrors Has Been Displayed Correctly
+    ${operation_ids}=    YangmanKeywords.Return List Of Operation IDs
+    ${operation_names}=    YangmanKeywords.Return List Of Operation Names
+    : FOR    ${i}    IN RANGE    0    len(${operation_ids})
+    \    ${operation_id}=    Collections.Get From List    ${operation_ids}    ${i}
+    \    ${operation_name}=    Collections.Get From List    ${operation_names}    ${i}
+    \    YangmanKeywords.Expand Operation Select Menu And Select Operation    ${operation_id}    ${operation_name}
+    \    Run Keyword If    "${operation_name}"=="PUT" or "${operation_name}"=="POST"    BuiltIn.Run Keywords    YangmanKeywords.Verify Sent Data CM Is Displayed
+    \    ...    AND    YangmanKeywords.Verify Received Data CM Is Displayed
+    \    Run Keyword If    "${operation_name}"=="GET" or "${operation_name}"=="DELETE"    YangmanKeywords.Verify Received Data CM Is Displayed
+
+Verify Displaying And Hiding Of CMs When Selecting Show Data Checkboxes
+    YangmanKeywords.Select Json View
+    YangmanKeywords.Expand Operation Select Menu And Select Operation    ${GET_OPTION}    GET
+    YangmanKeywords.Verify Sent Data CM Is Not Displayed
+    YangmanKeywords.Verify Received Data CM Is Displayed
+    GUIKeywords.Patient Click    ${SHOW_SENT_DATA_CHECKBOX_UNSELECTED}    ${SHOW_SENT_DATA_CHECKBOX_SELECTED}
+    YangmanKeywords.Verify Sent Data CM Is Displayed
+    YangmanKeywords.Verify Received Data CM Is Displayed
+    GUIKeywords.Patient Click    ${SHOW_RECEIVED_DATA_CHECKBOX_SELECTED}    ${SHOW_RECEIVED_DATA_CHECKBOX_UNSELECTED}
+    YangmanKeywords.Verify Sent Data CM Is Displayed
+    YangmanKeywords.Verify Received Data CM Is Not Displayed
+    GUIKeywords.Patient Click    ${SHOW_SENT_DATA_CHECKBOX_SELECTED}    ${SHOW_SENT_DATA_CHECKBOX_UNSELECTED}
+    YangmanKeywords.Verify Sent Data CM Is Not Displayed
+    YangmanKeywords.Verify Received Data CM Is Not Displayed
diff --git a/csit/testplans/dluxapps-yangman.txt b/csit/testplans/dluxapps-yangman.txt
new file mode 100644 (file)
index 0000000..233426f
--- /dev/null
@@ -0,0 +1,8 @@
+# Copyright (c) 2015 Inocybe Technologie and others. All rights reserved.
+#
+# This program and the accompanying materials are made available under the
+# terms of the Eclipse Public License v1.0 which accompanies this distribution,
+# and is available at http://www.eclipse.org/legal/epl-v10.html
+
+# Place the suites in run order:
+integration/test/csit/suites/dluxapps/yangman
\ No newline at end of file
diff --git a/csit/variables/YangmanGUIVariables.robot b/csit/variables/YangmanGUIVariables.robot
new file mode 100644 (file)
index 0000000..041ea19
--- /dev/null
@@ -0,0 +1,107 @@
+*** Settings ***
+Documentation     A resource file containing all global Yangman GUI variables
+...               to help Yangman GUI and functional testing.
+Resource          Variables.robot
+
+*** Variables ***
+${YANGMAN_LOGO}    //img[contains(@ng-src, "assets/images/logo_yangman.png") and contains(@id, "page_logo")]
+${TOGGLE_MENU_BUTTON}    //a[@id="toggleMenu"]
+${LOGOUT_BUTTON}    //a[@id="logout-button"]
+# Left Panel
+${MODULES_TAB_NAME}    Modules
+${HISTORY_TAB_NAME}    History
+${COLLECTIONS_TAB_NAME}    Collections
+${LEFT_TAB_AREA}    //md-tab-content[@id="tab-content-0"]
+${MODULES_TAB_SELECTED}    ${LEFT_TAB_AREA}//md-tab-item[@aria-selected="true"]/span[contains(text(), "${MODULES_TAB_NAME}")]
+${MODULES_TAB_UNSELECTED}    ${LEFT_TAB_AREA}//md-tab-item[@aria-selected="false"]/span[contains(text(), "${MODULES_TAB_NAME}")]
+${HISTORY_TAB_SELECTED}    ${LEFT_TAB_AREA}//md-tab-item[@aria-selected="true"]/span[contains(text(), "${HISTORY_TAB_NAME}")]
+${HISTORY_TAB_UNSELECTED}    ${LEFT_TAB_AREA}//md-tab-item[@aria-selected="false"]/span[contains(text(), "${HISTORY_TAB_NAME}")]
+${COLLECTIONS_TAB_SELECTED}    ${LEFT_TAB_AREA}//md-tab-item[@aria-selected="true"]/span[contains(text(), "${COLLECTIONS_TAB_NAME}")]
+${COLLECTIONS_TAB_UNSELECTED}    ${LEFT_TAB_AREA}//md-tab-item[@aria-selected="false"]/span[contains(text(), "${COLLECTIONS_TAB_NAME}")]
+${MODULES_WERE_LOADED_ALERT}    //span[contains(text(), "Modules were loaded.")]
+${TOGGLE_MODULE_DETAIL_BUTTON_LEFT}    //md-icon[@class="arrow-switcher material-icons" and @id="toggle-module-detail"]
+${TOGGLE_MODULE_DETAIL_BUTTON_RIGHT}    //md-icon[@class="arrow-switcher material-icons arrow-switcher__left"" and @id="toggle-module-detail"]
+# Modules Tab Left Panel
+${MODULE_TAB_CONTENT}    //*[@id="tab-content-2"]
+${MODULE_SEARCH_INPUT}    //input[@id="search-modules"]
+${MODULE_ID_LABEL}    module_
+${MODULE_LIST_ITEM}    ${MODULE_TAB_CONTENT}//md-list-item[contains(@id, "${MODULE_ID_LABEL}")]//div[@class="pointer title layout-align-center-center layout-row"]
+${MODULE_LIST_ITEM_COLLAPSED}    ${MODULE_LIST_ITEM}//following-sibling::md-list[@aria-hidden="true"]
+${MODULE_LIST_ITEM_EXPANDED}    ${MODULE_LIST_ITEM}//following-sibling::md-list[@aria-hidden="false"]
+${MODULE_LIST_MODULE_NAME_XPATH}    ${MODULE_LIST_ITEM}//p[@class="top-element flex"]
+${OPERATIONS_LABEL}    operations
+${OPERATIONAL_LABEL}    operational
+${CONFIG_LABEL}    config
+${TESTING_MODULE_NAME}    ${EMPTY}
+${TESTING_MODULE_XPATH}    ${MODULE_TAB_CONTENT}//p[contains(., "${TESTING_MODULE_NAME}")]//ancestor::md-list-item[contains(@id, "${MODULE_ID_LABEL}")]
+# Module Detail
+${MODULE_DETAIL_CONTENT}    //*[@id="tab-content-1"]
+${MODULE_DETAIL_MODULE_NAME_LABEL}    ${MODULE_DETAIL_CONTENT}//h4
+${MODULE_DETAIL_OPERATIONS_TAB_SELECTED}    ${MODULE_DETAIL_CONTENT}//md-tab-item[@aria-selected="true"]//span[contains(text(), "${OPERATIONS_LABEL}")]
+${MODULE_DETAIL_OPERATIONS_TAB_DESELECTED}    ${MODULE_DETAIL_CONTENT}//md-tab-item[@aria-selected="false"]//span[contains(text(), "${OPERATIONS_LABEL}")]
+${MODULE_DETAIL_OPERATIONAL_TAB_SELECTED}    ${MODULE_DETAIL_CONTENT}//md-tab-item[@aria-selected="true"]//span[contains(text(), "${OPERATIONAL_LABEL}")]
+${MODULE_DETAIL_OPERATIONAL_TAB_DESELECTED}    ${MODULE_DETAIL_CONTENT}//md-tab-item[@aria-selected="false"]//span[contains(text(), "${OPERATIONAL_LABEL}")]
+${MODULE_DETAIL_CONFIG_TAB_SELECTED}    ${MODULE_DETAIL_CONTENT}//md-tab-item[@aria-selected="true"]//span[contains(text(), "${CONFIG_LABEL}")]
+${MODULE_DETAIL_CONFIG_TAB_DESELECTED}    ${MODULE_DETAIL_CONTENT}//md-tab-item[@aria-selected="false"]//span[contains(text(), "${CONFIG_LABEL}")]
+${MODULE_DETAIL_TAB_CONTENT_LABEL}    tab-content-
+${MODULE_DETAIL_ACTIVE_TAB_CONTENT}    ${MODULE_DETAIL_CONTENT}//md-tab-content[contains(@class, "md-active")]
+${MODULE_DETAIL_EXPAND_BRANCH_BUTTON}    ${MODULE_DETAIL_ACTIVE_TAB_CONTENT}//md-icon[contains(., "add")]
+${MODULE_DETAIL_COLLAPSE_BRANCH_BUTTON}    ${MODULE_DETAIL_ACTIVE_TAB_CONTENT}//md-list-item//md-icon[contains(., "remove")]
+${BRANCH_LABEL}    ${EMPTY}
+${NETWORK_TOPOLOGY_LABEL}    network-topology
+${TOPOLOGY_TOPOLOGY_ID_LABEL}    topology {topology-id}
+${NODE_NODE_ID_LABEL}    node {node-id}
+${LINK_LINK_ID_LABEL}    link {link-id}
+${BRANCH_ID_LABEL}    branch-
+${MODULE_DETAIL_BRANCH}    ${MODULE_DETAIL_ACTIVE_TAB_CONTENT}//md-list-item[contains(@id, "${BRANCH_ID_LABEL}")]
+${MODULE_DETAIL_BRANCH_LABEL}    ${MODULE_DETAIL_BRANCH}//span[contains(@class, "indented tree-label ng-binding flex") and contains(text(), "${BRANCH_LABEL}")]
+#History Tab Left Panel
+#Collections Tab Left Panel
+#Right Panel Header
+${OPERATION_NAME}    EMPTY
+${OPERATION_SELECT_INPUT}    //md-select[@id="request-selected-operation"]
+${OPERATION_SELECT_INPUT_CLICKABLE}    ${OPERATION_SELECT_INPUT}//parent::md-input-container
+${SELECT_BACKDROP}    //md-backdrop[@class="md-select-backdrop md-click-catcher ng-scope"]
+${OPERATION_SELECT_MENU_EXPANDED}    //div[contains(@aria-hidden, "false") and contains(@id,"select_container_10")]
+${GET_OPTION}     //*[@id="select_option_12"]
+${POST_OPTION}    //*[@id="select_option_13"]
+${PUT_OPTION}     //*[@id="select_option_14"]
+${DELETE_OPTION}    //*[@id="select_option_15"]
+${SELECTED_OPERATION_XPATH}    ${OPERATION_SELECT_INPUT}//span/div[contains(text(), "${OPERATION_NAME}")]
+${REQUEST_URL_INPUT}    //*[@id="request-url"]
+${SEND_BUTTON}    //*[@id="send-request"]
+${SAVE_BUTTON}    //*[@id="save-request"]
+${PARAMETERS_BUTTON}    //*[@id="show-parameters"]
+${FORM_RADIOBUTTON_SELECTED}    //md-radio-button[contains(@id, "shown-data-type-form") and contains(@aria-checked, "true")]
+${FORM_RADIOBUTTON_UNSELECTED}    //md-radio-button[contains(@id, "shown-data-type-form") and contains(@aria-checked, "false")]
+${JSON_RADIOBUTTON_SELECTED}    //md-radio-button[contains(@id, "shown-data-type-json") and contains(@aria-checked, "true")]
+${JSON_RADIOBUTTON_UNSELECTED}    //md-radio-button[contains(@id, "shown-data-type-json") and contains(@aria-checked, "false")]
+${FILL_FORM_WITH_RECEIVED_DATA_CHECKBOX_SELECTED}    //span[contains(text(), "Fill form with received data after execution")]//ancestor::md-checkbox[@aria-checked="true"]
+${FILL_FORM_WITH_RECEIVED_DATA_CHECKBOX_UNSELECTED}    //span[contains(text(), "Fill form with received data after execution")]//ancestor::md-checkbox[@aria-checked="false"]
+${SHOW_SENT_DATA_CHECKBOX_SELECTED}    //md-checkbox[@id="show-sent-data-checkbox" and @aria-checked="true"]
+${SHOW_SENT_DATA_CHECKBOX_UNSELECTED}    //md-checkbox[@id="show-sent-data-checkbox" and @aria-checked="false"]
+${SHOW_RECEIVED_DATA_CHECKBOX_SELECTED}    //md-checkbox[@id="show-received-data-checkbox" and @aria-checked="true"]
+${SHOW_RECEIVED_DATA_CHECKBOX_UNSELECTED}    //md-checkbox[@id="show-received-data-checkbox" and @aria-checked="false"]
+${MILLISECONDS_LABEL}    ms
+${STATUS_LABEL}    //span[contains(text(), "Status:")]
+${STATUS_VALUE}    //span[@id="info-request-status"]
+${TIME_LABEL}     //span[contains(text(), "Time:")]
+${TIME_VALUE}     //span[@id="info-request-execution-time"]
+#Right Panel Json Content
+${SENT_DATA_CODE_MIRROR_DISPLAYED}    //div[@id="sentData" and @aria-hidden="false"]
+${SENT_DATA_LABEL}    ${SENT_DATA_CODE_MIRROR_DISPLAYED}//h5[contains(text(), Sent data)]
+${SENT_DATA_ENLARGE_FONT_SIZE_BUTTON}    ${SENT_DATA_CODE_MIRROR_DISPLAYED}//button[contains(@aria-label, arrow_drop_up)]
+${SENT_DATA_REDUCE_FONT_SIZE_BUTTON}    ${SENT_DATA_CODE_MIRROR_DISPLAYED}//button[contains(@aria-label, arrow_drop_down)]
+${RECEIVED_DATA_CODE_MIRROR_DISPLAYED}    //div[@id="ReceiveData" and @aria-hidden="false"]
+${RECEIVED_DATA_LABEL}    ${RECEIVED_DATA_CODE_MIRROR_DISPLAYED}//h5[contains(text(), Received data)]
+${RECEIVED_DATA_ENLARGE_FONT_SIZE_BUTTON}    ${RECEIVED_DATA_CODE_MIRROR_DISPLAYED}//button[contains(@aria-label, arrow_drop_up)]
+${RECEIVED_DATA_REDUCE_FONT_SIZE_BUTTON}    ${RECEIVED_DATA_CODE_MIRROR_DISPLAYED}//button[contains(@aria-label, arrow_drop_down)]
+# Right Panel Form Content
+${FORM_CONTENT}    //section[contains(@class, "yangmanModule__right-panel__form bottom-content ng-scope") and contains(@aria-hidden, "false")]
+${FORM_TOP_ELEMENT_CONTAINER}    ${FORM_CONTENT}//div[contains(@class, "yangmanModule__right-panel__form__element-container ng-scope")]
+${FORM_TOP_ELEMENT_POINTER}    ${FORM_TOP_ELEMENT_CONTAINER}//p[contains(@class, "top-element pointer")]
+${FORM_TOP_ELEMENT_LABEL_XPATH}    ${FORM_TOP_ELEMENT_POINTER}//span[contains(@class, "ng-binding ng-scope")]
+${FORM_TOP_ELEMENT_YANGMENU}    ${FORM_TOP_ELEMENT_CONTAINER}//yang-form-menu
+${FORM_TOP_ELEMENT_LIST_ITEM_ROW}    ${FORM_TOP_ELEMENT_CONTAINER}//section[@class="yangmanModule__right-panel__form__list__paginator ng-scope layout-column flex"]
+${FORM_TOP_ELEMENT_LIST_ITEM}    ${FORM_TOP_ELEMENT_LIST_ITEM_ROW}//md-tab-item[contains(@class, "md-tab ng-scope ng-isolate-scope md-ink-ripple")]
+${FORM_TOP_ELEMENT_LIST_ITEM_LABEL}    ${FORM_TOP_ELEMENT_LIST_ITEM}/span