• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Copyright 2017 The Chromium OS Authors. All rights reserved.
2# Use of this source code is governed by a BSD-style license that can be
3# found in the LICENSE file.
4
5import logging
6import tempfile
7
8from autotest_lib.client.bin import utils
9from autotest_lib.client.common_lib import error
10from autotest_lib.client.common_lib import file_utils
11from autotest_lib.client.common_lib.cros import arc, arc_util
12from autotest_lib.client.common_lib.cros import chrome
13from autotest_lib.client.cros import cryptohome
14from autotest_lib.client.cros.input_playback import keyboard
15
16
17_CHROME_EXEC_TIME = 'chrome-exec'
18_LOGIN_TIME = 'login-prompt-visible'
19_LOGOUT_STARTED_TIME = 'logout-started'
20_LOGOUT_TIMEOUT = 60  # logout should finsih in 60 seconds.
21
22
23class platform_LogoutPerf(arc.ArcTest):
24    """Measured the time for signing off from a logged on user session.
25
26    The test mainly measures the time for signing off a session and raises
27    an exception if it could not be finished in time. First, it uses telemetry
28    to login a GAIA account and waits for container boots up if the
29    device supports ARC++, then validates the account. Next, it injects the
30    ctrl+shift+q twice to logout the session, then waits for new login screen
31    , i.e. the event of 'login-visible-prompt' to calculate the time elapsed
32    for logging out.
33    """
34    version = 1
35
36
37    def _get_latest_uptime(self, filename):
38        with open('/tmp/uptime-' + filename) as statfile:
39            values = map(lambda l: float(l.split()[0]),
40                         statfile.readlines())
41        logging.info('timestamp of %s -> %s ', filename, values[-1])
42        return values[-1]
43
44
45    def _validate(self):
46        # Validate if the environment is expected.
47        if not cryptohome.is_vault_mounted(
48                user=chrome.NormalizeEmail(self.username)):
49            raise error.TestFail('Expected to find a mounted vault for %s'
50                                 % self.username)
51        tab = self.cr.browser.tabs.New()
52        tab.Navigate('http://accounts.google.com')
53        tab.WaitForDocumentReadyStateToBeComplete()
54        res = tab.EvaluateJavaScript('''
55                var res = '',
56                    divs = document.getElementsByTagName('div');
57                for (var i = 0; i < divs.length; i++) {
58                    res = divs[i].textContent;
59                    if (res.search('%s') > 1) {
60                    break;
61                    }
62                }
63                res;
64        ''' % self.username)
65        if not res:
66            raise error.TestFail('No references to %s on accounts page.'
67                                 % self.username)
68        tab.Close()
69
70
71    def initialize(self):
72        self.keyboard = keyboard.Keyboard()
73        self.username, password = arc_util.get_test_account_info()
74        # Login a user session.
75        if utils.is_arc_available():
76            super(platform_LogoutPerf, self).initialize(
77                    gaia_login=True,
78                    disable_arc_opt_in=False)
79            self.cr = self._chrome
80        else:
81            with tempfile.NamedTemporaryFile() as cap:
82                file_utils.download_file(arc_util._ARCP_URL, cap.name)
83                password = cap.read().rstrip()
84            self.cr = chrome.Chrome(gaia_login=True,
85                                    username=self.username,
86                                    password=password)
87
88
89    def arc_setup(self):
90        # Do nothing here
91        logging.info('No ARC++ specific setup required')
92
93
94    def arc_teardown(self):
95        # Do nothing here
96        logging.info('No ARC++ specific teardown required')
97
98
99    def cleanup(self):
100        self.keyboard.close()
101        if utils.is_arc_available():
102            super(platform_LogoutPerf, self).cleanup()
103
104
105    def run_once(self):
106        # Validate the current GAIA login session
107        self._validate()
108
109        # Start signing out the session, wait until the new event of
110        # 'login-prompt-visible'.
111        self.keyboard.press_key('ctrl+shift+q')
112        self.keyboard.press_key('ctrl+shift+q')
113
114        # Get current login prompt timestamp
115        login_timestamp = self._get_latest_uptime(_LOGIN_TIME)
116
117        # Poll for new login prompt timestamp
118        utils.poll_for_condition(
119                lambda: self._get_latest_uptime(_LOGIN_TIME) != login_timestamp,
120                exception=error.TestFail('Timeout: Could not sign off in time'),
121                timeout=_LOGOUT_TIMEOUT,
122                sleep_interval=2,
123                desc='Polling for user to be logged out.')
124
125        logout_started = self._get_latest_uptime(_LOGOUT_STARTED_TIME)
126        logging.info('logout started @%s', logout_started)
127        chrome_exec = self._get_latest_uptime(_CHROME_EXEC_TIME)
128        logging.info('chrome restarts @%s', chrome_exec)
129        elapsed_time = float(chrome_exec) - float(logout_started)
130        logging.info('The elapsed time for signout is %s', elapsed_time)
131        self.output_perf_value(description='Seconds elapsed for Signout',
132                               value=elapsed_time,
133                               higher_is_better=False,
134                               units='seconds')
135