1// Copyright (c) 2011 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 "chrome/test/webdriver/commands/find_element_commands.h"
6
7#include "base/values.h"
8#include "chrome/test/webdriver/commands/response.h"
9#include "chrome/test/webdriver/webdriver_element_id.h"
10#include "chrome/test/webdriver/webdriver_error.h"
11#include "chrome/test/webdriver/webdriver_session.h"
12
13namespace webdriver {
14
15FindElementCommand::FindElementCommand(
16    const std::vector<std::string>& path_segments,
17    const DictionaryValue* const parameters,
18    const bool find_one_element)
19    : WebDriverCommand(path_segments, parameters),
20      find_one_element_(find_one_element) {}
21
22FindElementCommand::~FindElementCommand() {}
23
24bool FindElementCommand::DoesPost() {
25  return true;
26}
27
28void FindElementCommand::ExecutePost(Response* const response) {
29  std::string locator, query;
30  if (!GetStringParameter("using", &locator) ||
31      !GetStringParameter("value", &query)) {
32    response->SetError(new Error(
33        kBadRequest,
34        "Request is missing required 'using' and/or 'value' data"));
35    return;
36  }
37
38  if (locator == "class name") {
39    locator = LocatorType::kClassName;
40  } else if (locator == "css selector") {
41    locator = LocatorType::kCss;
42  } else if (locator == "link text") {
43    locator = LocatorType::kLinkText;
44  } else if (locator == "partial link text") {
45    locator = LocatorType::kPartialLinkText;
46  } else if (locator == "tag name") {
47    locator = LocatorType::kTagName;
48  }
49  // The other locators do not need conversion. If the client supplied an
50  // invalid locator, let it fail in the atom.
51
52  // Searching under a custom root if the URL pattern is
53  // "/session/$session/element/$id/element(s)"
54  ElementId root_element(GetPathVariable(4));
55
56  if (find_one_element_) {
57    ElementId element;
58    Error* error = session_->FindElement(
59        session_->current_target(), root_element, locator, query, &element);
60    if (error) {
61      response->SetError(error);
62      return;
63    }
64    response->SetValue(element.ToValue());
65  } else {
66    std::vector<ElementId> elements;
67    Error* error = session_->FindElements(
68        session_->current_target(), root_element, locator, query, &elements);
69    if (error) {
70      response->SetError(error);
71      return;
72    }
73    ListValue* element_list = new ListValue();
74    for (size_t i = 0; i < elements.size(); ++i)
75      element_list->Append(elements[i].ToValue());
76    response->SetValue(element_list);
77  }
78  response->SetStatus(kSuccess);
79}
80
81}  // namespace webdriver
82