Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(4808)

Unified Diff: chrome/test/chromedriver/window_commands.cc

Issue 12675002: [chromedriver] Implement command: executeAsyncScript and setScriptTimeout (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Address +5000 timeout problem. Created 7 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « chrome/test/chromedriver/window_commands.h ('k') | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: chrome/test/chromedriver/window_commands.cc
diff --git a/chrome/test/chromedriver/window_commands.cc b/chrome/test/chromedriver/window_commands.cc
index 54dca1e590cc7a28603a83d5911204e9ef1ce1eb..613b0fab0ec77350a3b132585022d9d96ab4a5d4 100644
--- a/chrome/test/chromedriver/window_commands.cc
+++ b/chrome/test/chromedriver/window_commands.cc
@@ -9,6 +9,8 @@
#include "base/callback.h"
#include "base/string_number_conversions.h"
#include "base/stringprintf.h"
+#include "base/threading/platform_thread.h"
+#include "base/time.h"
#include "base/values.h"
#include "chrome/test/chromedriver/basic_types.h"
#include "chrome/test/chromedriver/chrome.h"
@@ -184,6 +186,88 @@ Status ExecuteExecuteScript(
session->frame, "function(){" + script + "}", *args, value);
}
+Status ExecuteExecuteAsyncScript(
+ Session* session,
+ WebView* web_view,
+ const base::DictionaryValue& params,
+ scoped_ptr<base::Value>* value) {
+ std::string script;
+ if (!params.GetString("script", &script))
+ return Status(kUnknownError, "'script' must be a string");
+ const base::ListValue* script_args;
+ if (!params.GetList("args", &script_args))
+ return Status(kUnknownError, "'args' must be a list");
+
+ base::ListValue args;
+ args.AppendString(script);
+ args.Append(script_args->DeepCopy());
+ args.AppendInteger(session->script_timeout);
+ scoped_ptr<base::Value> tmp;
+ Status status = web_view->CallFunction(
+ session->frame, kExecuteAsyncScriptScript, args, &tmp);
+ if (status.IsError())
+ return status;
+
+ base::Time start_time = base::Time::Now();
+ base::ListValue args_tmp;
+ const char* kGetAndClearResult =
+ "function() {"
+ " var toReturn = {};"
+ " var info = document.chromedriverAsyncScriptInfo;"
+ " toReturn.finished = info.finished;"
+ " if (info.finished) {"
+ " toReturn.result = info.result;"
+ " delete info.result;"
+ " }"
+ " return toReturn;"
+ "}";
+ while (true) {
+ scoped_ptr<base::Value> result;
+ status = web_view->CallFunction(
+ session->frame, kGetAndClearResult, args_tmp, &result);
+ if (status.IsError()) {
+ if (status.code() == kNoSuchFrame)
+ return Status(kJavaScriptError, "page or frame unload", status);
+ return status;
+ }
+ const base::DictionaryValue* dict;
+ if (!result->GetAsDictionary(&dict))
+ return Status(kUnknownError, "failed to tell if script has finished");
+ bool finished = false;
+ if (!dict->GetBoolean("finished", &finished))
+ return Status(kUnknownError, "flag 'finished' is not returned");
+ if (finished) {
+ if (!dict->HasKey("result")) {
+ value->reset(base::Value::CreateNullValue());
+ } else {
+ const base::Value* script_result;
+ dict->Get("result", &script_result);
+ value->reset(script_result->DeepCopy());
+ }
+ return Status(kOk);
+ }
+
+ if ((base::Time::Now() - start_time).InMilliseconds() >=
+ session->script_timeout)
+ break;
+
+ base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(50));
+ }
+
+ // Clear the result if it is set, otherwise prevent the script to set result
+ // by increasing the id.
+ const char* kClearResultForTimeoutScript =
+ "var info = document.chromedriverAsyncScriptInfo;"
+ "info.id++;"
+ "delete info.result;";
+ web_view->EvaluateScript(session->frame, kClearResultForTimeoutScript, &tmp);
+
+ return Status(
+ kScriptTimeout,
+ base::StringPrintf("timed out waiting for result after %d ms",
+ session->script_timeout));
+}
+
Status ExecuteSwitchToFrame(
Session* session,
WebView* web_view,
« no previous file with comments | « chrome/test/chromedriver/window_commands.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698