#include <boost/algorithm/string/case_conv.hpp>
#include <cctype>
#include <iostream>
#include <stdio.h>
#include <string>
#include <cctype>
#include <sqlite/command.hpp>
#include <sqlite/result.hpp>
#include <sqlite3.h>
#include <boost/algorithm/string.hpp>
/*
 * Implementing SQLite3 on suggestion from MD.rpm - Thanks MD!
 *
*/
//Declare all the functions
static int createDB(const char* s);
static int searchTable(const char* s, std::string msearch);
static int callback(void* NotUsed, int argc, char** argv, char** azColName);

// static int createTable(const char* s);

int main() {

  const char* dbFile = "hardware.db";
  sqlite3* hardwareDB;

  std::string msearch;
  std::string msearchlower;

  createDB(dbFile);

  char quit = '&';
  char searchby = '&';

  while(tolower(quit) != 'q') {
    std::cout << "\t\t----------=================================--------------\n";
    std::cout << "\t\t\tWelcome to the Universal Hardware database!\n";
    std::cout << "\t(S)earch for a part by model name\n";
    std::cout << "\t(Q)uit hardware database\n->";
    std::cin >>  quit; 
    switch(tolower(quit)) {
      case 's': 
        std::cout << "\t\t\tWhat would you like to search by?\n";
        std::cout << "\t(M)odel name\n";
        std::cout << "\tManufacture(R)\n";
        std::cout << "\t(Y)ear Released\n";
        std::cout << "\tMain (C)lock\n";
        std::cout << "\t(Q)uit\n->";
        std::cin >> searchby;
        switch(tolower(searchby)) {
          case 'm':
            std::cout << "\t\tEnter part of the model string.\n";
            std::cout << "\t\tExample: for Intel i75820k you would enter 5820\n->";
            std::cin >> msearch;
            msearchlower = boost::algorithm::to_lower_copy(msearch);
            searchTable(dbFile, msearchlower); // Replace this string with a variable that is the query grabbed from the user!  
            break;
          case 'r':
            std::cout << "Coming Soon!!!\n";
            break;
          case 'y':
            std::cout << "Coming Soon!!!\n";
            break;
          case 'c':
            std::cout << "Coming Soon!!!\n";
            break;
          default:
            break;
        }
      break;
      case 'q':
        break;
      // default:
        // break;
    }
  }

  // system("sleep 1s");
  return 0;
}

static int createDB(const char* s) {
  
  sqlite3* hardwareDB;
  int exit = 0;
  exit = sqlite3_open(s, &hardwareDB);

  sqlite3_close(hardwareDB);

  return 0;
}

static int searchTable(const char* s, std::string msearchlower) {

  sqlite3* hardwareDB;

  int exit = sqlite3_open(s, &hardwareDB);

  std::string sql = "SELECT * FROM cpu WHERE model LIKE '%" + msearchlower + "%';";

  sqlite3_exec(hardwareDB, sql.c_str(), callback, NULL, NULL);

  return 0;
}

static int callback(void* NotUsed, int argc, char** argv, char** azColName) {
  // Wrap out ouput so it's easier to read for multiple results
  std::cout << "=====================" << std::endl;

  for (int i=0; i < argc; i++) {
    //column name and value
    std::cout << azColName[i] << ": " << argv[i] << std::endl;
  }

  std::cout << std::endl;
  return 0;
}
