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

instruments-js.UIAutomation.js Maven / Gradle / Ivy

The newest version!
/**
 * @module ios-driver
 */

/**
 * @constructor
 * @type {{cache: Cache, CURL: string, COMMAND: string, HOST: String, TIMEOUT_IN_SEC:
 * {implicit: number}, SESSION: string, CAPABILITIES: number, createJSONResponse: Function,
 * postResponseAndGetNextCommand: Function, loadCapabilities: Function, getCapabilities:
 * Function, setTimeout: Function, getTimeout: Function, setAlertHandler:
 * Function, commandLoop: Function}}
 */
var UIAutomation = {
    cache: new Cache(),
    CURL: "/usr/bin/curl",
    COMMAND: "http://localhost:" + CONFIG_PORT + "/wd/hub/uiascriptproxy?sessionId=" + CONFIG_SESSION,
    HOST: UIATarget.localTarget().host(),
    TIMEOUT_IN_SEC: {
        "implicit": 0
    },
    SESSION: CONFIG_SESSION,
    AUT: CONFIG_AUT,
    COMMUNICATION_MODE: CONFIG_MODE,
    CAPABILITIES: -1,

    /**
     * Create a webdriver response for ios-driver. The response won't be sent to the client directly,
     * but to the ios-server first, and then potentially forwarded, and modified.
     * @param {string} sessionId the session currently controlling instruments.
     * @param {number} status the response status. 0 for ok.
     * @param {Object} value the response value
     * @return {string} the response value, stringified.
     */
    createJSONResponse: function (sessionId, status, value) {
        var result = {};
        result.sessionId = sessionId;
        result.status = status;
        var res = {};
        try {
            if (value && value.type && (value.type() === "UIAElementArray")) {
                var all = new Array();
                value = value.toArray();
                for (var i = 0; i < value.length; i++) {
                    var current = value[i];
                    var item = {};
                    item.ELEMENT = "" + current.reference();
                    item.type = current.type();
                    all.push(item);
                }
                res = all;
            } else if (value instanceof Array) {
                var all = new Array();
                for (var i = 0; i < value.length; i++) {
                    var current = value[i];
                    var item = {};

                    if (current.type) {
                        item.ELEMENT = "" + current.reference();
                        item.type = current.type();
                    } else {
                        item = current;
                    }

                    all.push(item);
                }
                res = all;
            } else if (value && value.type) {
                // check if the element is in an alert to throw the unexpected alert exception if needed
                try {
                    this.cache.get(value.reference());
                    res.ELEMENT = "" + value.reference();
                    res.type = value.type();
                } catch (err) {
                    res = err;
                    result.status = err.status || 13;
                }

            } else {
                res = value;
            }
            result.value = res;
        } catch (err) {
            result.status = 13;
            result.value = err;
        }

        var json = JSON.stringify(result);
        return json;
    },

    /**
     * Post the response from the previous call, and wait for the next command, up to 10 minutes.
     * @param {string} jsonResponse the response to send to ios-server.
     * @return {string} the next command.The command is a javascript snipet, that will be executed
     * using eval().
     */
    postResponseWithCURLAndGetNextCommand: function (jsonResponse) {
        log("posting response : " + jsonResponse);
        var nextCommand = this.HOST.performTaskWithPathArgumentsTimeout(this.CURL, [this.COMMAND,
                                                                                    "--data-binary",
                                                                                    jsonResponse],
                                                                        600);
        if (nextCommand.exitCode != 0) {
            throw new UIAutomationException("error getting new command. exit code : " + result
                .exitCode);
        }
        log("command : " + nextCommand.stdout);
        return nextCommand.stdout;

    },

    postResponseMultiAndGetNextCommand: function (jsonResponse) {
        response(jsonResponse);
        while (true) {
            UIATarget.localTarget().delay(0.05);
            var cmd = UIATarget.localTarget().frontMostApp().preferencesValueForKey('cmd');
            if (cmd) {
                UIATarget.localTarget().frontMostApp().setPreferencesValueForKey(null, 'cmd');
                return cmd;
            }
        }
    },

    /**
     * Initialises the capabilities for this session. Capabilities should be immutable.
     * @return {Object} the capabilities for the current session. Part of the capabilities a client
     * wants aren't accessible from instruments, and will be added by the ios-server.
     */
    loadCapabilities: function () {
        var result = new Object();
        var target = UIATarget.localTarget();
        var app = target.frontMostApp();

        // en , fr ...
        result.language = app.preferencesValueForKey("AppleLanguages")[0];
        // en_GB
        result.locale = app.preferencesValueForKey("AppleLocale");
        result.version = app.version();
        result.CFBundleIdentifier = app.bundleID();
        result.CFBundleVersion = app.bundleVersion();
        result.device = target.model();
        result.name = target.name();
        result.systemName = target.systemName();
        result.sdkVersion = target.systemVersion();
        result.aut = this.AUT;
        result.rect = target.rect();
        return result;
    },

    /**
     * Return the capabilities of the session. Hack inside to have the dimension of the target.
     * Capabilities should be immutable, and dimensions shouldn't be stored here.
     * @return {Object} the capabilities of the session.
     */
    getCapabilities: function () {
        if (this.CAPABILITIES === -1) {
            this.CAPABILITIES = this.loadCapabilities();
        }
        var result = this.CAPABILITIES;
        var target = UIATarget.localTarget();
        result.rect = target.rect();
        return result;
    },

    /**
     * set one of the timeout for the session
     * @param {string} type of the timout to set.
     * @param {number} timeoutInSeconds  in seconds.
     */
    setTimeout: function (type, timeoutInSeconds) {
        this.TIMEOUT_IN_SEC[type] = timeoutInSeconds;
    },

    /**
     * returns the timeout in seconds for the specified type.
     * @param {string} type
     * @return {number} the timeout for that type.
     */
    getTimeout: function (type) {
        return this.TIMEOUT_IN_SEC[type];
    },

    /**
     * wires the alert handler. If the handler isn't attached, all alerts are ignored, and clicked
     * away.
     */
    setAlertHandler: function () {
        var ignoreAllAlerts = false;
        UIATarget.onAlert = function onAlert(alert) {

            log(alert);
            log(alert.tree());
            //UIAutomation.cache.setAlert(alert);
            return !ignoreAllAlerts;
            //return ignoreAllAlerts;
        }
    },

    /**
     * Keep executing commands and sending the responses until the stop command is received.
     */
    commandLoop: function () {
        // first command after registration sends the capabilities.
        var init = {};
        if (this.COMMUNICATION_MODE === "MULTI") {
            UIATarget.localTarget().frontMostApp().setPreferencesValueForKey(null, 'cmd');
        }
        init.firstResponse = UIAutomation.getCapabilities();
        var response = this.createJSONResponse(this.SESSION, 0, init);
        var ok = true;
        while (ok) {
            try {
                var request;
                if (this.COMMUNICATION_MODE === "CURL") {
                    request = this.postResponseWithCURLAndGetNextCommand(response);
                } else {
                    request = this.postResponseMultiAndGetNextCommand(response);
                }
                if (request === "stop") {
                    ok = false;
                    log("end of the command loop.");

                    return;
                } else {
                    try {
                        response = eval(request);
                    } catch (err) {
                        if (err.status) {
                            response =
                            this.createJSONResponse(this.SESSION, err.status, err.message);
                        } else {
                            response = this.createJSONResponse(this.SESSION, 17, err.message);
                        }
                    }
                }
            } catch (err) {
                var response = this.createJSONResponse(this.SESSION, 13, err);
                log("err2 : " + JSON.stringify(err));
                return;
            }
        }
    }
};




© 2015 - 2024 Weber Informatics LLC | Privacy Policy