// Licensed to the Software Freedom Conservancy (SFC) under one
// or more contributor license agreements. See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership. The SFC licenses this file
// to you under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "server.h"
#include <algorithm>
#include <cstdio>
#include <cstring>
#include <sstream>
#include "session.h"
#include "errorcodes.h"
#include "uri_info.h"
#include "logging.h"

#define SERVER_DEFAULT_PAGE "<html><head><title>WebDriver</title></head><body><p id='main'>This is the initial start page for the WebDriver server.</p></body></html>"
#define SERVER_DEFAULT_WHITELIST "127.0.0.1"
#define SERVER_DEFAULT_BLACKLIST "-0.0.0.0/0"
#define HTML_CONTENT_TYPE "text/html"
#define JSON_CONTENT_TYPE "application/json"

#if defined(WINDOWS)
#include <cstdarg>
inline int wd_snprintf(char* str, size_t size, const char* format, ...) {
  va_list args;
  va_start(args, format);
  int count = _vscprintf(format, args);
  if (str != NULL && size > 0) {
    count = _vsnprintf_s(str, size, _TRUNCATE, format, args);
  }
  va_end(args);
  return count;
}
#define snprintf wd_snprintf
#endif

namespace webdriver {

Server::Server(const int port) {
  this->Initialize(port, "", "", "", "");
}

Server::Server(const int port, const std::string& host) {
  this->Initialize(port, host, "", "", "");
}

Server::Server(const int port,
               const std::string& host,
               const std::string& log_level,
               const std::string& log_file) {
  this->Initialize(port, host, log_level, log_file, "");
}

Server::Server(const int port,
               const std::string& host,
               const std::string& log_level,
               const std::string& log_file,
               const std::string& acl) {
    this->Initialize(port, host, log_level, log_file, acl);
}

Server::~Server(void) {
  SessionMap::iterator it = this->sessions_.begin();
  for (; it != this->sessions_.end(); ++it) {
    std::string session_id = it->first;
    this->ShutDownSession(session_id);
  }
}

void Server::Initialize(const int port,
                        const std::string& host,
                        const std::string& log_level,
                        const std::string& log_file,
                        const std::string& acl) {
  LOG::Level(log_level);
  LOG::File(log_file);
  LOG(INFO) << "Starting WebDriver server on port: '"
            << port << "' on host: '" << host << "'";
  this->port_ = port;
  this->host_ = host;
  if (acl.size() > 0) {
    this->ProcessWhitelist(acl);
  }
  this->PopulateCommandRepository();
}

void Server::ProcessWhitelist(const std::string& whitelist) {
  std::string input_copy = whitelist;
  while (input_copy.size() > 0) {
    size_t delimiter_pos = input_copy.find(",");
    std::string token = input_copy.substr(0, delimiter_pos);
    if (delimiter_pos == std::string::npos) {
      input_copy = "";
    } else {
      input_copy = input_copy.substr(delimiter_pos + 1);
    }
    this->whitelist_.push_back(token);
  }
}

std::string Server::GetListeningPorts(const bool use_ipv6) {
  std::string port_format_string = "%s:%d";
  if (this->host_.size() == 0) {
    // If the host name is an empty string, then we want to bind
    // to the local loopback address on both IPv4 and IPv6 if we
    // can. Using the addresses in the listening port format string
    // will prevent connection from external IP addresses.
    port_format_string = "%s127.0.0.1:%d";
    if (use_ipv6) {
      port_format_string.append(",[::1]:%d");
    }
  } else if (this->whitelist_.size() > 0) {
    // If there are white-listed IP addresses, we can only use IPv4,
    // and we don't want the colon in the listening ports string.
    // Instead, we want to bind to all adapters, and use the access
    // control list to determine which addresses can connect. So to
    // remove the host from the format string, when we use printf to
    // format, the %s will be replaced by an empty string.
    port_format_string = "%s%d";
  }
  int formatted_string_size = snprintf(NULL,
                                       0,
                                       port_format_string.c_str(),
                                       this->host_.c_str(),
                                       this->port_,
                                       this->port_) + 1;
  std::vector<char> listening_ports_buffer(formatted_string_size);
  snprintf(&listening_ports_buffer[0],
           formatted_string_size,
           port_format_string.c_str(),
           this->host_.c_str(),
           this->port_,
           this->port_);
  return &listening_ports_buffer[0];
}

std::string Server::GetAccessControlList() {
  std::string acl = "";
  if (this->whitelist_.size() > 0) {
    acl = SERVER_DEFAULT_BLACKLIST;
    for (std::vector<std::string>::const_iterator it = this->whitelist_.begin();
      it < this->whitelist_.end();
      ++it) {
      acl.append(",+").append(*it);
    }
    LOG(DEBUG) << "Civetweb ACL is " << acl;
  }
  return acl;
}

void Server::GenerateOptionsList(std::vector<const char*>* options) {
  std::map<std::string, std::string>::const_iterator it = this->options_.begin();
  for (; it != this->options_.end(); ++it) {
    options->push_back(it->first.c_str());
    options->push_back(it->second.c_str());
  }
  options->push_back(NULL);
}

int Server::OnNewHttpRequest(struct mg_connection* conn) {
  mg_context* context = mg_get_context(conn);
  Server* current_server = reinterpret_cast<Server*>(mg_get_user_data(context));
  const mg_request_info* request_info = mg_get_request_info(conn);
  int handler_result_code = current_server->ProcessRequest(conn, request_info);
  return handler_result_code;
}

bool Server::Start() {
  LOG(TRACE) << "Entering Server::Start";

  std::string listening_port_option = this->GetListeningPorts(true);
  this->options_["listening_ports"] = listening_port_option;

  std::string acl_option = this->GetAccessControlList();
  if (acl_option.size() > 0) {
    this->options_["access_control_list"] = acl_option;
  }

  this->options_["enable_keep_alive"] = "yes";

  std::vector<const char*> options;
  this->GenerateOptionsList(&options);

  mg_callbacks callbacks = {};
  callbacks.begin_request = &OnNewHttpRequest;
  context_ = mg_start(&callbacks, this, &options[0]);
  if (context_ == NULL) {
    std::string ipv4_port_option = this->GetListeningPorts(false);
    if (listening_port_option == ipv4_port_option) {
      // If the IPv4 and IPv6 versions of the port option string
      // are equal, then either a host to bind to or an ACL was
      // specified, so there is no need to retry.
      LOG(WARN) << "Failed to start Civetweb";
      return false;
    } else {
      // If we fail, a host and ACL aren't specified, we might not
      // be able to bind to an IPv6 address. Try again to bind to
      // the IPv4 loopback only.
      LOG(INFO) << "Failed first attempt to start Civetweb. Attempt start with IPv4 only";
      this->options_["listening_ports"] = listening_port_option;
      options.clear();
      this->GenerateOptionsList(&options);
      context_ = mg_start(&callbacks, this, &options[0]);
      if (context_ == NULL) {
        LOG(WARN) << "Failed to start Civetweb";
        return false;
      }
    }
  }
  return true;
}

void Server::Stop() {
  LOG(TRACE) << "Entering Server::Stop";
  if (context_) {
    mg_stop(context_);
    context_ = NULL;
  }
}

int Server::ProcessRequest(struct mg_connection* conn,
    const struct mg_request_info* request_info) {
  LOG(TRACE) << "Entering Server::ProcessRequest";

  int http_response_code = 0;
  std::string http_verb = request_info->request_method;
  std::string request_body = "{}";
  if (http_verb == "POST") {
    request_body = this->ReadRequestBody(conn, request_info);
  }

  LOG(TRACE) << "Process request with:"
             << " URI: "  << request_info->local_uri
             << " HTTP verb: " << http_verb << std::endl
             << "body: " << request_body;

  if (strcmp(request_info->local_uri, "/") == 0) {
    this->SendHttpOk(conn,
                     request_info,
                     SERVER_DEFAULT_PAGE,
                     HTML_CONTENT_TYPE);
    http_response_code = 0;
  } else if (strcmp(request_info->local_uri, "/shutdown") == 0) {
    this->SendHttpOk(conn,
                     request_info,
                     SERVER_DEFAULT_PAGE,
                     HTML_CONTENT_TYPE);
    http_response_code = 0;
    this->ShutDown();
  } else {
    std::string serialized_response = this->DispatchCommand(request_info->local_uri,
                                                            http_verb,
                                                            request_body);
    http_response_code = this->SendResponseToClient(conn,
                                                    request_info,
                                                    serialized_response);
  }

  return http_response_code;
}

void Server::AddCommand(const std::string& url,
                        const std::string& http_verb,
                        const std::string& command_name) {
  if (this->commands_.find(url) == this->commands_.end()) {
    this->commands_[url] = std::shared_ptr<UriInfo>(
        new UriInfo(url, http_verb, command_name));
  } else {
    this->commands_[url]->AddHttpVerb(http_verb, command_name);
  }
}

void Server::ShutDownSession(const std::string& session_id) {
  LOG(TRACE) << "Entering Server::ShutDownSession";

  SessionMap::iterator it = this->sessions_.find(session_id);
  if (it != this->sessions_.end()) {
    it->second->ShutDown();
    this->sessions_.erase(session_id);
  } else {
    LOG(DEBUG) << "Shutdown session is not found";
  }
}

std::string Server::ReadRequestBody(struct mg_connection* conn,
    const struct mg_request_info* request_info) {
  LOG(TRACE) << "Entering Server::ReadRequestBody";

  std::string request_body = "";
  int content_length = 0;
  for (int header_index = 0; header_index < 64; ++header_index) {
    if (request_info->http_headers[header_index].name == NULL) {
      break;
    }
    std::string header_name(request_info->http_headers[header_index].name);
    std::transform(header_name.begin(),
                   header_name.end(),
                   header_name.begin(),
                   ::tolower);
    if (header_name.compare("content-length") == 0) {
      content_length = atoi(request_info->http_headers[header_index].value);
      break;
    }
  }
  if (content_length != 0) {
    std::vector<char> buffer(content_length + 1);
    int bytes_read = 0;
    while (bytes_read < content_length) {
      bytes_read += mg_read(conn,
                            &buffer[bytes_read],
                            content_length - bytes_read);
    }
    buffer[content_length] = '\0';
    request_body.append(&buffer[0]);
  }

  return request_body;
}

std::string Server::DispatchCommand(const std::string& uri,
                                     const std::string& http_verb,
                                     const std::string& command_body) {
  LOG(TRACE) << "Entering Server::DispatchCommand";

  std::string session_id = "";
  std::string locator_parameters = "";
  std::string serialized_response = "";
  std::string command = this->LookupCommand(uri,
                                            http_verb,
                                            &session_id,
                                            &locator_parameters);
  LOG(DEBUG) << "Command: " << http_verb << " " << uri << " " << command_body;

  if (command == webdriver::CommandType::NoCommand) {
    Response invalid_command_response;
    if (locator_parameters.size() > 0) {
      std::string unknown_method_body = "Invalid method requested: ";
      unknown_method_body.append(http_verb);
      unknown_method_body.append(" is not a valid HTTP verb for ");
      unknown_method_body.append(uri);
      unknown_method_body.append("; acceptable verbs are: ");
      unknown_method_body.append(locator_parameters);
      invalid_command_response.SetErrorResponse(ERROR_UNKNOWN_METHOD,
                                                unknown_method_body);
      invalid_command_response.AddAdditionalData("verbs", locator_parameters);
    } else {
      std::string unknown_command_body = "Command not found: ";
      unknown_command_body.append(http_verb);
      unknown_command_body.append(" ");
      unknown_command_body.append(uri);
      invalid_command_response.SetErrorResponse(ERROR_UNKNOWN_COMMAND,
                                                unknown_command_body);
    }
    serialized_response = invalid_command_response.Serialize();
  } else if (command == webdriver::CommandType::Status) {
    // Status command must be handled by the server, not by the session.
    serialized_response = this->GetStatus();
  } else if (command == webdriver::CommandType::GetSessionList) {
    // GetSessionList command must be handled by the server,
    // not by the session.
    serialized_response = this->ListSessions();
  } else {
    SessionHandle session_handle;
    if (command != webdriver::CommandType::NewSession &&
        !this->LookupSession(session_id, &session_handle)) {
      if (command == webdriver::CommandType::Quit) {
        // Calling quit on an invalid session should be a no-op.
        // Hand-code the response for quit on an invalid (already
        // quit) session.
        serialized_response.append("{ \"value\" : null }");
      } else {
        Response invalid_session_id_response;
        std::string invalid_session_message = "session ";
        invalid_session_message.append(session_id);
        invalid_session_message.append(" does not exist");
        invalid_session_id_response.SetErrorResponse(ERROR_INVALID_SESSION_ID,
                                                     invalid_session_message);
        serialized_response = invalid_session_id_response.Serialize();
      }
    } else {
      if (command == webdriver::CommandType::NewSession &&
          this->sessions_.size() > 0) {
        std::string session_exists_message = "Only one session may ";
        session_exists_message.append("be created at a time, and a ");
        session_exists_message.append("session already exists.");
        Response session_exists_response;
        session_exists_response.SetErrorResponse(ERROR_SESSION_NOT_CREATED,
                                                 session_exists_message);
        serialized_response = session_exists_response.Serialize();
      } else {
        // Compile the serialized JSON representation of the command by hand.
        std::string serialized_command = "{ \"name\" : \"" + command + "\"";
        serialized_command.append(", \"locator\" : ");
        serialized_command.append(locator_parameters);
        serialized_command.append(", \"parameters\" : ");
        serialized_command.append(command_body);
        serialized_command.append(" }");
        if (command == webdriver::CommandType::NewSession) {
          session_handle = this->InitializeSession();
        }
        bool session_is_valid = session_handle->ExecuteCommand(
            serialized_command,
            &serialized_response);
        if (command == webdriver::CommandType::NewSession) {
          Response new_session_response;
          new_session_response.Deserialize(serialized_response);
          this->sessions_[new_session_response.GetSessionId()] = session_handle;
        }
        if (!session_is_valid) {
          this->ShutDownSession(session_id);
        }
      }
    }
  }
  LOG(DEBUG) << "Response: " << serialized_response;
  return serialized_response;
}

std::string Server::ListSessions() {
  LOG(TRACE) << "Entering Server::ListSessions";

  // Manually construct the serialized command for getting 
  // session capabilities.
  std::string get_caps_command = "{ \"name\" : \"" + 
                                 webdriver::CommandType::GetSessionCapabilities
                                 + "\"" +
                                 ", \"locator\" : {}, \"parameters\" : {} }";

  Json::Value sessions(Json::arrayValue);
  SessionMap::iterator it = this->sessions_.begin();
  for (; it != this->sessions_.end(); ++it) {
    // Each element of the GetSessionList command is an object with two
    // named properties, "id" and "capabilities". We already know the
    // ID, so we execute the GetSessionCapabilities command on each session
    // to be able to return the capabilities.
    Json::Value session_descriptor;
    session_descriptor["id"] = it->first;

    SessionHandle session = it->second;
    std::string serialized_session_response;
    session->ExecuteCommand(get_caps_command, &serialized_session_response);

    Response session_response;
    session_response.Deserialize(serialized_session_response);
    session_descriptor["capabilities"] = session_response.value();
    sessions.append(session_descriptor);
  }
  Response response;
  response.SetSuccessResponse(sessions);
  return response.Serialize();
}

bool Server::LookupSession(const std::string& session_id,
                           SessionHandle* session_handle) {
  LOG(TRACE) << "Entering Server::LookupSession";

  SessionMap::iterator it = this->sessions_.find(session_id);
  if (it == this->sessions_.end()) {
    return false;
  }
  *session_handle = it->second;
  return true;
}

int Server::SendResponseToClient(struct mg_connection* conn,
                                 const struct mg_request_info* request_info,
                                 const std::string& serialized_response) {
  LOG(TRACE) << "Entering Server::SendResponseToClient";

  int return_code = 0;
  if (serialized_response.size() > 0) {
    Response response;
    response.Deserialize(serialized_response);
    return_code = response.GetHttpResponseCode();
    if (return_code == 0) {
      this->SendHttpOk(conn,
                       request_info,
                       serialized_response,
                       HTML_CONTENT_TYPE);
      return_code = 200;
    } else if (return_code == 200) {
      this->SendHttpOk(conn,
                       request_info,
                       serialized_response,
                       JSON_CONTENT_TYPE);
    } else if (return_code == 303) {
      std::string location = response.value().asString();
      response.SetSuccessResponse(response.value());
      this->SendHttpSeeOther(conn, request_info, location);
      return_code = 303;
    } else if (return_code == 400) {
      this->SendHttpBadRequest(conn, request_info, serialized_response);
      return_code = 400;
    } else if (return_code == 404) {
      this->SendHttpNotFound(conn, request_info, serialized_response);
      return_code = 404;
    } else if (return_code == 405) {
      std::string allowed_verbs = "";
      Json::Value additional_data = response.additional_data();
      if (additional_data.isObject() && additional_data.isMember("verbs")) {
        allowed_verbs = additional_data["verbs"].asString();
      }
      this->SendHttpMethodNotAllowed(conn,
                                     request_info,
                                     allowed_verbs,
                                     serialized_response);
      return_code = 405;
    } else if (return_code == 501) {
      this->SendHttpNotImplemented(conn,
                                   request_info,
                                   "");
      return_code = 501;
    } else {
      this->SendHttpInternalError(conn, request_info, serialized_response);
      return_code = 500;
    }
  }
  return return_code;
}

// The standard HTTP Status codes are implemented below.  Chrome uses
// OK, See Other, Not Found, Method Not Allowed, and Internal Error.
// Internal Error, HTTP 500, is used as a catch all for any issue
// not covered in the JSON protocol.
void Server::SendHttpOk(struct mg_connection* connection,
                        const struct mg_request_info* request_info,
                        const std::string& body,
                        const std::string& content_type) {
  LOG(TRACE) << "Entering Server::SendHttpOk";

  std::string body_to_send = body + "\r\n";

  std::ostringstream out;
  out << "HTTP/1.1 200 OK\r\n"
      << "Content-Length: " << strlen(body_to_send.c_str()) << "\r\n"
      << "Content-Type: " << content_type << "; charset=utf-8\r\n"
      << "Cache-Control: no-cache\r\n"
      << "Vary: Accept-Charset, Accept-Encoding, Accept-Language, Accept\r\n"
      << "Accept-Ranges: bytes\r\n\r\n";
  if (strcmp(request_info->request_method, "HEAD") != 0) {
    out << body_to_send;
  }

  mg_write(connection, out.str().c_str(), out.str().size());
}

void Server::SendHttpBadRequest(struct mg_connection* const connection,
                                const struct mg_request_info* request_info,
                                const std::string& body) {
  LOG(TRACE) << "Entering Server::SendHttpBadRequest";

  std::string body_to_send = body + "\r\n";

  std::ostringstream out;
  out << "HTTP/1.1 400 Bad Request\r\n"
      << "Content-Length: " << strlen(body_to_send.c_str()) << "\r\n"
      << "Content-Type: application/json; charset=utf-8\r\n"
      << "Cache-Control: no-cache\r\n"
      << "Vary: Accept-Charset, Accept-Encoding, Accept-Language, Accept\r\n"
      << "Accept-Ranges: bytes\r\n\r\n";
  if (strcmp(request_info->request_method, "HEAD") != 0) {
    out << body_to_send;
  }

  mg_printf(connection, "%s", out.str().c_str());
}

void Server::SendHttpInternalError(struct mg_connection* connection,
                                   const struct mg_request_info* request_info,
                                   const std::string& body) {
  LOG(TRACE) << "Entering Server::SendHttpInternalError";

  std::string body_to_send = body + "\r\n";

  std::ostringstream out;
  out << "HTTP/1.1 500 Internal Server Error\r\n"
      << "Content-Length: " << strlen(body_to_send.c_str()) << "\r\n"
      << "Content-Type: application/json; charset=utf-8\r\n"
      << "Cache-Control: no-cache\r\n"
      << "Vary: Accept-Charset, Accept-Encoding, Accept-Language, Accept\r\n"
      << "Accept-Ranges: bytes\r\n\r\n";
  if (strcmp(request_info->request_method, "HEAD") != 0) {
    out << body_to_send;
  }

  mg_write(connection, out.str().c_str(), out.str().size());
}

void Server::SendHttpNotFound(struct mg_connection* const connection,
                              const struct mg_request_info* request_info,
                              const std::string& body) {
  LOG(TRACE) << "Entering Server::SendHttpNotFound";

  std::string body_to_send = body + "\r\n";

  std::ostringstream out;
  out << "HTTP/1.1 404 Not Found\r\n"
      << "Content-Length: " << strlen(body_to_send.c_str()) << "\r\n"
      << "Content-Type: application/json; charset=utf-8\r\n"
      << "Cache-Control: no-cache\r\n"
      << "Vary: Accept-Charset, Accept-Encoding, Accept-Language, Accept\r\n"
      << "Accept-Ranges: bytes\r\n\r\n";
  if (strcmp(request_info->request_method, "HEAD") != 0) {
    out << body_to_send;
  }

  mg_printf(connection, "%s", out.str().c_str());
}

void Server::SendHttpMethodNotAllowed(
    struct mg_connection* connection,
    const struct mg_request_info* request_info,
    const std::string& allowed_methods,
    const std::string& body) {
  LOG(TRACE) << "Entering Server::SendHttpMethodNotAllowed";

  std::string body_to_send = body + "\r\n";

  std::ostringstream out;
  out << "HTTP/1.1 405 Method Not Allowed\r\n"
      << "Content-Type: text/html\r\n"
      << "Content-Length: " << strlen(body_to_send.c_str()) << "\r\n"
      << "Allow: " << allowed_methods << "\r\n\r\n";
  if (strcmp(request_info->request_method, "HEAD") != 0) {
    out << body_to_send;
  }

  mg_write(connection, out.str().c_str(), out.str().size());
}

void Server::SendHttpTimeout(struct mg_connection* connection,
                             const struct mg_request_info* request_info,
                             const std::string& body) {
  LOG(TRACE) << "Entering Server::SendHttpTimeout";

  std::ostringstream out;
  out << "HTTP/1.1 408 Timeout\r\n\r\n"
      << "Content-Length: " << strlen(body.c_str()) << "\r\n"
      << "Content-Type: application/json; charset=utf-8\r\n"
      << "Cache-Control: no-cache\r\n"
      << "Vary: Accept-Charset, Accept-Encoding, Accept-Language, Accept\r\n"
      << "Accept-Ranges: bytes\r\n\r\n";

  mg_write(connection, out.str().c_str(), out.str().size());
}

void Server::SendHttpNotImplemented(struct mg_connection* connection,
                                    const struct mg_request_info* request_info,
                                    const std::string& body) {
  LOG(TRACE) << "Entering Server::SendHttpNotImplemented";

  std::ostringstream out;
  out << "HTTP/1.1 501 Not Implemented\r\n\r\n";

  mg_write(connection, out.str().c_str(), out.str().size());
}

void Server::SendHttpSeeOther(struct mg_connection* connection,
                              const struct mg_request_info* request_info,
                              const std::string& location) {
  LOG(TRACE) << "Entering Server::SendHttpSeeOther";

  std::ostringstream out;
  out << "HTTP/1.1 303 See Other\r\n"
      << "Location: " << location << "\r\n"
      << "Content-Type: text/html\r\n"
      << "Content-Length: 0\r\n\r\n";

  mg_write(connection, out.str().c_str(), out.str().size());
}

std::string Server::LookupCommand(const std::string& uri,
                                  const std::string& http_verb,
                                  std::string* session_id,
                                  std::string* locator) {
  LOG(TRACE) << "Entering Server::LookupCommand";

  std::string value = webdriver::CommandType::NoCommand;
  std::vector<std::string> url_fragments;
  UriInfo::ParseUri(uri, &url_fragments, NULL);
  UrlMap::const_iterator it = this->commands_.begin();
  for (; it != this->commands_.end(); ++it) {
    std::vector<std::string> locator_param_names;
    std::vector<std::string> locator_param_values;
    if (it->second->IsUriMatch(url_fragments,
                               &locator_param_names,
                               &locator_param_values)) {
      if (it->second->HasHttpVerb(http_verb, &value)) {
        std::string param = this->ConstructLocatorParameterJson(
            locator_param_names, locator_param_values, session_id);
        locator->append(param);
      } else {
        locator->append(it->second->GetSupportedVerbs());
      }
      break;
    }
  }
  return value;
}

std::string Server::ConstructLocatorParameterJson(
    std::vector<std::string> locator_param_names, 
    std::vector<std::string> locator_param_values,
    std::string* session_id) {
  std::string param = "{";
  size_t param_count = locator_param_names.size();
  for (unsigned int i = 0; i < param_count; i++) {
    if (i != 0) {
      param.append(",");
    }

    param.append(" \"");
    param.append(locator_param_names[i]);
    param.append("\" : \"");
    param.append(locator_param_values[i]);
    param.append("\"");
    if (locator_param_names[i] == "sessionid") {
      session_id->append(locator_param_values[i]);
    }
  }

  param.append(" }");
  return param;
}

void Server::PopulateCommandRepository() {
  LOG(TRACE) << "Entering Server::PopulateCommandRepository";

  this->AddCommand("/session", "POST",  webdriver::CommandType::NewSession);
  this->AddCommand("/session/:sessionid", "DELETE",  webdriver::CommandType::Quit);
  this->AddCommand("/status", "GET", webdriver::CommandType::Status);
  this->AddCommand("/session/:sessionid/timeouts", "GET", webdriver::CommandType::GetTimeouts);
  this->AddCommand("/session/:sessionid/timeouts", "POST", webdriver::CommandType::SetTimeouts);
  this->AddCommand("/session/:sessionid/url", "GET",  webdriver::CommandType::GetCurrentUrl);
  this->AddCommand("/session/:sessionid/url", "POST",  webdriver::CommandType::Get);
  this->AddCommand("/session/:sessionid/back", "POST",  webdriver::CommandType::GoBack);
  this->AddCommand("/session/:sessionid/forward", "POST",  webdriver::CommandType::GoForward);
  this->AddCommand("/session/:sessionid/refresh", "POST",  webdriver::CommandType::Refresh);
  this->AddCommand("/session/:sessionid/title", "GET",  webdriver::CommandType::GetTitle);
  this->AddCommand("/session/:sessionid/window", "GET",  webdriver::CommandType::GetCurrentWindowHandle);
  this->AddCommand("/session/:sessionid/window", "POST",  webdriver::CommandType::SwitchToWindow);
  this->AddCommand("/session/:sessionid/window", "DELETE",  webdriver::CommandType::CloseWindow);
  this->AddCommand("/session/:sessionid/window/handles", "GET",  webdriver::CommandType::GetWindowHandles);
  this->AddCommand("/session/:sessionid/window/new", "POST",  webdriver::CommandType::NewWindow);
  this->AddCommand("/session/:sessionid/frame", "POST",  webdriver::CommandType::SwitchToFrame);
  this->AddCommand("/session/:sessionid/frame/parent", "POST",  webdriver::CommandType::SwitchToParentFrame);
  this->AddCommand("/session/:sessionid/window/rect", "GET", webdriver::CommandType::GetWindowRect);
  this->AddCommand("/session/:sessionid/window/rect", "POST", webdriver::CommandType::SetWindowRect);
  this->AddCommand("/session/:sessionid/window/maximize", "POST", webdriver::CommandType::MaximizeWindow);
  this->AddCommand("/session/:sessionid/window/minimize", "POST", webdriver::CommandType::MinimizeWindow);
  this->AddCommand("/session/:sessionid/window/fullscreen", "POST", webdriver::CommandType::FullscreenWindow);
  this->AddCommand("/session/:sessionid/element/active", "GET",  webdriver::CommandType::GetActiveElement);
  this->AddCommand("/session/:sessionid/element", "POST",  webdriver::CommandType::FindElement);
  this->AddCommand("/session/:sessionid/elements", "POST",  webdriver::CommandType::FindElements);
  this->AddCommand("/session/:sessionid/element/:id/element", "POST",  webdriver::CommandType::FindChildElement);
  this->AddCommand("/session/:sessionid/element/:id/elements", "POST",  webdriver::CommandType::FindChildElements);
  this->AddCommand("/session/:sessionid/element/:id/selected", "GET",  webdriver::CommandType::IsElementSelected);
  this->AddCommand("/session/:sessionid/element/:id/attribute/:name", "GET", webdriver::CommandType::GetElementAttribute);
  this->AddCommand("/session/:sessionid/element/:id/property/:name", "GET", webdriver::CommandType::GetElementProperty);
  this->AddCommand("/session/:sessionid/element/:id/css/:propertyName", "GET",  webdriver::CommandType::GetElementValueOfCssProperty);
  this->AddCommand("/session/:sessionid/element/:id/text", "GET",  webdriver::CommandType::GetElementText);
  this->AddCommand("/session/:sessionid/element/:id/name", "GET",  webdriver::CommandType::GetElementTagName);
  this->AddCommand("/session/:sessionid/element/:id/rect", "GET", webdriver::CommandType::GetElementRect);
  this->AddCommand("/session/:sessionid/element/:id/enabled", "GET",  webdriver::CommandType::IsElementEnabled);
  this->AddCommand("/session/:sessionid/element/:id/click", "POST",  webdriver::CommandType::ClickElement);
  this->AddCommand("/session/:sessionid/element/:id/clear", "POST",  webdriver::CommandType::ClearElement);
  this->AddCommand("/session/:sessionid/element/:id/value", "POST",  webdriver::CommandType::SendKeysToElement);
  this->AddCommand("/session/:sessionid/source", "GET",  webdriver::CommandType::GetPageSource);
  this->AddCommand("/session/:sessionid/execute/sync", "POST",  webdriver::CommandType::ExecuteScript);
  this->AddCommand("/session/:sessionid/execute/async", "POST",  webdriver::CommandType::ExecuteAsyncScript);
  this->AddCommand("/session/:sessionid/cookie", "GET",  webdriver::CommandType::GetAllCookies);
  this->AddCommand("/session/:sessionid/cookie/:name", "GET", webdriver::CommandType::GetNamedCookie);
  this->AddCommand("/session/:sessionid/cookie", "POST",  webdriver::CommandType::AddCookie);
  this->AddCommand("/session/:sessionid/cookie", "DELETE",  webdriver::CommandType::DeleteAllCookies);
  this->AddCommand("/session/:sessionid/cookie/:name", "DELETE",  webdriver::CommandType::DeleteNamedCookie);
  this->AddCommand("/session/:sessionid/actions", "POST", webdriver::CommandType::Actions);
  this->AddCommand("/session/:sessionid/actions", "DELETE", webdriver::CommandType::ReleaseActions);
  this->AddCommand("/session/:sessionid/alert/dismiss", "POST",  webdriver::CommandType::DismissAlert);
  this->AddCommand("/session/:sessionid/alert/accept", "POST",  webdriver::CommandType::AcceptAlert);
  this->AddCommand("/session/:sessionid/alert/text", "GET",  webdriver::CommandType::GetAlertText);
  this->AddCommand("/session/:sessionid/alert/text", "POST",  webdriver::CommandType::SendKeysToAlert);
  this->AddCommand("/session/:sessionid/screenshot", "GET", webdriver::CommandType::Screenshot);
  this->AddCommand("/session/:sessionid/element/:id/screenshot", "GET", webdriver::CommandType::ElementScreenshot);

  // Additional commands required to be supported, but not defined
  // in the specification.
  this->AddCommand("/session/:sessionid/alert/credentials", "POST",  webdriver::CommandType::SetAlertCredentials);
  this->AddCommand("/session/:sessionid/element/:id/displayed", "GET",  webdriver::CommandType::IsElementDisplayed);
  this->AddCommand("/session/:sessionid/element/:id/equals/:other", "GET",  webdriver::CommandType::ElementEquals);
  this->AddCommand("/sessions", "GET",  webdriver::CommandType::GetSessionList);
  this->AddCommand("/session/:sessionid", "GET",  webdriver::CommandType::GetSessionCapabilities);

  this->AddCommand("/session/:sessionid/ime/available_engines", "GET",  webdriver::CommandType::ListAvailableImeEngines);
  this->AddCommand("/session/:sessionid/ime/active_engines", "GET",  webdriver::CommandType::GetActiveImeEngine);
  this->AddCommand("/session/:sessionid/ime/activated", "GET",  webdriver::CommandType::IsImeActivated);
  this->AddCommand("/session/:sessionid/ime/activate", "POST",  webdriver::CommandType::ActivateImeEngine);
  this->AddCommand("/session/:sessionid/ime/deactivate", "POST",  webdriver::CommandType::DeactivateImeEngine);
}

}  // namespace webdriver
