// Copyright 2014 The Chromium OS Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "buffet/url_utils.h"

#include <algorithm>

namespace {
// Given a URL string, determine where the query string starts and ends.
// URLs have schema, domain and path (along with possible user name, password
// and port number which are of no interest for us here) which could optionally
// have a query string that is separated from the path by '?'. Finally, the URL
// could also have a '#'-separated URL fragment which is usually used by the
// browser as a bookmark element. So, for example:
//    http://server.com/path/to/object?k=v&foo=bar#fragment
// Here:
//    http://server.com/path/to/object - is the URL of the object,
//    ?k=v&foo=bar                     - URL query string
//    #fragment                        - URL fragment string
// If |exclude_fragment| is true, the function returns the start character and
// the length of the query string alone. If it is false, the query string length
// will include both the query string and the fragment.
bool GetQueryStringPos(const std::string& url, bool exclude_fragment,
                       size_t* query_pos, size_t* query_len) {
  size_t query_start = url.find_first_of("?#");
  if (query_start == std::string::npos) {
    *query_pos = url.size();
    if (query_len)
      *query_len = 0;
    return false;
  }

  *query_pos = query_start;
  if (query_len) {
    size_t query_end = url.size();

    if (exclude_fragment) {
      if (url[query_start] == '?') {
        size_t pos_fragment = url.find('#', query_start);
        if (pos_fragment != std::string::npos)
          query_end = pos_fragment;
      } else {
        query_end = query_start;
      }
    }
    *query_len = query_end - query_start;
  }
  return true;
}
}  // anonymous namespace

namespace buffet {

std::string url::TrimOffQueryString(std::string* url) {
  size_t query_pos;
  if (!GetQueryStringPos(*url, false, &query_pos, nullptr))
    return std::string();
  std::string query_string = url->substr(query_pos);
  url->resize(query_pos);
  return query_string;
}

std::string url::Combine(
    const std::string& url, const std::string& subpath) {
  return CombineMultiple(url, {subpath});
}

std::string url::CombineMultiple(
    const std::string& url, const std::vector<std::string>& parts) {
  std::string result = url;
  if (!parts.empty()) {
    std::string query_string = TrimOffQueryString(&result);
    for (const auto& part : parts) {
      if (!part.empty()) {
        if (!result.empty() && result.back() != '/')
          result += '/';
        size_t non_slash_pos = part.find_first_not_of('/');
        if (non_slash_pos != std::string::npos)
          result += part.substr(non_slash_pos);
      }
    }
    result += query_string;
  }
  return result;
}

std::string url::GetQueryString(
    const std::string& url, bool remove_fragment) {
  std::string query_string;
  size_t query_pos, query_len;
  if (GetQueryStringPos(url, remove_fragment, &query_pos, &query_len)) {
    query_string = url.substr(query_pos, query_len);
  }
  return query_string;
}

data_encoding::WebParamList url::GetQueryStringParameters(
    const std::string& url) {
  // Extract the query string and remove the leading '?'.
  std::string query_string = GetQueryString(url, true);
  if (!query_string.empty() && query_string.front() == '?')
    query_string.erase(query_string.begin());
  return data_encoding::WebParamsDecode(query_string);
}

std::string url::GetQueryStringValue(
    const std::string& url, const std::string& name) {
  return GetQueryStringValue(GetQueryStringParameters(url), name);
}

std::string url::GetQueryStringValue(
    const data_encoding::WebParamList& params,
    const std::string& name) {
  for (const auto& pair : params) {
    if (name.compare(pair.first) == 0)
      return pair.second;
  }
  return std::string();
}

std::string url::RemoveQueryString(
    const std::string& url, bool remove_fragment_too) {
  size_t query_pos, query_len;
  if (!GetQueryStringPos(url, !remove_fragment_too, &query_pos, &query_len))
    return url;
  std::string result = url.substr(0, query_pos);
  size_t fragment_pos = query_pos + query_len;
  if (fragment_pos < url.size()) {
    result += url.substr(fragment_pos);
  }
  return result;
}

std::string url::AppendQueryParam(
    const std::string& url, const std::string& name, const std::string& value) {
  return AppendQueryParams(url, {{name, value}});
}

std::string url::AppendQueryParams(
    const std::string& url,
    const data_encoding::WebParamList& params) {
  if (params.empty())
    return url;
  size_t query_pos, query_len;
  GetQueryStringPos(url, true, &query_pos, &query_len);
  size_t fragment_pos = query_pos + query_len;
  std::string result = url.substr(0, fragment_pos);
  if (query_len == 0) {
    result += '?';
  } else if (query_len > 1) {
    result += '&';
  }
  result += data_encoding::WebParamsEncode(params);
  if (fragment_pos < url.size()) {
    result += url.substr(fragment_pos);
  }
  return result;
}

bool url::HasQueryString(const std::string& url) {
  size_t query_pos, query_len;
  GetQueryStringPos(url, true, &query_pos, &query_len);
  return (query_len > 0);
}

}  // namespace buffet
