# Copyright 2015 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

import logging, json

from autotest_lib.client.bin import test, utils
from autotest_lib.client.common_lib import error
from autotest_lib.client.cros.networking.chrome_testing \
        import chrome_networking_test_context as cntc
from autotest_lib.client.cros.networking.chrome_testing \
        import chrome_networking_test_api as cnta
from autotest_lib.client.cros.networking.chrome_testing import test_utils
from autotest_lib.client.cros.power import sys_power
from collections import namedtuple

NetworkInfo = namedtuple('NetworkInfo', ['name', 'guid', 'connectionState',
                                         'networkType'])

class network_ChromeCellularEndToEnd(test.test):
    """
    Tests the following UI functionality with chrome.networkingPrivate APIs:
        1. Tests that the device auto connects to cellular network.
        3. Tests that the device prefers ethernet over cellular network.
        4. Tests that the enabling and disabling of cellular modem works.

    """
    version = 1


    def _extract_network_info(self, networks_found):
        """Extract the needed information from the list of networks.

        @param networks_found: Networks found via api.
        @return Formatted list of available cellular networks.

        """
        formatted_network_list = []

        for network in networks_found:
          network = NetworkInfo(name=network['Name'],
                  guid=network['GUID'],
                  connectionState=network.get('ConnectionState', 'none'),
                  networkType=network['Type'])
          formatted_network_list.append(network)

        return formatted_network_list


    def _set_autoconnect(self, service, value=True):
        """Turn on autoconnect for cellular network.

        @param service: Cellular service dictionary
        @value: Set / unset autoconnect

        """
        logging.debug('_set_autoconnect')
        properties = json.dumps({'Cellular': {'AutoConnect': value}})
        set_properties = test_utils.call_test_function_check_success(
                self._chrome_testing,
                'setProperties',
                ('"' + service['GUID'] + '"', properties))
        self.chrome_net.scan_for_networks()


    def _is_cellular_network_connected(self, service):
        """Check if device is connected to cellular network.

        @param service: Cellular service dict
        @return True if connected to cellular, else False

        """
        network_properties = self.chrome_net._chrome_testing.call_test_function(
                test_utils.LONG_TIMEOUT,
                'getNetworkInfo',
                ('"' + service['GUID'] + '"'))

        logging.debug('Network properties: %s', network_properties)

        if network_properties['status'] == 'chrome-test-call-status-failure':
            raise error.TestFail('getNetworkInfo did not return with status '
                                 'SUCCESS: %s' % network_properties['error'])

        if network_properties['result']['ConnectionState'] == 'Connected':
            return True

        return False


    def _cellular_service(self):
        """Find cellular service.

        @return Cellular service dict

        """
        cell_networks = self.chrome_net._chrome_testing.find_cellular_networks()
        for service in cell_networks:
            if service['GUID']:
                return service

        return None


    def _find_cellular_service(self):
        """Find and return cellular service if available.

        @return Cellular service

        """
        utils.poll_for_condition(lambda: self._cellular_service() is not None,
                                 exception=error.TestFail('No cell service.'),
                                 sleep_interval=1,
                                 timeout=60)
        return self._cellular_service()


    def _connect_to_cellular_network(self, service):
        """Connect to cellular network.

        @param service: Cellular service dict

        """
        logging.debug('_connect_to_cellular_network')
        if service is None:
            raise error.TestFail('GUID not available for cellular network.')
        self.chrome_net.connect_to_network(service)
        self.chrome_net.scan_for_networks()


    def _autoconnect_cellular(self):
        """Verify that the DUT is able to autoconnect to cellular network."""
        logging.debug('_autoconnect_cellular')
        service = self._find_cellular_service()
        logging.debug('Cellular service: %s', service)

        if service['ConnectionState'] == 'NotConnected':
            self._connect_to_cellular_network(service)

        self._set_autoconnect(service)

        logging.debug('Suspend and resume device')
        sys_power.do_suspend(20)
        service = self._find_cellular_service()

        utils.poll_for_condition(
                lambda: self._is_cellular_network_connected(service),
                exception=error.TestFail('Network not connected after suspend '
                                         'and resume.'),
                sleep_interval=1,
                timeout=60)
        logging.debug('Autoconnect works after suspend/resume.')


    def _get_networks(self, network_type='All'):
        """Get available networks with getNetworks api.

        @param network_type: Type of network, defaults to All
        @return List of networks found

        """
        logging.debug('_get_networks')
        properties = json.dumps({'networkType': network_type,
                                 'visible': True,
                                 'limit': 2})
        network_list = self.chrome_net._chrome_testing.call_test_function(
                test_utils.LONG_TIMEOUT,
                'getNetworks',
                (properties))
        return network_list


    def _ethernet_preferred_over_cellular(self):
        """Verify that the DUT prefers ethernet over cellular connection."""
        logging.debug('_ethernet_preferred_over_cellular')
        self.chrome_net.disable_network_device(self.chrome_net.WIFI_DEVICE)
        network_list = self._get_networks()

        if not len(network_list['result']) > 1:
            logging.debug('Available networks: %s', network_list)
            raise error.TestFail('Not enough networks available to check '
                                 'network preference. Need minimum 2 networks '
                                 'to do a successfull comparision.')

        formatted_network_list = self._extract_network_info(
                network_list['result'])

        logging.debug('Available network list: %s', formatted_network_list)

        if not formatted_network_list[0].networkType == 'Ethernet':
            raise error.TestFail('Ethernet is not preferred.')

        if not formatted_network_list[1].networkType == 'Cellular':
            raise error.TestFail('Cellular is not available to determine '
                                 'network preference.')

        if (not formatted_network_list[0].connectionState == 'Connected' or
            not formatted_network_list[1].connectionState == 'Connected'):
            raise error.TestFail('Ethernet and Cellular should both be '
                                 'connected to successfully determine '
                                 'network preference.')

        logging.debug('Ethernet is preferred over cellular.')


    def _enable_disable_network_check(
            self, original_enabled_networks, new_enabled_networks):
        """Tests enabling and disabling of Cellular.

        @param original_enabled_networks: Original list of network devices that
                were enabled when the test started.
        @param new_enabled_networks: New list of network devices that are
                enabled now.
        @raises error.TestFail if Cellular state is not toggled.

        """
        # Make sure we leave the Cellular modem in enabled state before
        # ending the test.
        logging.debug('_enable_disable_network_check')
        self.chrome_net.enable_network_device(self.chrome_net.CELLULAR)

        if self.chrome_net.CELLULAR in original_enabled_networks:
            if self.chrome_net.CELLULAR in new_enabled_networks:
                raise error.TestFail('Cellular was not disabled.')
            elif self.chrome_net.CELLULAR not in new_enabled_networks:
                logging.info('Cellular was successfully disabled.')

        if self.chrome_net.CELLULAR not in original_enabled_networks:
            if self.chrome_net.CELLULAR not in new_enabled_networks:
                raise error.TestFail('Cellular was not enabled.')
            elif self.chrome_net.CELLULAR in new_enabled_networks:
                logging.info('Cellular was successfully enabled.')


    def _enable_disable_cellular(self):
        """Verify that the test is able to enable and disable Cellular."""
        logging.debug('_enable_disable_cellular')
        original_enabled_networks = self.chrome_net.get_enabled_devices()
        if self.chrome_net.CELLULAR in original_enabled_networks:
            self.chrome_net.disable_network_device(self.chrome_net.CELLULAR)
        else:
            self.chrome_net.enable_network_device(self.chrome_net.CELLULAR)
        new_enabled_networks = self.chrome_net.get_enabled_devices()
        self._enable_disable_network_check(
                original_enabled_networks, new_enabled_networks)


    def run_once(self, test):
        """Runs the test.

        @param test: Set by the server test control file depending on the test
                that is being run.

        """
        with cntc.ChromeNetworkingTestContext() as testing_context:
            self._chrome_testing = testing_context
            self.chrome_net = cnta.ChromeNetworkProvider(testing_context)
            enabled_devices = self.chrome_net.get_enabled_devices()

            logging.debug('Enabled devices: %s', enabled_devices)
            if (self.chrome_net.CELLULAR not in enabled_devices):
                self.chrome_net.enable_network_device(
                    self.chrome_net.CELLULAR)
            self.chrome_net.scan_for_networks()

            if test == 'autoconnectCellular':
                self._autoconnect_cellular()
            elif test == 'ethernetPreferred':
                self._ethernet_preferred_over_cellular()
            elif test == 'enableDisableCellular':
                self._enable_disable_cellular()
