15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/test/chromedriver/session.h"
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
72a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include <list>
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
958537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)#include "base/lazy_instance.h"
1058537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)#include "base/threading/thread_local.h"
112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/values.h"
122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/test/chromedriver/chrome/chrome.h"
132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/test/chromedriver/chrome/status.h"
142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/test/chromedriver/chrome/web_view.h"
15b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "chrome/test/chromedriver/logging.h"
162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)namespace {
1858537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
1958537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)base::LazyInstance<base::ThreadLocalPointer<Session> >
2058537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)    lazy_tls_session = LAZY_INSTANCE_INITIALIZER;
2158537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
2258537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)}  // namespace
2358537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)FrameInfo::FrameInfo(const std::string& parent_frame_id,
252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                     const std::string& frame_id,
262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                     const std::string& chromedriver_frame_id)
272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : parent_frame_id(parent_frame_id),
282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      frame_id(frame_id),
292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      chromedriver_frame_id(chromedriver_frame_id) {}
302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
31424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)const base::TimeDelta Session::kDefaultPageLoadTimeout =
32424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)    base::TimeDelta::FromMinutes(5);
33868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)
342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)Session::Session(const std::string& id)
352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : id(id),
36a3f7b4e666c476898878fa745f637129375cd889Ben Murdoch      quit(false),
3790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      detach(false),
38424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)      force_devtools_screenshot(false),
39c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)      sticky_modifiers(0),
402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      mouse_position(0, 0),
415d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      page_load_timeout(kDefaultPageLoadTimeout),
425d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      auto_reporting_enabled(false) {}
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Session::Session(const std::string& id, scoped_ptr<Chrome> chrome)
452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : id(id),
46a3f7b4e666c476898878fa745f637129375cd889Ben Murdoch      quit(false),
4790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      detach(false),
48424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)      force_devtools_screenshot(false),
492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      chrome(chrome.Pass()),
50c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)      sticky_modifiers(0),
512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      mouse_position(0, 0),
525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      page_load_timeout(kDefaultPageLoadTimeout),
535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      auto_reporting_enabled(false) {}
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Session::~Session() {}
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)Status Session::GetTargetWindow(WebView** web_view) {
582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (!chrome)
592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    return Status(kNoSuchWindow, "no chrome started in this session");
602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  Status status = chrome->GetWebViewById(window, web_view);
622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (status.IsError())
632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    status = Status(kNoSuchWindow, "target window already closed", status);
642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  return status;
652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)void Session::SwitchToTopFrame() {
682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  frames.clear();
692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
71a02191e04bc25c4935f804f2c080ae28663d096dBen Murdochvoid Session::SwitchToParentFrame() {
72a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch  if (!frames.empty())
73a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch    frames.pop_back();
74a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch}
75a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch
762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)void Session::SwitchToSubFrame(const std::string& frame_id,
772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                               const std::string& chromedriver_frame_id) {
782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  std::string parent_frame_id;
792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (!frames.empty())
802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    parent_frame_id = frames.back().frame_id;
812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  frames.push_back(FrameInfo(parent_frame_id, frame_id, chromedriver_frame_id));
822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)std::string Session::GetCurrentFrameId() const {
852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (frames.empty())
86c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)    return std::string();
872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  return frames.back().frame_id;
882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
9058537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)std::vector<WebDriverLog*> Session::GetAllLogs() const {
9158537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  std::vector<WebDriverLog*> logs;
9258537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  for (ScopedVector<WebDriverLog>::const_iterator log = devtools_logs.begin();
9358537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)       log != devtools_logs.end();
9458537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)       ++log) {
9558537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)    logs.push_back(*log);
9658537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  }
9758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  if (driver_log)
9858537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)    logs.push_back(driver_log.get());
9958537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  return logs;
10058537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)}
10158537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
1025d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)std::string Session::GetFirstBrowserError() const {
1035d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  for (ScopedVector<WebDriverLog>::const_iterator it = devtools_logs.begin();
1045d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)       it != devtools_logs.end();
1055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)       ++it) {
1065d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if ((*it)->type() == WebDriverLog::kBrowserType) {
1075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      std::string message = (*it)->GetFirstErrorMessage();
1085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      if (!message.empty())
1095d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        return message;
1105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    }
1115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  }
1125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  return std::string();
1135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)}
1145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
11558537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)Session* GetThreadLocalSession() {
11658537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  return lazy_tls_session.Pointer()->Get();
11758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)}
11858537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
11958537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)void SetThreadLocalSession(scoped_ptr<Session> session) {
12058537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  lazy_tls_session.Pointer()->Set(session.release());
1212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
122