• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (c) 2013 The Chromium 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 
5 #include <list>
6 #include <string>
7 
8 #include "base/compiler_specific.h"
9 #include "base/memory/scoped_ptr.h"
10 #include "base/values.h"
11 #include "chrome/test/chromedriver/chrome/devtools_client.h"
12 #include "chrome/test/chromedriver/chrome/status.h"
13 #include "chrome/test/chromedriver/chrome/web_view_impl.h"
14 #include "testing/gtest/include/gtest/gtest.h"
15 
16 namespace {
17 
18 class FakeDevToolsClient : public DevToolsClient {
19  public:
FakeDevToolsClient()20   FakeDevToolsClient() : id_("fake-id"), status_(kOk) {}
~FakeDevToolsClient()21   virtual ~FakeDevToolsClient() {}
22 
set_status(const Status & status)23   void set_status(const Status& status) {
24     status_ = status;
25   }
set_result(const base::DictionaryValue & result)26   void set_result(const base::DictionaryValue& result) {
27     result_.Clear();
28     result_.MergeDictionary(&result);
29   }
30 
31   // Overridden from DevToolsClient:
GetId()32   virtual const std::string& GetId() OVERRIDE {
33     return id_;
34   }
WasCrashed()35   virtual bool WasCrashed() OVERRIDE {
36     return false;
37   }
ConnectIfNecessary()38   virtual Status ConnectIfNecessary() OVERRIDE {
39     return Status(kOk);
40   }
SendCommand(const std::string & method,const base::DictionaryValue & params)41   virtual Status SendCommand(const std::string& method,
42                              const base::DictionaryValue& params) OVERRIDE {
43     return SendCommandAndGetResult(method, params, NULL);
44   }
SendCommandAndGetResult(const std::string & method,const base::DictionaryValue & params,scoped_ptr<base::DictionaryValue> * result)45   virtual Status SendCommandAndGetResult(
46       const std::string& method,
47       const base::DictionaryValue& params,
48       scoped_ptr<base::DictionaryValue>* result) OVERRIDE {
49     if (status_.IsError())
50       return status_;
51     result->reset(result_.DeepCopy());
52     return Status(kOk);
53   }
AddListener(DevToolsEventListener * listener)54   virtual void AddListener(DevToolsEventListener* listener) OVERRIDE {}
HandleEventsUntil(const ConditionalFunc & conditional_func,const base::TimeDelta & timeout)55   virtual Status HandleEventsUntil(
56       const ConditionalFunc& conditional_func,
57       const base::TimeDelta& timeout) OVERRIDE {
58     return Status(kOk);
59   }
HandleReceivedEvents()60   virtual Status HandleReceivedEvents() OVERRIDE {
61     return Status(kOk);
62   }
63 
64  private:
65   const std::string id_;
66   Status status_;
67   base::DictionaryValue result_;
68 };
69 
AssertEvalFails(const base::DictionaryValue & command_result)70 void AssertEvalFails(const base::DictionaryValue& command_result) {
71   scoped_ptr<base::DictionaryValue> result;
72   FakeDevToolsClient client;
73   client.set_result(command_result);
74   Status status = internal::EvaluateScript(
75       &client, 0, std::string(), internal::ReturnByValue, &result);
76   ASSERT_EQ(kUnknownError, status.code());
77   ASSERT_FALSE(result);
78 }
79 
80 }  // namespace
81 
TEST(EvaluateScript,CommandError)82 TEST(EvaluateScript, CommandError) {
83   scoped_ptr<base::DictionaryValue> result;
84   FakeDevToolsClient client;
85   client.set_status(Status(kUnknownError));
86   Status status = internal::EvaluateScript(
87       &client, 0, std::string(), internal::ReturnByValue, &result);
88   ASSERT_EQ(kUnknownError, status.code());
89   ASSERT_FALSE(result);
90 }
91 
TEST(EvaluateScript,MissingWasThrown)92 TEST(EvaluateScript, MissingWasThrown) {
93   base::DictionaryValue dict;
94   ASSERT_NO_FATAL_FAILURE(AssertEvalFails(dict));
95 }
96 
TEST(EvaluateScript,MissingResult)97 TEST(EvaluateScript, MissingResult) {
98   base::DictionaryValue dict;
99   dict.SetBoolean("wasThrown", false);
100   ASSERT_NO_FATAL_FAILURE(AssertEvalFails(dict));
101 }
102 
TEST(EvaluateScript,Throws)103 TEST(EvaluateScript, Throws) {
104   base::DictionaryValue dict;
105   dict.SetBoolean("wasThrown", true);
106   dict.SetString("result.type", "undefined");
107   ASSERT_NO_FATAL_FAILURE(AssertEvalFails(dict));
108 }
109 
TEST(EvaluateScript,Ok)110 TEST(EvaluateScript, Ok) {
111   scoped_ptr<base::DictionaryValue> result;
112   base::DictionaryValue dict;
113   dict.SetBoolean("wasThrown", false);
114   dict.SetInteger("result.key", 100);
115   FakeDevToolsClient client;
116   client.set_result(dict);
117   ASSERT_TRUE(internal::EvaluateScript(
118       &client, 0, std::string(), internal::ReturnByValue, &result).IsOk());
119   ASSERT_TRUE(result);
120   ASSERT_TRUE(result->HasKey("key"));
121 }
122 
TEST(EvaluateScriptAndGetValue,MissingType)123 TEST(EvaluateScriptAndGetValue, MissingType) {
124   scoped_ptr<base::Value> result;
125   FakeDevToolsClient client;
126   base::DictionaryValue dict;
127   dict.SetBoolean("wasThrown", false);
128   dict.SetInteger("result.value", 1);
129   client.set_result(dict);
130   ASSERT_TRUE(internal::EvaluateScriptAndGetValue(
131       &client, 0, std::string(), &result).IsError());
132 }
133 
TEST(EvaluateScriptAndGetValue,Undefined)134 TEST(EvaluateScriptAndGetValue, Undefined) {
135   scoped_ptr<base::Value> result;
136   FakeDevToolsClient client;
137   base::DictionaryValue dict;
138   dict.SetBoolean("wasThrown", false);
139   dict.SetString("result.type", "undefined");
140   client.set_result(dict);
141   Status status =
142       internal::EvaluateScriptAndGetValue(&client, 0, std::string(), &result);
143   ASSERT_EQ(kOk, status.code());
144   ASSERT_TRUE(result && result->IsType(base::Value::TYPE_NULL));
145 }
146 
TEST(EvaluateScriptAndGetValue,Ok)147 TEST(EvaluateScriptAndGetValue, Ok) {
148   scoped_ptr<base::Value> result;
149   FakeDevToolsClient client;
150   base::DictionaryValue dict;
151   dict.SetBoolean("wasThrown", false);
152   dict.SetString("result.type", "integer");
153   dict.SetInteger("result.value", 1);
154   client.set_result(dict);
155   Status status =
156       internal::EvaluateScriptAndGetValue(&client, 0, std::string(), &result);
157   ASSERT_EQ(kOk, status.code());
158   int value;
159   ASSERT_TRUE(result && result->GetAsInteger(&value));
160   ASSERT_EQ(1, value);
161 }
162 
TEST(EvaluateScriptAndGetObject,NoObject)163 TEST(EvaluateScriptAndGetObject, NoObject) {
164   FakeDevToolsClient client;
165   base::DictionaryValue dict;
166   dict.SetBoolean("wasThrown", false);
167   dict.SetString("result.type", "integer");
168   client.set_result(dict);
169   bool got_object;
170   std::string object_id;
171   ASSERT_TRUE(internal::EvaluateScriptAndGetObject(
172       &client, 0, std::string(), &got_object, &object_id).IsOk());
173   ASSERT_FALSE(got_object);
174   ASSERT_TRUE(object_id.empty());
175 }
176 
TEST(EvaluateScriptAndGetObject,Ok)177 TEST(EvaluateScriptAndGetObject, Ok) {
178   FakeDevToolsClient client;
179   base::DictionaryValue dict;
180   dict.SetBoolean("wasThrown", false);
181   dict.SetString("result.objectId", "id");
182   client.set_result(dict);
183   bool got_object;
184   std::string object_id;
185   ASSERT_TRUE(internal::EvaluateScriptAndGetObject(
186       &client, 0, std::string(), &got_object, &object_id).IsOk());
187   ASSERT_TRUE(got_object);
188   ASSERT_STREQ("id", object_id.c_str());
189 }
190 
TEST(ParseCallFunctionResult,NotDict)191 TEST(ParseCallFunctionResult, NotDict) {
192   scoped_ptr<base::Value> result;
193   base::FundamentalValue value(1);
194   ASSERT_NE(kOk, internal::ParseCallFunctionResult(value, &result).code());
195 }
196 
TEST(ParseCallFunctionResult,Ok)197 TEST(ParseCallFunctionResult, Ok) {
198   scoped_ptr<base::Value> result;
199   base::DictionaryValue dict;
200   dict.SetInteger("status", 0);
201   dict.SetInteger("value", 1);
202   Status status = internal::ParseCallFunctionResult(dict, &result);
203   ASSERT_EQ(kOk, status.code());
204   int value;
205   ASSERT_TRUE(result && result->GetAsInteger(&value));
206   ASSERT_EQ(1, value);
207 }
208 
TEST(ParseCallFunctionResult,ScriptError)209 TEST(ParseCallFunctionResult, ScriptError) {
210   scoped_ptr<base::Value> result;
211   base::DictionaryValue dict;
212   dict.SetInteger("status", 1);
213   dict.SetInteger("value", 1);
214   Status status = internal::ParseCallFunctionResult(dict, &result);
215   ASSERT_EQ(1, status.code());
216   ASSERT_FALSE(result);
217 }
218