/*
 * Copyright (C) 2015 The Android Open Source Project
 *
 * Licensed 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 <iostream>
#include <string>

#include "util/Maybe.h"
#include "util/Util.h"
#include "xml/XmlPullParser.h"
#include "xml/XmlUtil.h"

using ::aapt::io::InputStream;
using ::android::StringPiece;

namespace aapt {
namespace xml {

constexpr char kXmlNamespaceSep = 1;

XmlPullParser::XmlPullParser(InputStream* in) : in_(in), empty_(), depth_(0) {
  parser_ = XML_ParserCreateNS(nullptr, kXmlNamespaceSep);
  XML_SetUserData(parser_, this);
  XML_SetElementHandler(parser_, StartElementHandler, EndElementHandler);
  XML_SetNamespaceDeclHandler(parser_, StartNamespaceHandler,
                              EndNamespaceHandler);
  XML_SetCharacterDataHandler(parser_, CharacterDataHandler);
  XML_SetCommentHandler(parser_, CommentDataHandler);
  event_queue_.push(EventData{Event::kStartDocument, 0, depth_++});
}

XmlPullParser::~XmlPullParser() {
  XML_ParserFree(parser_);
}

XmlPullParser::Event XmlPullParser::Next() {
  const Event currentEvent = event();
  if (currentEvent == Event::kBadDocument || currentEvent == Event::kEndDocument) {
    return currentEvent;
  }

  event_queue_.pop();
  while (event_queue_.empty()) {
    const char* buffer = nullptr;
    size_t buffer_size = 0;
    bool done = false;
    if (!in_->Next(reinterpret_cast<const void**>(&buffer), &buffer_size)) {
      if (in_->HadError()) {
        error_ = in_->GetError();
        event_queue_.push(EventData{Event::kBadDocument});
        break;
      }

      done = true;
    }

    if (XML_Parse(parser_, buffer, buffer_size, done) == XML_STATUS_ERROR) {
      error_ = XML_ErrorString(XML_GetErrorCode(parser_));
      event_queue_.push(EventData{Event::kBadDocument});
      break;
    }

    if (done) {
      event_queue_.push(EventData{Event::kEndDocument, 0, 0});
    }
  }

  Event next_event = event();

  // Record namespace prefixes and package names so that we can do our own
  // handling of references that use namespace aliases.
  if (next_event == Event::kStartNamespace ||
      next_event == Event::kEndNamespace) {
    Maybe<ExtractedPackage> result =
        ExtractPackageFromNamespace(namespace_uri());
    if (next_event == Event::kStartNamespace) {
      if (result) {
        package_aliases_.emplace_back(
            PackageDecl{namespace_prefix(), std::move(result.value())});
      }
    } else {
      if (result) {
        package_aliases_.pop_back();
      }
    }
  }

  return next_event;
}

XmlPullParser::Event XmlPullParser::event() const {
  return event_queue_.front().event;
}

const std::string& XmlPullParser::error() const { return error_; }

const std::string& XmlPullParser::comment() const {
  return event_queue_.front().data1;
}

size_t XmlPullParser::line_number() const {
  return event_queue_.front().line_number;
}

size_t XmlPullParser::depth() const { return event_queue_.front().depth; }

const std::string& XmlPullParser::text() const {
  if (event() != Event::kText) {
    return empty_;
  }
  return event_queue_.front().data1;
}

const std::string& XmlPullParser::namespace_prefix() const {
  const Event current_event = event();
  if (current_event != Event::kStartNamespace &&
      current_event != Event::kEndNamespace) {
    return empty_;
  }
  return event_queue_.front().data1;
}

const std::string& XmlPullParser::namespace_uri() const {
  const Event current_event = event();
  if (current_event != Event::kStartNamespace &&
      current_event != Event::kEndNamespace) {
    return empty_;
  }
  return event_queue_.front().data2;
}

Maybe<ExtractedPackage> XmlPullParser::TransformPackageAlias(
    const StringPiece& alias, const StringPiece& local_package) const {
  if (alias.empty()) {
    return ExtractedPackage{local_package.to_string(), false /* private */};
  }

  const auto end_iter = package_aliases_.rend();
  for (auto iter = package_aliases_.rbegin(); iter != end_iter; ++iter) {
    if (alias == iter->prefix) {
      if (iter->package.package.empty()) {
        return ExtractedPackage{local_package.to_string(), iter->package.private_namespace};
      }
      return iter->package;
    }
  }
  return {};
}

const std::string& XmlPullParser::element_namespace() const {
  const Event current_event = event();
  if (current_event != Event::kStartElement &&
      current_event != Event::kEndElement) {
    return empty_;
  }
  return event_queue_.front().data1;
}

const std::string& XmlPullParser::element_name() const {
  const Event current_event = event();
  if (current_event != Event::kStartElement &&
      current_event != Event::kEndElement) {
    return empty_;
  }
  return event_queue_.front().data2;
}

XmlPullParser::const_iterator XmlPullParser::begin_attributes() const {
  return event_queue_.front().attributes.begin();
}

XmlPullParser::const_iterator XmlPullParser::end_attributes() const {
  return event_queue_.front().attributes.end();
}

size_t XmlPullParser::attribute_count() const {
  if (event() != Event::kStartElement) {
    return 0;
  }
  return event_queue_.front().attributes.size();
}

/**
 * Extracts the namespace and name of an expanded element or attribute name.
 */
static void SplitName(const char* name, std::string* out_ns, std::string* out_name) {
  const char* p = name;
  while (*p != 0 && *p != kXmlNamespaceSep) {
    p++;
  }

  if (*p == 0) {
    out_ns->clear();
    out_name->assign(name);
  } else {
    out_ns->assign(name, (p - name));
    out_name->assign(p + 1);
  }
}

void XMLCALL XmlPullParser::StartNamespaceHandler(void* user_data,
                                                  const char* prefix,
                                                  const char* uri) {
  XmlPullParser* parser = reinterpret_cast<XmlPullParser*>(user_data);
  std::string namespace_uri = uri != nullptr ? uri : std::string();
  parser->namespace_uris_.push(namespace_uri);
  parser->event_queue_.push(
      EventData{Event::kStartNamespace,
                XML_GetCurrentLineNumber(parser->parser_), parser->depth_++,
                prefix != nullptr ? prefix : std::string(), namespace_uri});
}

void XMLCALL XmlPullParser::StartElementHandler(void* user_data,
                                                const char* name,
                                                const char** attrs) {
  XmlPullParser* parser = reinterpret_cast<XmlPullParser*>(user_data);

  EventData data = {Event::kStartElement,
                    XML_GetCurrentLineNumber(parser->parser_),
                    parser->depth_++};
  SplitName(name, &data.data1, &data.data2);

  while (*attrs) {
    Attribute attribute;
    SplitName(*attrs++, &attribute.namespace_uri, &attribute.name);
    attribute.value = *attrs++;

    // Insert in sorted order.
    auto iter = std::lower_bound(data.attributes.begin(), data.attributes.end(),
                                 attribute);
    data.attributes.insert(iter, std::move(attribute));
  }

  // Move the structure into the queue (no copy).
  parser->event_queue_.push(std::move(data));
}

void XMLCALL XmlPullParser::CharacterDataHandler(void* user_data, const char* s,
                                                 int len) {
  XmlPullParser* parser = reinterpret_cast<XmlPullParser*>(user_data);

  parser->event_queue_.push(EventData{Event::kText, XML_GetCurrentLineNumber(parser->parser_),
                                      parser->depth_, std::string(s, len)});
}

void XMLCALL XmlPullParser::EndElementHandler(void* user_data,
                                              const char* name) {
  XmlPullParser* parser = reinterpret_cast<XmlPullParser*>(user_data);

  EventData data = {Event::kEndElement,
                    XML_GetCurrentLineNumber(parser->parser_),
                    --(parser->depth_)};
  SplitName(name, &data.data1, &data.data2);

  // Move the data into the queue (no copy).
  parser->event_queue_.push(std::move(data));
}

void XMLCALL XmlPullParser::EndNamespaceHandler(void* user_data,
                                                const char* prefix) {
  XmlPullParser* parser = reinterpret_cast<XmlPullParser*>(user_data);

  parser->event_queue_.push(
      EventData{Event::kEndNamespace, XML_GetCurrentLineNumber(parser->parser_),
                --(parser->depth_), prefix != nullptr ? prefix : std::string(),
                parser->namespace_uris_.top()});
  parser->namespace_uris_.pop();
}

void XMLCALL XmlPullParser::CommentDataHandler(void* user_data,
                                               const char* comment) {
  XmlPullParser* parser = reinterpret_cast<XmlPullParser*>(user_data);

  parser->event_queue_.push(EventData{Event::kComment,
                                      XML_GetCurrentLineNumber(parser->parser_),
                                      parser->depth_, comment});
}

Maybe<StringPiece> FindAttribute(const XmlPullParser* parser,
                                 const StringPiece& name) {
  auto iter = parser->FindAttribute("", name);
  if (iter != parser->end_attributes()) {
    return StringPiece(util::TrimWhitespace(iter->value));
  }
  return {};
}

Maybe<StringPiece> FindNonEmptyAttribute(const XmlPullParser* parser,
                                         const StringPiece& name) {
  auto iter = parser->FindAttribute("", name);
  if (iter != parser->end_attributes()) {
    StringPiece trimmed = util::TrimWhitespace(iter->value);
    if (!trimmed.empty()) {
      return trimmed;
    }
  }
  return {};
}

}  // namespace xml
}  // namespace aapt
