/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
/*
 * Copyright (c) 2013, Regents of the University of California
 *                     Yingdi Yu
 *
 * BSD license, See the LICENSE file for more information
 *
 * Author: Yingdi Yu <yingdi@cs.ucla.edu>
 */

#include "contact-storage.hpp"

#include <boost/filesystem.hpp>
#include "cryptopp.hpp"
#include "logging.h"


// INIT_LOGGER ("chronos.ContactStorage");

namespace chronos {

namespace fs = boost::filesystem;

using std::string;
using std::vector;

using ndn::PublicKey;

// user's own profile;
const string INIT_SP_TABLE =
  "CREATE TABLE IF NOT EXISTS                          "
  "  SelfProfile(                                      "
  "      profile_type      BLOB NOT NULL,              "
  "      profile_value     BLOB NOT NULL,              "
  "      PRIMARY KEY (profile_type)                    "
  "  );                                                "
  "CREATE INDEX sp_index ON SelfProfile(profile_type); ";

// user's self endorse cert;
const string INIT_SE_TABLE =
  "CREATE TABLE IF NOT EXISTS                      "
  "  SelfEndorse(                                  "
  "      identity          BLOB NOT NULL UNIQUE,   "
  "      endorse_data      BLOB NOT NULL,          "
  "      PRIMARY KEY (identity)                    "
  "  );                                            "
  "CREATE INDEX se_index ON SelfEndorse(identity); ";

// contact's basic info
const string INIT_CONTACT_TABLE =
  "CREATE TABLE IF NOT EXISTS                                "
  "  Contact(                                                "
  "      contact_namespace BLOB NOT NULL,                    "
  "      contact_alias     BLOB NOT NULL,                    "
  "      contact_keyName   BLOB NOT NULL,                    "
  "      contact_key       BLOB NOT NULL,                    "
  "      notBefore         INTEGER DEFAULT 0,                "
  "      notAfter          INTEGER DEFAULT 0,                "
  "      is_introducer     INTEGER DEFAULT 0,                "
  "      PRIMARY KEY (contact_namespace)                     "
  "  );                                                      "
  "CREATE INDEX contact_index ON Contact(contact_namespace); ";

// contact's trust scope;
const string INIT_TS_TABLE =
  "CREATE TABLE IF NOT EXISTS                                 "
  "  TrustScope(                                              "
  "      id                INTEGER PRIMARY KEY AUTOINCREMENT, "
  "      contact_namespace BLOB NOT NULL,                     "
  "      trust_scope       BLOB NOT NULL                      "
  "  );                                                       "
  "CREATE INDEX ts_index ON TrustScope(contact_namespace);    ";

// contact's profile
const string INIT_CP_TABLE =
  "CREATE TABLE IF NOT EXISTS                                 "
  "  ContactProfile(                                          "
  "      profile_identity  BLOB NOT NULL,                     "
  "      profile_type      BLOB NOT NULL,                     "
  "      profile_value     BLOB NOT NULL,                     "
  "      endorse           INTEGER NOT NULL,                  "
  "      PRIMARY KEY (profile_identity, profile_type)         "
  "  );                                                       "
  "CREATE INDEX cp_index ON ContactProfile(profile_identity); ";

// user's endorsement on contacts
const string INIT_PE_TABLE =
  "CREATE TABLE IF NOT EXISTS                         "
  "  ProfileEndorse(                                  "
  "      identity          BLOB NOT NULL UNIQUE,      "
  "      endorse_data      BLOB NOT NULL,             "
  "      PRIMARY KEY (identity)                       "
  "  );                                               "
  "CREATE INDEX pe_index ON ProfileEndorse(identity); ";

// contact's endorsements on the user
const string INIT_CE_TABLE =
  "CREATE TABLE IF NOT EXISTS               "
  "  CollectEndorse(                        "
  "      endorser          BLOB NOT NULL,   "
  "      endorse_name      BLOB NOT NULL,   "
  "      endorse_data      BLOB NOT NULL,   "
  "      PRIMARY KEY (endorser)             "
  "  );                                     ";

// dns data;
const string INIT_DD_TABLE =
  "CREATE TABLE IF NOT EXISTS                             "
  "  DnsData(                                             "
  "      dns_name      BLOB NOT NULL,                     "
  "      dns_type      BLOB NOT NULL,                     "
  "      data_name     BLOB NOT NULL,                     "
  "      dns_value     BLOB NOT NULL,                     "
  "      PRIMARY KEY (dns_name, dns_type)                 "
  "  );                                                   "
  "CREATE INDEX dd_index ON DnsData(dns_name, dns_type);  "
  "CREATE INDEX dd_index2 ON DnsData(data_name);          ";

/**
 * A utility function to call the normal sqlite3_bind_text where the value and length are
 * value.c_str() and value.size().
 */
static int
sqlite3_bind_string(sqlite3_stmt* statement,
                    int index,
                    const string& value,
                    void(*destructor)(void*))
{
  return sqlite3_bind_text(statement, index, value.c_str(), value.size(), destructor);
}

/**
 * A utility function to call the normal sqlite3_bind_blob where the value and length are
 * block.wire() and block.size().
 */
static int
sqlite3_bind_block(sqlite3_stmt* statement,
                   int index,
                   const Block& block,
                   void(*destructor)(void*))
{
  return sqlite3_bind_blob(statement, index, block.wire(), block.size(), destructor);
}

/**
 * A utility function to generate string by calling the normal sqlite3_column_text.
 */
static string
sqlite3_column_string(sqlite3_stmt* statement, int column)
{
  return string(reinterpret_cast<const char*>(sqlite3_column_text(statement, column)),
                sqlite3_column_bytes(statement, column));
}

/**
 * A utility function to generate block by calling the normal sqlite3_column_text.
 */
static Block
sqlite3_column_block(sqlite3_stmt* statement, int column)
{
  return Block(reinterpret_cast<const char*>(sqlite3_column_blob(statement, column)),
               sqlite3_column_bytes(statement, column));
}


ContactStorage::ContactStorage(const Name& identity)
  : m_identity(identity)
{
  fs::path chronosDir = fs::path(getenv("HOME")) / ".chronos";
  fs::create_directories(chronosDir);

  int res = sqlite3_open((chronosDir / getDBName()).c_str(), &m_db);
  if (res != SQLITE_OK)
    throw Error("Chronos DB cannot be open/created");

  initializeTable("SelfProfile", INIT_SP_TABLE);
  initializeTable("SelfEndorse", INIT_SE_TABLE);
  initializeTable("Contact", INIT_CONTACT_TABLE);
  initializeTable("TrustScope", INIT_TS_TABLE);
  initializeTable("ContactProfile", INIT_CP_TABLE);
  initializeTable("ProfileEndorse", INIT_PE_TABLE);
  initializeTable("CollectEndorse", INIT_CE_TABLE);
  initializeTable("DnsData", INIT_DD_TABLE);

}

string
ContactStorage::getDBName()
{
  string dbName("chronos-");

  std::stringstream ss;
  {
    using namespace CryptoPP;

    SHA256 hash;
    StringSource(m_identity.wireEncode().wire(), m_identity.wireEncode().size(), true,
                 new HashFilter(hash, new HexEncoder(new FileSink(ss), false)));
  }
  dbName.append(ss.str()).append(".db");

  return dbName;
}

void
ContactStorage::initializeTable(const string& tableName, const string& sqlCreateStmt)
{
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db,
                     "SELECT name FROM sqlite_master WHERE type='table' And name=?",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, tableName, SQLITE_TRANSIENT);
  int res = sqlite3_step(stmt);

  bool tableExist = false;
  if (res == SQLITE_ROW)
    tableExist = true;
  sqlite3_finalize(stmt);

  if (!tableExist) {
    char *errmsg = 0;
    res = sqlite3_exec(m_db, sqlCreateStmt.c_str (), NULL, NULL, &errmsg);
    if (res != SQLITE_OK && errmsg != 0)
      throw Error("Init \"error\" in " + tableName);
  }
}

shared_ptr<Profile>
ContactStorage::getSelfProfile()
{
  shared_ptr<Profile> profile = make_shared<Profile>(m_identity);
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "SELECT profile_type, profile_value FROM SelfProfile", -1, &stmt, 0);

  while (sqlite3_step(stmt) == SQLITE_ROW) {
    string profileType = sqlite3_column_string(stmt, 0);
    string profileValue = sqlite3_column_string (stmt, 1);
    (*profile)[profileType] = profileValue;
  }
  sqlite3_finalize(stmt);

  return profile;
}

void
ContactStorage::addSelfEndorseCertificate(const EndorseCertificate& newEndorseCertificate)
{
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db,
                     "INSERT OR REPLACE INTO SelfEndorse (identity, endorse_data) values (?, ?)",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, m_identity.toUri(), SQLITE_TRANSIENT);
  sqlite3_bind_block(stmt, 2, newEndorseCertificate.wireEncode(), SQLITE_TRANSIENT);
  sqlite3_step(stmt);

  sqlite3_finalize(stmt);
}

void
ContactStorage::addEndorseCertificate(const EndorseCertificate& endorseCertificate,
                                      const Name& identity)
{
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db,
                     "INSERT OR REPLACE INTO ProfileEndorse \
                      (identity, endorse_data) values (?, ?)",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, identity.toUri(), SQLITE_TRANSIENT);
  sqlite3_bind_block(stmt, 2, endorseCertificate.wireEncode(), SQLITE_TRANSIENT);
  sqlite3_step(stmt);

  sqlite3_finalize(stmt);
}

void
ContactStorage::updateCollectEndorse(const EndorseCertificate& endorseCertificate)
{
  Name endorserName = endorseCertificate.getSigner();
  Name certName = endorseCertificate.getName();

  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db,
                     "INSERT OR REPLACE INTO CollectEndorse \
                      (endorser, endorse_name, endorse_data) \
                      VALUES (?, ?, ?, ?)",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, endorserName.toUri(), SQLITE_TRANSIENT);
  sqlite3_bind_string(stmt, 2, certName.toUri(), SQLITE_TRANSIENT);
  sqlite3_bind_block(stmt, 3, endorseCertificate.wireEncode(), SQLITE_TRANSIENT);
  sqlite3_step(stmt);
  sqlite3_finalize(stmt);
  return;
}

void
ContactStorage::getCollectEndorse(EndorseCollection& endorseCollection)
{
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "SELECT endorse_name, endorse_data FROM CollectEndorse", -1, &stmt, 0);

  while (sqlite3_step(stmt) == SQLITE_ROW) {
    string certName = sqlite3_column_string(stmt, 0);
    std::stringstream ss;
    {
      using namespace CryptoPP;
      SHA256 hash;

      StringSource(sqlite3_column_text(stmt, 1), sqlite3_column_bytes (stmt, 1), true,
                   new HashFilter(hash, new FileSink(ss)));
    }
    EndorseCollection::Endorsement* endorsement = endorseCollection.add_endorsement();
    endorsement->set_certname(certName);
    endorsement->set_hash(ss.str());
  }

  sqlite3_finalize(stmt);
}

void
ContactStorage::getEndorseList(const Name& identity, vector<string>& endorseList)
{
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db,
                     "SELECT profile_type FROM ContactProfile \
                      WHERE profile_identity=? AND endorse=1 ORDER BY profile_type",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, identity.toUri(), SQLITE_TRANSIENT);

  while (sqlite3_step(stmt) == SQLITE_ROW) {
    string profileType = sqlite3_column_string(stmt, 0);
    endorseList.push_back(profileType);
  }
  sqlite3_finalize(stmt);
}


void
ContactStorage::removeContact(const Name& identityName)
{
  string identity = identityName.toUri();

  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "DELETE FROM Contact WHERE contact_namespace=?", -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
  sqlite3_step(stmt);
  sqlite3_finalize(stmt);

  sqlite3_prepare_v2(m_db, "DELETE FROM ContactProfile WHERE profile_identity=?", -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
  sqlite3_step(stmt);
  sqlite3_finalize(stmt);

  sqlite3_prepare_v2(m_db, "DELETE FROM TrustScope WHERE contact_namespace=?", -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
  sqlite3_step(stmt);
  sqlite3_finalize(stmt);
}

void
ContactStorage::addContact(const Contact& contact)
{
  if (doesContactExist(contact.getNameSpace()))
    throw Error("Normal Contact has already existed");

  string identity = contact.getNameSpace().toUri();
  bool isIntroducer = contact.isIntroducer();

  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db,
                     "INSERT INTO Contact (contact_namespace, contact_alias, contact_keyName, \
                      contact_key, notBefore, notAfter, is_introducer) \
                      values (?, ?, ?, ?, ?, ?, ?)",
                     -1, &stmt, 0);

  sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
  sqlite3_bind_string(stmt, 2, contact.getAlias(), SQLITE_TRANSIENT);
  sqlite3_bind_string(stmt, 3, contact.getPublicKeyName().toUri(), SQLITE_TRANSIENT);
  sqlite3_bind_text(stmt, 4,
                    reinterpret_cast<const char*>(contact.getPublicKey().get().buf()),
                    contact.getPublicKey().get().size(), SQLITE_TRANSIENT);
  sqlite3_bind_int64(stmt, 5, time::toUnixTimestamp(contact.getNotBefore()).count());
  sqlite3_bind_int64(stmt, 6, time::toUnixTimestamp(contact.getNotAfter()).count());
  sqlite3_bind_int(stmt, 7, (isIntroducer ? 1 : 0));

  int res = sqlite3_step(stmt);

  sqlite3_finalize(stmt);

  const Profile& profile = contact.getProfile();
  for (Profile::const_iterator it = profile.begin(); it != profile.end(); it++) {
    sqlite3_prepare_v2(m_db,
                       "INSERT INTO ContactProfile \
                        (profile_identity, profile_type, profile_value, endorse) \
                        values (?, ?, ?, 0)",
                       -1, &stmt, 0);
    sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
    sqlite3_bind_string(stmt, 2, it->first, SQLITE_TRANSIENT);
    sqlite3_bind_string(stmt, 3, it->second, SQLITE_TRANSIENT);
    res = sqlite3_step(stmt);
    sqlite3_finalize(stmt);
  }

  if (isIntroducer) {
    Contact::const_iterator it  = contact.trustScopeBegin();
    Contact::const_iterator end = contact.trustScopeEnd();

    while (it != end) {
      sqlite3_prepare_v2(m_db,
                         "INSERT INTO TrustScope (contact_namespace, trust_scope) values (?, ?)",
                         -1, &stmt, 0);
      sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
      sqlite3_bind_string(stmt, 2, it->first.toUri(), SQLITE_TRANSIENT);
      res = sqlite3_step(stmt);
      sqlite3_finalize(stmt);
      it++;
    }
  }
}


shared_ptr<Contact>
ContactStorage::getContact(const Name& identity) const
{
  shared_ptr<Contact> contact;
  Profile profile;

  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db,
                     "SELECT contact_alias, contact_keyName, contact_key, notBefore, notAfter, \
                      is_introducer FROM Contact where contact_namespace=?",
                      -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, identity.toUri(), SQLITE_TRANSIENT);

  if (sqlite3_step(stmt) == SQLITE_ROW) {
    string alias = sqlite3_column_string(stmt, 0);
    string keyName = sqlite3_column_string(stmt, 1);
    PublicKey key(sqlite3_column_text(stmt, 2), sqlite3_column_bytes (stmt, 2));
    time::system_clock::TimePoint notBefore =
      time::fromUnixTimestamp(time::milliseconds(sqlite3_column_int64 (stmt, 3)));
    time::system_clock::TimePoint notAfter =
      time::fromUnixTimestamp(time::milliseconds(sqlite3_column_int64 (stmt, 4)));
    int isIntroducer = sqlite3_column_int (stmt, 5);

    contact = make_shared<Contact>(identity, alias, Name(keyName),
                                   notBefore, notAfter, key, isIntroducer);
  }
  sqlite3_finalize(stmt);

  sqlite3_prepare_v2(m_db,
                     "SELECT profile_type, profile_value FROM ContactProfile \
                      where profile_identity=?",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, identity.toUri(), SQLITE_TRANSIENT);

  while (sqlite3_step(stmt) == SQLITE_ROW) {
    string type = sqlite3_column_string(stmt, 0);
    string value = sqlite3_column_string(stmt, 1);
    profile[type] = value;
  }
  sqlite3_finalize(stmt);
  contact->setProfile(profile);

  if (contact->isIntroducer()) {
    sqlite3_prepare_v2(m_db,
                       "SELECT trust_scope FROM TrustScope WHERE contact_namespace=?",
                       -1, &stmt, 0);
    sqlite3_bind_string(stmt, 1, identity.toUri(), SQLITE_TRANSIENT);

    while (sqlite3_step(stmt) == SQLITE_ROW) {
      Name scope(sqlite3_column_string(stmt, 0));
      contact->addTrustScope(scope);
    }
    sqlite3_finalize(stmt);
  }

  return contact;
}


void
ContactStorage::updateIsIntroducer(const Name& identity, bool isIntroducer)
{
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "UPDATE Contact SET is_introducer=? WHERE contact_namespace=?",
                     -1, &stmt, 0);
  sqlite3_bind_int(stmt, 1, (isIntroducer ? 1 : 0));
  sqlite3_bind_string(stmt, 2, identity.toUri(), SQLITE_TRANSIENT);
  sqlite3_step(stmt);
  sqlite3_finalize(stmt);
  return;
}

void
ContactStorage::updateAlias(const Name& identity, const string& alias)
{
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "UPDATE Contact SET contact_alias=? WHERE contact_namespace=?",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, alias, SQLITE_TRANSIENT);
  sqlite3_bind_string(stmt, 2, identity.toUri(), SQLITE_TRANSIENT);
  sqlite3_step(stmt);
  sqlite3_finalize(stmt);
  return;
}

bool
ContactStorage::doesContactExist(const Name& name)
{
  bool result = false;

  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "SELECT count(*) FROM Contact WHERE contact_namespace=?", -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, name.toUri(), SQLITE_TRANSIENT);

  int res = sqlite3_step(stmt);

  if (res == SQLITE_ROW) {
    int countAll = sqlite3_column_int (stmt, 0);
    if (countAll > 0)
      result = true;
  }

  sqlite3_finalize(stmt);
  return result;
}

void
ContactStorage::getAllContacts(vector<shared_ptr<Contact> >& contacts) const
{
  vector<Name> contactNames;

  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "SELECT contact_namespace FROM Contact", -1, &stmt, 0);

  while (sqlite3_step(stmt) == SQLITE_ROW) {
    string identity = sqlite3_column_string(stmt, 0);
    contactNames.push_back(Name(identity));
  }
  sqlite3_finalize(stmt);

  for (vector<Name>::iterator it = contactNames.begin(); it != contactNames.end(); it++) {
    shared_ptr<Contact> contact = getContact(*it);
    if (static_cast<bool>(contact))
      contacts.push_back(contact);
  }
}

void
ContactStorage::updateDnsData(const Block& data, const string& name,
                              const string& type, const string& dataName)
{
  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db,
                     "INSERT OR REPLACE INTO DnsData (dns_name, dns_type, dns_value, data_name) \
                      VALUES (?, ?, ?, ?)",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, name, SQLITE_TRANSIENT);
  sqlite3_bind_string(stmt, 2, type, SQLITE_TRANSIENT);
  sqlite3_bind_block(stmt, 3, data, SQLITE_TRANSIENT);
  sqlite3_bind_string(stmt, 4, dataName, SQLITE_TRANSIENT);
  sqlite3_step(stmt);

  sqlite3_finalize(stmt);
}

shared_ptr<Data>
ContactStorage::getDnsData(const Name& dataName)
{
  shared_ptr<Data> data;

  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "SELECT dns_value FROM DnsData where data_name=?", -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, dataName.toUri(), SQLITE_TRANSIENT);

  if (sqlite3_step(stmt) == SQLITE_ROW) {
    data = make_shared<Data>();
    data->wireDecode(sqlite3_column_block(stmt, 0));
  }
  sqlite3_finalize(stmt);

  return data;
}

shared_ptr<Data>
ContactStorage::getDnsData(const string& name, const string& type)
{
  shared_ptr<Data> data;

  sqlite3_stmt *stmt;
  sqlite3_prepare_v2(m_db, "SELECT dns_value FROM DnsData where dns_name=? and dns_type=?",
                     -1, &stmt, 0);
  sqlite3_bind_string(stmt, 1, name, SQLITE_TRANSIENT);
  sqlite3_bind_string(stmt, 2, type, SQLITE_TRANSIENT);

  if (sqlite3_step(stmt) == SQLITE_ROW) {
    data = make_shared<Data>();
    data->wireDecode(sqlite3_column_block(stmt, 0));
  }
  sqlite3_finalize(stmt);

  return data;
}

} // namespace chronos
