/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
/*
 * Copyright (c) 2014-2017, Regents of the University of California.
 *
 * This file is part of NDNS (Named Data Networking Domain Name Service).
 * See AUTHORS.md for complete list of NDNS authors and contributors.
 *
 * NDNS is free software: you can redistribute it and/or modify it under the terms
 * of the GNU General Public License as published by the Free Software Foundation,
 * either version 3 of the License, or (at your option) any later version.
 *
 * NDNS is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
 * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
 * PURPOSE.  See the GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License along with
 * NDNS, e.g., in COPYING.md file.  If not, see <http://www.gnu.org/licenses/>.
 */

#include "ndns-label.hpp"
#include "logger.hpp"
#include "clients/response.hpp"
#include "clients/query.hpp"
#include "clients/iterative-query-controller.hpp"
#include "validator/validator.hpp"
#include "util/util.hpp"

#include <ndn-cxx/security/key-chain.hpp>
#include <ndn-cxx/face.hpp>
#include <boost/program_options.hpp>
#include <boost/asio.hpp>
#include <boost/filesystem.hpp>
#include <boost/noncopyable.hpp>

#include <iostream>
#include <memory>
#include <string>
#include <fstream>

NDNS_LOG_INIT("NdnsDig")

namespace ndn {
namespace ndns {

class NdnsDig
{
public:
  NdnsDig(const Name& dstLabel,
          const name::Component& rrType, bool shouldValidateIntermediate)
    : m_dstLabel(dstLabel)
    , m_rrType(rrType)
    , m_interestLifetime(DEFAULT_INTEREST_LIFETIME)
    , m_validator(NdnsValidatorBuilder::create(m_face))
    , m_shouldValidateIntermediate(shouldValidateIntermediate)
    , m_hasError(false)
  {
    if (m_shouldValidateIntermediate)
      m_ctr = std::unique_ptr<IterativeQueryController>
        (new IterativeQueryController(m_dstLabel, m_rrType, m_interestLifetime,
                                      bind(&NdnsDig::onSucceed, this, _1, _2),
                                      bind(&NdnsDig::onFail, this, _1, _2),
                                      m_face, m_validator.get()));
    else
      m_ctr = std::unique_ptr<IterativeQueryController>
        (new IterativeQueryController(m_dstLabel, m_rrType, m_interestLifetime,
                                      bind(&NdnsDig::onSucceed, this, _1, _2),
                                      bind(&NdnsDig::onFail, this, _1, _2),
                                      m_face, nullptr));
  }

  void
  run()
  {
    NDNS_LOG_INFO(" =================================== "
                  << "start to dig label = " << this->m_dstLabel
                  << " for type = " << this->m_rrType
                  << " =================================== ");

    try {
      m_ctr->start(); // non-block, may throw exception
      m_face.processEvents();
    }
    catch (const std::exception& e) {
      std::cerr << "Error: " << e.what();
      m_hasError = true;
    }
  }

  void
  stop()
  {
    m_face.getIoService().stop();
    NDNS_LOG_TRACE("application stops.");
  }

  void
  setStartZone(const Name& start)
  {
    m_ctr->setStartComponentIndex(start.size());
  }

private:
  void
  onSucceed(const Data& data, const Response& response)
  {
    NDNS_LOG_INFO("Dig get following Response (need verification):");
    Name name = Name().append(response.getZone()).append(response.getRrLabel());
    if (name == m_dstLabel && m_rrType == response.getRrType()) {
      NDNS_LOG_INFO("This is the final response returned by zone=" << response.getZone()
                    << " and NdnsType=" << response.getContentType()
                    << ". It contains " << response.getRrs().size() << " RR(s)");

      std::string msg;
      size_t i = 0;
      for (const auto& rr : response.getRrs()) {
        try {
          msg = std::string(reinterpret_cast<const char*>(rr.value()), rr.value_size());
          NDNS_LOG_INFO("succeed to get the info from RR[" << i << "]"
                        "type=" << rr.type() << " content=" << msg);
        }
        catch (const std::exception& e) {
          NDNS_LOG_INFO("error to get the info from RR[" << i << "]"
                        "type=" << rr.type());
        }
        ++i;
      }
    }
    else {
      NDNS_LOG_INFO("[* !! *] This is not final response.The target Label: "
                    << m_dstLabel << " may not exist");
    }

    if (m_dstFile.empty()) {
      ;
    }
    else if (m_dstFile == "-") {
      output(data, std::cout, true);
    }
    else {
      NDNS_LOG_INFO("output Data packet to " << m_dstFile << " with BASE64 encoding format");
      std::filebuf fb;
      fb.open(m_dstFile, std::ios::out);
      std::ostream os(&fb);
      output(data, os, false);
    }

    NDNS_LOG_INFO(response);

    NDNS_LOG_TRACE("to verify the response");
    m_validator->validate(data,
                         bind(&NdnsDig::onDataValidated, this, _1),
                         bind(&NdnsDig::onDataValidationFailed, this, _1, _2)
                         );
  }


  void
  onFail(uint32_t errCode, const std::string& errMsg)
  {
    NDNS_LOG_INFO("fail to get response: errCode=" << errCode << " msg=" << errMsg);
    m_hasError = true;
    this->stop();
  }

  void
  onDataValidated(const Data& data)
  {
    NDNS_LOG_INFO("final data pass verification");
    this->stop();
  }

  void
  onDataValidationFailed(const Data& data, const security::v2::ValidationError& err)
  {
    NDNS_LOG_INFO("final data does not pass verification");
    m_hasError = true;
    this->stop();
  }

public:
  void
  setInterestLifetime(const time::milliseconds& lifetime)
  {
    m_interestLifetime = lifetime;
  }

  bool
  hasError() const
  {
    return m_hasError;
  }

  void
  setDstFile(const std::string& dstFile)
  {
    m_dstFile = dstFile;
  }

private:
  Name m_dstLabel;
  name::Component m_rrType;

  Name m_certName;
  time::milliseconds m_interestLifetime;

  Face m_face;

  unique_ptr<security::v2::Validator> m_validator;
  bool m_shouldValidateIntermediate;
  std::unique_ptr<QueryController> m_ctr;

  bool m_hasError;
  std::string m_dstFile;
};

} // namespace ndns
} // namespace ndn


int
main(int argc, char* argv[])
{
  ndn::ndns::log::init();
  using std::string;
  using namespace ndn;

  Name dstLabel;
  int ttl = 4;
  string rrType = "TXT";
  string dstFile;
  bool shouldValidateIntermediate = true;
  Name start("/ndn");

  try {
    namespace po = boost::program_options;
    po::variables_map vm;

    po::options_description generic("Generic Options");
    generic.add_options()("help,h", "print help message");

    po::options_description config("Configuration");
    config.add_options()
      ("timeout,T", po::value<int>(&ttl), "query timeout. default: 4 sec")
      ("rrtype,t", po::value<std::string>(&rrType), "set request RR Type. default: TXT")
      ("dstFile,d", po::value<std::string>(&dstFile), "set output file of the received Data. "
       "if omitted, not print; if set to be -, print to stdout; else print to file")
      ("start,s", po::value<Name>(&start)->default_value("/ndn"), "set first zone to query")
      ("not-validate,n", "trigger not validate intermediate results")
      ;

    po::options_description hidden("Hidden Options");
    hidden.add_options()
      ("name", po::value<Name>(&dstLabel), "name to be resolved")
      ;
    po::positional_options_description postion;
    postion.add("name", 1);

    po::options_description cmdline_options;
    cmdline_options.add(generic).add(config).add(hidden);

    po::options_description config_file_options;
    config_file_options.add(config).add(hidden);

    po::options_description visible("Usage: ndns-dig /name/to/be/resolved [-t rrType] [-T ttl]"
                                    "[-d dstFile] [-s startZone] [-n]\n"
                                    "Allowed options");

    visible.add(generic).add(config);

    po::parsed_options parsed =
      po::command_line_parser(argc, argv).options(cmdline_options).positional(postion).run();

    po::store(parsed, vm);
    po::notify(vm);

    if (vm.count("help")) {
      std::cout << visible << std::endl;
      return 0;
    }

    if (!vm.count("name")) {
      std::cerr << "must contain a target label parameter." << std::endl;
      std::cerr << visible << std::endl;
      return 1;
    }

    if (!start.isPrefixOf(dstLabel)) {
      std::cerr << "Error: start zone " << start << " is not prefix of the target label "
                << dstLabel << std::endl;
      return 1;
    }

    if (vm.count("not-validate")) {
      shouldValidateIntermediate = false;
    }

    if (ttl < 0) {
      std::cerr << "Error: ttl parameter cannot be negative" << std::endl;
      return 1;
    }
  }
  catch (const std::exception& ex) {
    std::cerr << "Parameter Error: " << ex.what() << std::endl;
    return 1;
  }

  try {
    ndn::ndns::NdnsDig dig(dstLabel, ndn::name::Component(rrType), shouldValidateIntermediate);
    dig.setInterestLifetime(ndn::time::seconds(ttl));
    dig.setDstFile(dstFile);

    // Due to ndn testbed does not contain the root zone
    // dig here starts from the TLD (Top-level Domain)
    // precondition is that TLD : 1) only contains one component in its name; 2) its name is routable
    dig.setStartZone(start);

    dig.run();

    if (dig.hasError())
      return 1;
    else
      return 0;
  }
  catch (const std::exception& e) {
    std::cerr << "Error: " << e.what() << std::endl;
    return 1;
  }

}
