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

#include "url/gurl.h"

#include <stddef.h>

#include <algorithm>
#include <memory>
#include <ostream>
#include <utility>

#include "polyfills/base/check_op.h"
#include "base/no_destructor.h"
#include "base/strings/string_piece.h"
#include "base/strings/string_util.h"
#include "polyfills/base/trace_event/memory_usage_estimator.h"
#include "polyfills/third_party/perfetto/include/perfetto/tracing/traced_value.h"
#include "url/url_canon_stdstring.h"
#include "url/url_util.h"

GURL::GURL() : is_valid_(false) {
}

GURL::GURL(const GURL& other)
    : spec_(other.spec_),
      is_valid_(other.is_valid_),
      parsed_(other.parsed_) {
  if (other.inner_url_)
    inner_url_ = std::make_unique<GURL>(*other.inner_url_);
  // Valid filesystem urls should always have an inner_url_.
  GURL_DCHECK(!is_valid_ || !SchemeIsFileSystem() || inner_url_);
}

GURL::GURL(GURL&& other) noexcept
    : spec_(std::move(other.spec_)),
      is_valid_(other.is_valid_),
      parsed_(other.parsed_),
      inner_url_(std::move(other.inner_url_)) {
  other.is_valid_ = false;
  other.parsed_ = url::Parsed();
}

GURL::GURL(gurl_base::StringPiece url_string) {
  InitCanonical(url_string, true);
}

GURL::GURL(gurl_base::StringPiece16 url_string) {
  InitCanonical(url_string, true);
}

GURL::GURL(const std::string& url_string, RetainWhiteSpaceSelector) {
  InitCanonical(url_string, false);
}

GURL::GURL(const char* canonical_spec,
           size_t canonical_spec_len,
           const url::Parsed& parsed,
           bool is_valid)
    : spec_(canonical_spec, canonical_spec_len),
      is_valid_(is_valid),
      parsed_(parsed) {
  InitializeFromCanonicalSpec();
}

GURL::GURL(std::string canonical_spec, const url::Parsed& parsed, bool is_valid)
    : spec_(std::move(canonical_spec)), is_valid_(is_valid), parsed_(parsed) {
  InitializeFromCanonicalSpec();
}

template <typename T, typename CharT>
void GURL::InitCanonical(T input_spec, bool trim_path_end) {
  url::StdStringCanonOutput output(&spec_);
  is_valid_ = url::Canonicalize(
      input_spec.data(), static_cast<int>(input_spec.length()), trim_path_end,
      NULL, &output, &parsed_);

  output.Complete();  // Must be done before using string.
  if (is_valid_ && SchemeIsFileSystem()) {
    inner_url_ = std::make_unique<GURL>(spec_.data(), parsed_.Length(),
                                        *parsed_.inner_parsed(), true);
  }
  // Valid URLs always have non-empty specs.
  GURL_DCHECK(!is_valid_ || !spec_.empty());
}

void GURL::InitializeFromCanonicalSpec() {
  if (is_valid_ && SchemeIsFileSystem()) {
    inner_url_ = std::make_unique<GURL>(spec_.data(), parsed_.Length(),
                                        *parsed_.inner_parsed(), true);
  }

#ifndef NDEBUG
  // For testing purposes, check that the parsed canonical URL is identical to
  // what we would have produced. Skip checking for invalid URLs have no meaning
  // and we can't always canonicalize then reproducibly.
  if (is_valid_) {
    GURL_DCHECK(!spec_.empty());
    url::Component scheme;
    // We can't do this check on the inner_url of a filesystem URL, as
    // canonical_spec actually points to the start of the outer URL, so we'd
    // end up with infinite recursion in this constructor.
    if (!url::FindAndCompareScheme(spec_.data(), spec_.length(),
                                   url::kFileSystemScheme, &scheme) ||
        scheme.begin == parsed_.scheme.begin) {
      // We need to retain trailing whitespace on path URLs, as the |parsed_|
      // spec we originally received may legitimately contain trailing white-
      // space on the path or  components e.g. if the #ref has been
      // removed from a "foo:hello #ref" URL (see http://crbug.com/291747).
      GURL test_url(spec_, RETAIN_TRAILING_PATH_WHITEPACE);

      GURL_DCHECK_EQ(test_url.is_valid_, is_valid_);
      GURL_DCHECK_EQ(test_url.spec_, spec_);

      GURL_DCHECK_EQ(test_url.parsed_.scheme, parsed_.scheme);
      GURL_DCHECK_EQ(test_url.parsed_.username, parsed_.username);
      GURL_DCHECK_EQ(test_url.parsed_.password, parsed_.password);
      GURL_DCHECK_EQ(test_url.parsed_.host, parsed_.host);
      GURL_DCHECK_EQ(test_url.parsed_.port, parsed_.port);
      GURL_DCHECK_EQ(test_url.parsed_.path, parsed_.path);
      GURL_DCHECK_EQ(test_url.parsed_.query, parsed_.query);
      GURL_DCHECK_EQ(test_url.parsed_.ref, parsed_.ref);
    }
  }
#endif
}

GURL::~GURL() = default;

GURL& GURL::operator=(const GURL& other) {
  spec_ = other.spec_;
  is_valid_ = other.is_valid_;
  parsed_ = other.parsed_;

  if (!other.inner_url_)
    inner_url_.reset();
  else if (inner_url_)
    *inner_url_ = *other.inner_url_;
  else
    inner_url_ = std::make_unique<GURL>(*other.inner_url_);

  return *this;
}

GURL& GURL::operator=(GURL&& other) noexcept {
  spec_ = std::move(other.spec_);
  is_valid_ = other.is_valid_;
  parsed_ = other.parsed_;
  inner_url_ = std::move(other.inner_url_);

  other.is_valid_ = false;
  other.parsed_ = url::Parsed();
  return *this;
}

const std::string& GURL::spec() const {
  if (is_valid_ || spec_.empty())
    return spec_;

  GURL_DCHECK(false) << "Trying to get the spec of an invalid URL!";
  return gurl_base::EmptyString();
}

bool GURL::operator<(const GURL& other) const {
  return spec_ < other.spec_;
}

bool GURL::operator>(const GURL& other) const {
  return spec_ > other.spec_;
}

// Note: code duplicated below (it's inconvenient to use a template here).
GURL GURL::Resolve(gurl_base::StringPiece relative) const {
  // Not allowed for invalid URLs.
  if (!is_valid_)
    return GURL();

  GURL result;
  url::StdStringCanonOutput output(&result.spec_);
  if (!url::ResolveRelative(spec_.data(), static_cast<int>(spec_.length()),
                            parsed_, relative.data(),
                            static_cast<int>(relative.length()),
                            nullptr, &output, &result.parsed_)) {
    // Error resolving, return an empty URL.
    return GURL();
  }

  output.Complete();
  result.is_valid_ = true;
  if (result.SchemeIsFileSystem()) {
    result.inner_url_ =
        std::make_unique<GURL>(result.spec_.data(), result.parsed_.Length(),
                               *result.parsed_.inner_parsed(), true);
  }
  return result;
}

// Note: code duplicated above (it's inconvenient to use a template here).
GURL GURL::Resolve(gurl_base::StringPiece16 relative) const {
  // Not allowed for invalid URLs.
  if (!is_valid_)
    return GURL();

  GURL result;
  url::StdStringCanonOutput output(&result.spec_);
  if (!url::ResolveRelative(spec_.data(), static_cast<int>(spec_.length()),
                            parsed_, relative.data(),
                            static_cast<int>(relative.length()),
                            nullptr, &output, &result.parsed_)) {
    // Error resolving, return an empty URL.
    return GURL();
  }

  output.Complete();
  result.is_valid_ = true;
  if (result.SchemeIsFileSystem()) {
    result.inner_url_ =
        std::make_unique<GURL>(result.spec_.data(), result.parsed_.Length(),
                               *result.parsed_.inner_parsed(), true);
  }
  return result;
}

// Note: code duplicated below (it's inconvenient to use a template here).
GURL GURL::ReplaceComponents(const Replacements& replacements) const {
  GURL result;

  // Not allowed for invalid URLs.
  if (!is_valid_)
    return GURL();

  url::StdStringCanonOutput output(&result.spec_);
  result.is_valid_ = url::ReplaceComponents(
      spec_.data(), static_cast<int>(spec_.length()), parsed_, replacements,
      NULL, &output, &result.parsed_);

  output.Complete();

  result.ProcessFileSystemURLAfterReplaceComponents();
  return result;
}

// Note: code duplicated above (it's inconvenient to use a template here).
GURL GURL::ReplaceComponents(const ReplacementsW& replacements) const {
  GURL result;

  // Not allowed for invalid URLs.
  if (!is_valid_)
    return GURL();

  url::StdStringCanonOutput output(&result.spec_);
  result.is_valid_ = url::ReplaceComponents(
      spec_.data(), static_cast<int>(spec_.length()), parsed_, replacements,
      NULL, &output, &result.parsed_);

  output.Complete();

  result.ProcessFileSystemURLAfterReplaceComponents();

  return result;
}

void GURL::ProcessFileSystemURLAfterReplaceComponents() {
  if (!is_valid_)
    return;
  if (SchemeIsFileSystem()) {
    inner_url_ = std::make_unique<GURL>(spec_.data(), parsed_.Length(),
                                        *parsed_.inner_parsed(), true);
  }
}

GURL GURL::DeprecatedGetOriginAsURL() const {
  // This doesn't make sense for invalid or nonstandard URLs, so return
  // the empty URL.
  if (!is_valid_ || !IsStandard())
    return GURL();

  if (SchemeIsFileSystem())
    return inner_url_->DeprecatedGetOriginAsURL();

  Replacements replacements;
  replacements.ClearUsername();
  replacements.ClearPassword();
  replacements.ClearPath();
  replacements.ClearQuery();
  replacements.ClearRef();

  return ReplaceComponents(replacements);
}

GURL GURL::GetAsReferrer() const {
  if (!is_valid() || !IsReferrerScheme(spec_.data(), parsed_.scheme))
    return GURL();

  if (!has_ref() && !has_username() && !has_password())
    return GURL(*this);

  Replacements replacements;
  replacements.ClearRef();
  replacements.ClearUsername();
  replacements.ClearPassword();
  return ReplaceComponents(replacements);
}

GURL GURL::GetWithEmptyPath() const {
  // This doesn't make sense for invalid or nonstandard URLs, so return
  // the empty URL.
  if (!is_valid_ || !IsStandard())
    return GURL();

  // We could optimize this since we know that the URL is canonical, and we are
  // appending a canonical path, so avoiding re-parsing.
  GURL other(*this);
  if (parsed_.path.len == 0)
    return other;

  // Clear everything after the path.
  other.parsed_.query.reset();
  other.parsed_.ref.reset();

  // Set the path, since the path is longer than one, we can just set the
  // first character and resize.
  other.spec_[other.parsed_.path.begin] = '/';
  other.parsed_.path.len = 1;
  other.spec_.resize(other.parsed_.path.begin + 1);
  return other;
}

GURL GURL::GetWithoutFilename() const {
  return Resolve(".");
}

bool GURL::IsStandard() const {
  return url::IsStandard(spec_.data(), parsed_.scheme);
}

bool GURL::IsAboutBlank() const {
  return IsAboutUrl(url::kAboutBlankPath);
}

bool GURL::IsAboutSrcdoc() const {
  return IsAboutUrl(url::kAboutSrcdocPath);
}

bool GURL::SchemeIs(gurl_base::StringPiece lower_ascii_scheme) const {
  GURL_DCHECK(gurl_base::IsStringASCII(lower_ascii_scheme));
  GURL_DCHECK(gurl_base::ToLowerASCII(lower_ascii_scheme) == lower_ascii_scheme);

  if (!has_scheme())
    return lower_ascii_scheme.empty();
  return scheme_piece() == lower_ascii_scheme;
}

bool GURL::SchemeIsHTTPOrHTTPS() const {
  return SchemeIs(url::kHttpScheme) || SchemeIs(url::kHttpsScheme);
}

bool GURL::SchemeIsWSOrWSS() const {
  return SchemeIs(url::kWsScheme) || SchemeIs(url::kWssScheme);
}

bool GURL::SchemeIsCryptographic() const {
  if (!has_scheme())
    return false;
  return SchemeIsCryptographic(scheme_piece());
}

bool GURL::SchemeIsCryptographic(gurl_base::StringPiece lower_ascii_scheme) {
  GURL_DCHECK(gurl_base::IsStringASCII(lower_ascii_scheme));
  GURL_DCHECK(gurl_base::ToLowerASCII(lower_ascii_scheme) == lower_ascii_scheme);

  return lower_ascii_scheme == url::kHttpsScheme ||
         lower_ascii_scheme == url::kWssScheme;
}

bool GURL::SchemeIsLocal() const {
  // The `filesystem:` scheme is not in the Fetch spec, but Chromium still
  // supports it in large part. It should be treated as a local scheme too.
  return SchemeIs(url::kAboutScheme) || SchemeIs(url::kBlobScheme) ||
         SchemeIs(url::kDataScheme) || SchemeIs(url::kFileSystemScheme);
}

int GURL::IntPort() const {
  if (parsed_.port.is_nonempty())
    return url::ParsePort(spec_.data(), parsed_.port);
  return url::PORT_UNSPECIFIED;
}

int GURL::EffectiveIntPort() const {
  int int_port = IntPort();
  if (int_port == url::PORT_UNSPECIFIED && IsStandard())
    return url::DefaultPortForScheme(spec_.data() + parsed_.scheme.begin,
                                     parsed_.scheme.len);
  return int_port;
}

std::string GURL::ExtractFileName() const {
  url::Component file_component;
  url::ExtractFileName(spec_.data(), parsed_.path, &file_component);
  return ComponentString(file_component);
}

gurl_base::StringPiece GURL::PathForRequestPiece() const {
  GURL_DCHECK(parsed_.path.len > 0)
      << "Canonical path for requests should be non-empty";
  if (parsed_.ref.len >= 0) {
    // Clip off the reference when it exists. The reference starts after the
    // #-sign, so we have to subtract one to also remove it.
    return gurl_base::StringPiece(&spec_[parsed_.path.begin],
                             parsed_.ref.begin - parsed_.path.begin - 1);
  }
  // Compute the actual path length, rather than depending on the spec's
  // terminator. If we're an inner_url, our spec continues on into our outer
  // URL's path/query/ref.
  int path_len = parsed_.path.len;
  if (parsed_.query.is_valid())
    path_len = parsed_.query.end() - parsed_.path.begin;

  return gurl_base::StringPiece(&spec_[parsed_.path.begin], path_len);
}

std::string GURL::PathForRequest() const {
  return std::string(PathForRequestPiece());
}

std::string GURL::HostNoBrackets() const {
  return std::string(HostNoBracketsPiece());
}

gurl_base::StringPiece GURL::HostNoBracketsPiece() const {
  // If host looks like an IPv6 literal, strip the square brackets.
  url::Component h(parsed_.host);
  if (h.len >= 2 && spec_[h.begin] == '[' && spec_[h.end() - 1] == ']') {
    h.begin++;
    h.len -= 2;
  }
  return ComponentStringPiece(h);
}

std::string GURL::GetContent() const {
  return std::string(GetContentPiece());
}

gurl_base::StringPiece GURL::GetContentPiece() const {
  if (!is_valid_)
    return gurl_base::StringPiece();
  url::Component content_component = parsed_.GetContent();
  if (!SchemeIs(url::kJavaScriptScheme) && parsed_.ref.len >= 0)
    content_component.len -= parsed_.ref.len + 1;
  return ComponentStringPiece(content_component);
}

bool GURL::HostIsIPAddress() const {
  return is_valid_ && url::HostIsIPAddress(host_piece());
}

const GURL& GURL::EmptyGURL() {
  static gurl_base::NoDestructor<GURL> empty_gurl;
  return *empty_gurl;
}

bool GURL::DomainIs(gurl_base::StringPiece canonical_domain) const {
  if (!is_valid_)
    return false;

  // FileSystem URLs have empty host_piece, so check this first.
  if (inner_url_ && SchemeIsFileSystem())
    return inner_url_->DomainIs(canonical_domain);
  return url::DomainIs(host_piece(), canonical_domain);
}

bool GURL::EqualsIgnoringRef(const GURL& other) const {
  int ref_position = parsed_.CountCharactersBefore(url::Parsed::REF, true);
  int ref_position_other =
      other.parsed_.CountCharactersBefore(url::Parsed::REF, true);
  return gurl_base::StringPiece(spec_).substr(0, ref_position) ==
         gurl_base::StringPiece(other.spec_).substr(0, ref_position_other);
}

void GURL::Swap(GURL* other) {
  spec_.swap(other->spec_);
  std::swap(is_valid_, other->is_valid_);
  std::swap(parsed_, other->parsed_);
  inner_url_.swap(other->inner_url_);
}

size_t GURL::EstimateMemoryUsage() const {
  return gurl_base::trace_event::EstimateMemoryUsage(spec_) +
         gurl_base::trace_event::EstimateMemoryUsage(inner_url_) +
         (parsed_.inner_parsed() ? sizeof(url::Parsed) : 0);
}

bool GURL::IsAboutUrl(gurl_base::StringPiece allowed_path) const {
  if (!SchemeIs(url::kAboutScheme))
    return false;

  if (has_host() || has_username() || has_password() || has_port())
    return false;

  return IsAboutPath(path_piece(), allowed_path);
}

// static
bool GURL::IsAboutPath(gurl_base::StringPiece actual_path,
                       gurl_base::StringPiece allowed_path) {
  if (!gurl_base::StartsWith(actual_path, allowed_path))
    return false;

  if (actual_path.size() == allowed_path.size()) {
    GURL_DCHECK_EQ(actual_path, allowed_path);
    return true;
  }

  if ((actual_path.size() == allowed_path.size() + 1) &&
      actual_path.back() == '/') {
    GURL_DCHECK_EQ(actual_path, std::string(allowed_path) + '/');
    return true;
  }

  return false;
}

void GURL::WriteIntoTrace(perfetto::TracedValue context) const {
  std::move(context).WriteString(possibly_invalid_spec());
}

std::ostream& operator<<(std::ostream& out, const GURL& url) {
  return out << url.possibly_invalid_spec();
}

bool operator==(const GURL& x, const GURL& y) {
  return x.possibly_invalid_spec() == y.possibly_invalid_spec();
}

bool operator!=(const GURL& x, const GURL& y) {
  return !(x == y);
}

bool operator==(const GURL& x, const gurl_base::StringPiece& spec) {
  GURL_DCHECK_EQ(GURL(spec).possibly_invalid_spec(), spec)
      << "Comparisons of GURLs and strings must ensure as a precondition that "
         "the string is fully canonicalized.";
  return x.possibly_invalid_spec() == spec;
}

bool operator==(const gurl_base::StringPiece& spec, const GURL& x) {
  return x == spec;
}

bool operator!=(const GURL& x, const gurl_base::StringPiece& spec) {
  return !(x == spec);
}

bool operator!=(const gurl_base::StringPiece& spec, const GURL& x) {
  return !(x == spec);
}

namespace url::debug {

ScopedUrlCrashKey::ScopedUrlCrashKey(gurl_base::debug::CrashKeyString* crash_key,
                                     const GURL& url)
    : scoped_string_value_(
          crash_key,
          url.is_empty() ? "<empty url>" : url.possibly_invalid_spec()) {}

ScopedUrlCrashKey::~ScopedUrlCrashKey() = default;

}  // namespace url::debug
