1 // Copyright 2015 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 "content/public/test/test_web_ui.h"
6 
7 #include <utility>
8 
9 #include "base/callback.h"
10 #include "base/memory/ptr_util.h"
11 #include "base/notreached.h"
12 #include "base/strings/string_piece.h"
13 #include "content/public/browser/web_ui_controller.h"
14 #include "content/public/browser/web_ui_message_handler.h"
15 
16 namespace content {
17 
TestWebUI()18 TestWebUI::TestWebUI() : web_contents_(nullptr) {}
19 
~TestWebUI()20 TestWebUI::~TestWebUI() {
21   ClearTrackedCalls();
22 }
23 
ClearTrackedCalls()24 void TestWebUI::ClearTrackedCalls() {
25   call_data_.clear();
26 }
27 
HandleReceivedMessage(const std::string & handler_name,const base::ListValue * args)28 void TestWebUI::HandleReceivedMessage(const std::string& handler_name,
29                                       const base::ListValue* args) {
30   const auto callbacks_map_it = message_callbacks_.find(handler_name);
31 
32   if (callbacks_map_it == message_callbacks_.end())
33     return;
34 
35   // Create a copy of the callbacks before running them. Without this, it could
36   // be possible for the callback's handler to register a new message handler
37   // during iteration of the vector, resulting in undefined behavior.
38   std::vector<MessageCallback> callbacks_to_run = callbacks_map_it->second;
39   for (auto& callback : callbacks_to_run)
40     callback.Run(args);
41 }
42 
GetWebContents()43 WebContents* TestWebUI::GetWebContents() {
44   return web_contents_;
45 }
46 
GetController()47 WebUIController* TestWebUI::GetController() {
48   return controller_.get();
49 }
50 
SetController(std::unique_ptr<WebUIController> controller)51 void TestWebUI::SetController(std::unique_ptr<WebUIController> controller) {
52   controller_ = std::move(controller);
53 }
54 
GetDeviceScaleFactor()55 float TestWebUI::GetDeviceScaleFactor() {
56   return 1.0f;
57 }
58 
GetOverriddenTitle()59 const base::string16& TestWebUI::GetOverriddenTitle() {
60   return temp_string_;
61 }
62 
GetBindings()63 int TestWebUI::GetBindings() {
64   return bindings_;
65 }
66 
SetBindings(int bindings)67 void TestWebUI::SetBindings(int bindings) {
68   bindings_ = bindings;
69 }
70 
GetRequestableSchemes()71 const std::vector<std::string>& TestWebUI::GetRequestableSchemes() {
72   NOTIMPLEMENTED();
73   return std::move(std::vector<std::string>());
74 }
75 
AddRequestableScheme(const char * scheme)76 void TestWebUI::AddRequestableScheme(const char* scheme) {
77   NOTIMPLEMENTED();
78   return;
79 }
80 
AddMessageHandler(std::unique_ptr<WebUIMessageHandler> handler)81 void TestWebUI::AddMessageHandler(
82     std::unique_ptr<WebUIMessageHandler> handler) {
83   handler->set_web_ui(this);
84   handler->RegisterMessages();
85   handlers_.push_back(std::move(handler));
86 }
87 
RegisterMessageCallback(base::StringPiece message,const MessageCallback & callback)88 void TestWebUI::RegisterMessageCallback(base::StringPiece message,
89                                         const MessageCallback& callback) {
90   message_callbacks_[message.as_string()].push_back(callback);
91 }
92 
CanCallJavascript()93 bool TestWebUI::CanCallJavascript() {
94   return true;
95 }
96 
CallJavascriptFunctionUnsafe(const std::string & function_name)97 void TestWebUI::CallJavascriptFunctionUnsafe(const std::string& function_name) {
98   call_data_.push_back(base::WrapUnique(new CallData(function_name)));
99   OnJavascriptCall(*call_data_.back());
100 }
101 
CallJavascriptFunctionUnsafe(const std::string & function_name,const base::Value & arg1)102 void TestWebUI::CallJavascriptFunctionUnsafe(const std::string& function_name,
103                                              const base::Value& arg1) {
104   call_data_.push_back(base::WrapUnique(new CallData(function_name)));
105   call_data_.back()->TakeAsArg1(arg1.CreateDeepCopy());
106   OnJavascriptCall(*call_data_.back());
107 }
108 
CallJavascriptFunctionUnsafe(const std::string & function_name,const base::Value & arg1,const base::Value & arg2)109 void TestWebUI::CallJavascriptFunctionUnsafe(const std::string& function_name,
110                                              const base::Value& arg1,
111                                              const base::Value& arg2) {
112   call_data_.push_back(base::WrapUnique(new CallData(function_name)));
113   call_data_.back()->TakeAsArg1(arg1.CreateDeepCopy());
114   call_data_.back()->TakeAsArg2(arg2.CreateDeepCopy());
115   OnJavascriptCall(*call_data_.back());
116 }
117 
CallJavascriptFunctionUnsafe(const std::string & function_name,const base::Value & arg1,const base::Value & arg2,const base::Value & arg3)118 void TestWebUI::CallJavascriptFunctionUnsafe(const std::string& function_name,
119                                              const base::Value& arg1,
120                                              const base::Value& arg2,
121                                              const base::Value& arg3) {
122   call_data_.push_back(base::WrapUnique(new CallData(function_name)));
123   call_data_.back()->TakeAsArg1(arg1.CreateDeepCopy());
124   call_data_.back()->TakeAsArg2(arg2.CreateDeepCopy());
125   call_data_.back()->TakeAsArg3(arg3.CreateDeepCopy());
126   OnJavascriptCall(*call_data_.back());
127 }
128 
CallJavascriptFunctionUnsafe(const std::string & function_name,const base::Value & arg1,const base::Value & arg2,const base::Value & arg3,const base::Value & arg4)129 void TestWebUI::CallJavascriptFunctionUnsafe(const std::string& function_name,
130                                              const base::Value& arg1,
131                                              const base::Value& arg2,
132                                              const base::Value& arg3,
133                                              const base::Value& arg4) {
134   call_data_.push_back(base::WrapUnique(new CallData(function_name)));
135   call_data_.back()->TakeAsArg1(arg1.CreateDeepCopy());
136   call_data_.back()->TakeAsArg2(arg2.CreateDeepCopy());
137   call_data_.back()->TakeAsArg3(arg3.CreateDeepCopy());
138   call_data_.back()->TakeAsArg4(arg4.CreateDeepCopy());
139   OnJavascriptCall(*call_data_.back());
140 }
141 
CallJavascriptFunctionUnsafe(const std::string & function_name,const std::vector<const base::Value * > & args)142 void TestWebUI::CallJavascriptFunctionUnsafe(
143     const std::string& function_name,
144     const std::vector<const base::Value*>& args) {
145   NOTREACHED();
146 }
147 
OnJavascriptCall(const CallData & call_data)148 void TestWebUI::OnJavascriptCall(const CallData& call_data) {
149   for (JavascriptCallObserver& observer : javascript_call_observers_)
150     observer.OnJavascriptFunctionCalled(call_data);
151 }
152 
153 std::vector<std::unique_ptr<WebUIMessageHandler>>*
GetHandlersForTesting()154 TestWebUI::GetHandlersForTesting() {
155   return &handlers_;
156 }
157 
CallData(const std::string & function_name)158 TestWebUI::CallData::CallData(const std::string& function_name)
159     : function_name_(function_name) {
160 }
161 
~CallData()162 TestWebUI::CallData::~CallData() {
163 }
164 
TakeAsArg1(std::unique_ptr<base::Value> arg)165 void TestWebUI::CallData::TakeAsArg1(std::unique_ptr<base::Value> arg) {
166   arg1_ = std::move(arg);
167 }
168 
TakeAsArg2(std::unique_ptr<base::Value> arg)169 void TestWebUI::CallData::TakeAsArg2(std::unique_ptr<base::Value> arg) {
170   arg2_ = std::move(arg);
171 }
172 
TakeAsArg3(std::unique_ptr<base::Value> arg)173 void TestWebUI::CallData::TakeAsArg3(std::unique_ptr<base::Value> arg) {
174   arg3_ = std::move(arg);
175 }
176 
TakeAsArg4(std::unique_ptr<base::Value> arg)177 void TestWebUI::CallData::TakeAsArg4(std::unique_ptr<base::Value> arg) {
178   arg4_ = std::move(arg);
179 }
180 
181 }  // namespace content
182