All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.seleniumtests.connectors.extools.Uft Maven / Gradle / Ivy

package com.seleniumtests.connectors.extools;

import java.io.File;
import java.io.IOException;
import java.io.StringReader;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import com.seleniumtests.util.logging.Sys;
import org.apache.commons.io.FileUtils;
import org.jdom2.*;
import org.jdom2.input.SAXBuilder;
import org.jsoup.Jsoup;
import org.testng.Reporter;
import org.xml.sax.InputSource;

import com.seleniumtests.connectors.selenium.SeleniumGridConnector;
import com.seleniumtests.core.SeleniumTestsContextManager;
import com.seleniumtests.core.TestTasks;
import com.seleniumtests.customexception.ConfigurationException;
import com.seleniumtests.customexception.ScenarioException;
import com.seleniumtests.driver.DriverMode;
import com.seleniumtests.reporter.logger.TestAction;
import com.seleniumtests.reporter.logger.TestMessage;
import com.seleniumtests.reporter.logger.TestMessage.MessageType;
import com.seleniumtests.reporter.logger.TestStep;
import com.seleniumtests.util.logging.ScenarioLogger;

/**
 * Connector for executing UFT tests either locally or remotely on selenium grid
 *
 * @author S047432
 */
public class Uft {

    private static final ScenarioLogger logger = ScenarioLogger.getScenarioLogger(Uft.class);
    private static final String START_LOGS = "_____OUTPUT_____";
    private static final String END_LOGS = "_____ENDOUTPUT_____";
    private static final String SCRIPT_NAME = "uft.vbs";

    private String almServer;
    private String almUser;
    private String almPassword;
    private String almDomain;
    private String almProject;
    private String scriptPath;
    private String scriptName;
    private boolean killUftOnStartup = true;
    private boolean loaded = false;
    Map parameters = new HashMap<>();
    ;

    /**
     * @param scriptPath path to the script, either local or from ALM. If test is
     *                   from ALM, prefix it with '[QualityCenter]'. e.g:
     *                   '[QualityCenter]Subject\TOOLS\TestsFoo\foo'
     */
    public Uft(String scriptPath) {
        this.scriptPath = scriptPath;
        this.scriptName = new File(scriptPath).getName();
    }

    public Uft(String almServer, String almUser, String almPassword, String almDomain, String almProject, String scriptPath) {
        this.scriptPath = scriptPath;
        this.scriptName = new File(scriptPath).getName();
        this.almServer = almServer;
        this.almUser = almUser;
        this.almPassword = almPassword;
        this.almDomain = almDomain;
        this.almProject = almProject;
    }

    public String getScriptPath() {
        return scriptPath;
    }

    public Map getParameters() {
        return parameters;
    }

    public void setParameters(Map parameters) {
        this.parameters = parameters;
    }

    public void loadScript(boolean killUftOnStartup) {
        this.killUftOnStartup = killUftOnStartup;
        List args = prepareArguments(true, false);
        TestTasks.executeCommand("cscript.exe", 60, null, args.toArray(new String[]{}));
        loaded = true;
    }

    /**
     * Executes an UFT script with timeout
     *
     * @param timeout timeout in seconds for UFT execution
     * @return the generated test step
     */
    public List executeScript(int timeout, Map parameters) {
        if (!loaded) {
            throw new IllegalStateException("Test script has not been loaded. Call 'loadScript' before");
        }
        this.parameters = parameters;

        String output = TestTasks.executeCommand("cscript.exe", timeout, null, prepareArguments(false, true).toArray(new String[]{}));

        // when execution ends, UFT is stopped
        loaded = false;
        return analyseOutput(output);
    }

    /**
     * Prepare list of arguments
     *
     * @param load    if true, add '/load'
     * @param execute if true, add '/execute'
     * @return
     */
    public List prepareArguments(boolean load, boolean execute) {
        // copy uft.vbs to disk
        String vbsPath;
        try {
            File tempFile = Files.createTempDirectory("uft").resolve(SCRIPT_NAME).toFile();
            tempFile.deleteOnExit();
            FileUtils.copyInputStreamToFile(
                    Thread.currentThread().getContextClassLoader().getResourceAsStream("uft/" + SCRIPT_NAME), tempFile);
            vbsPath = tempFile.getAbsolutePath();
        } catch (IOException e) {
            throw new ScenarioException("Error sending UFT script to grid node: " + e.getMessage());
        }

        if (SeleniumTestsContextManager.getThreadContext().getRunMode() == DriverMode.GRID) {
            SeleniumGridConnector gridConnector = SeleniumTestsContextManager.getThreadContext().getSeleniumGridConnector();
            if (gridConnector != null) {
                vbsPath = Paths.get(gridConnector.uploadFileToNode(vbsPath, true), SCRIPT_NAME).toString();
            } else {
                throw new ScenarioException("No grid connector present, executing UFT script needs a browser to be initialized");
            }
        }

        List args = new ArrayList<>();
        args.add(vbsPath);
        args.add(scriptPath);

        if (execute) {
            args.add("/execute");
            parameters.forEach((key, value) -> args.add(String.format("\"%s=%s\"", key, value)));
        }

        if (load) {
            if (almServer != null && almUser != null && almPassword != null && almDomain != null && almProject != null) {
                args.add("/server:" + almServer);
                args.add("/user:" + almUser);
                args.add("/password:" + almPassword);
                args.add("/domain:" + almDomain);
                args.add("/project:" + almProject);
            } else if (almServer != null || almUser != null || almPassword != null || almDomain != null || almProject != null) {
                throw new ConfigurationException(
                        "All valuers pour ALM connection must be provided: server, user, password, domain and project");
            }

            args.add("/load");

            if (killUftOnStartup) {
                args.add("/clean");
            }
        }
        return args;
    }

    /**
     * Analyze Result.xml content
     *
     * @param output the Result.xml content as a string // * @param duration
     *               duration of the execution
     * @return
     */
    public List analyseOutput(String output) {
        StringBuilder uftOutput = new StringBuilder();
        List stepList = new ArrayList<>();

        boolean logging = false;
        for (String line : output.split("\n")) {
            line = line.trim();

            if (line.contains(START_LOGS)) {
                logging = true;
                continue;
            } else if (line.contains(END_LOGS)) {
                logging = false;
            }

            if (logging) {
                uftOutput.append(line);
            }
        }

        stepList = readXmlResult(uftOutput.toString());

        return stepList;
    }

    /**
     * Read an action element
     * 

* // * @param parentStep * * @param actionElement * @throws DataConversionException */ private TestStep readAction(Element actionElement) throws DataConversionException { Element data = actionElement.getChild("Data"); // data null au second passage parce que pas de balise data après TestStep actionStep = new TestStep("UFT: " + data.getChild("Name").getValue().trim(), Reporter.getCurrentTestResult(), new ArrayList<>(), false); if (data != null && data.getChild("Result").getValue().contains("Failed")) { actionStep.setFailed(true); } for (Element element : actionElement.getChildren()) { if ("Data".equals(element.getName())) { } else if (element.getAttributeValue("type").equals("Action")) { TestStep readStep = readAction(element); actionStep.addStep(readStep); } else if (element.getAttributeValue("type").equals("Step")) { TestAction readAction = readStep(element); actionStep.addAction(readAction); } else if (element.getAttributeValue("type").equals("Context")) { TestStep readStep = readAction(element); actionStep.addStep(readStep); } else if (element.getAttributeValue("type").equals("User")) { TestStep readStep = readAction(element); actionStep.addStep(readStep); } } return actionStep; } /** * Read a step element *

* // * @param parentStep * * @param stepElement */ private TestAction readStep(Element stepElement) { String stepDescription = ""; TestAction stepAction; List stepList = stepElement.getChildren("ReportNode"); if (stepElement.getChild("Data").getChild("Description") != null) { if (!stepElement.getChild("Data").getChild("Description").getContent().isEmpty()) { org.jsoup.nodes.Document htmlDoc = Jsoup.parseBodyFragment(stepElement.getChild("Data").getChildText("Description")); String details = htmlDoc.text(); stepDescription = String.format("%s: %s", stepElement.getChild("Data").getChildText("Name"), details).trim(); } } else { stepDescription = String.format(stepElement.getChild("Data").getChildText("Name")).trim(); } if (stepList.isEmpty()) { stepAction = new TestAction(stepDescription, false, new ArrayList<>()); } else { stepAction = new TestStep(stepDescription, Reporter.getCurrentTestResult(), new ArrayList<>(), false); for (Element subStepElement : stepElement.getChildren("ReportNode")) { TestAction readAction = readStep(subStepElement); ((TestStep) stepAction).addAction(readAction); } } return stepAction; } public List readXmlResult(String xmlString) { Document document; SAXBuilder builder = new SAXBuilder(); List listStep = new ArrayList<>(); try { String xml = xmlString.substring(xmlString.indexOf("<")); String xml10pattern = "[^" + "\u0009\r\n" + "\u0020-\uD7FF" + "\uE000-\uFFFD" + "\ud800\udc00-\udbff\udfff" + "]"; xml = xml.replaceAll(xml10pattern, ""); document = builder.build(new InputSource(new StringReader(xml))); // we skip BOM by searching the first "<" character Element docElement = document.getRootElement().getChild("ReportNode"); Element elementToIterate = docElement.getChild("ReportNode"); Element iterationChild = elementToIterate.getChild("ReportNode"); Element data = docElement.getChild("Data"); if (!iterationChild.getChildren("ReportNode").isEmpty()) { elementToIterate = iterationChild; } for (Element element : elementToIterate.getChildren()) { if ("ReportNode".equals(element.getName())) { TestStep readStep = readAction(element); listStep.add(readStep); } // else if ("Data".equals(element.getName())) { // readStep(element); // } } } catch (IndexOutOfBoundsException e) { addStepWithoutXml(listStep, "Invalid XML data: ", e); } catch (JDOMException | IOException e) { addStepWithoutXml(listStep, "Could not read UFT report: ", e); } return listStep; } private void addStepWithoutXml(List listStep, String messageException, Exception e) { logger.error(messageException + e.getMessage()); TestStep readStep = new TestStep("UFT: " + scriptName, Reporter.getCurrentTestResult(), new ArrayList<>(), false); readStep.addMessage(new TestMessage(messageException + e.getMessage(), MessageType.ERROR)); listStep.add(readStep); } public void setKillUftOnStartup(boolean killUftOnStartup) { this.killUftOnStartup = killUftOnStartup; } public boolean isKillUftOnStartup() { return killUftOnStartup; } }





© 2015 - 2025 Weber Informatics LLC | Privacy Policy