/*
 Copyright 2019 Alain Dargelas
 
 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.
 */

/* 
 * File:   Report.cpp
 * Author: alain
 * 
 * Created on April 10, 2017, 8:56 PM
 */

#include "../SourceCompile/SymbolTable.h"
#include "ErrorContainer.h"
#include "../CommandLine/CommandLineParser.hpp"
#include "Report.h"
#include <iostream>
#include <fstream>
#include <unistd.h>
#include <iomanip>
#include <regex>
#include <mutex>
using namespace SURELOG;

Report::Report () { }

Report::Report (const Report& orig) { }

Report::~Report () { }


class Result {
public:
  std::string m_nbFatal;
  std::string m_nbError;
  std::string m_nbWarning;
  std::string m_nbNote;
  std::string m_nbInfo;
};

bool
parseReportFile (std::string logFile, Result& result)
{
  bool ret = false;
  std::ifstream ifs (logFile.c_str ());
  if (!ifs.bad ())
    {
      std::string line;
      while (std::getline (ifs, line))
        {
          if (ifs.bad()) break;
          if (line.find ("[  FATAL] : ") != std::string::npos)
            {
              result.m_nbFatal = line.substr (12, line.size()-11);
            }
          if (line.find ("[  ERROR] : ") != std::string::npos)
            {
              result.m_nbError = line.substr (12, line.size()-11);
            }
          if (line.find ("[WARNING] : ") != std::string::npos)
            {
              result.m_nbWarning = line.substr (12, line.size()-11);
            }
          if (line.find ("[   NOTE] : ") != std::string::npos)
            {
              result.m_nbNote = line.substr (12, line.size()-11);
              ret = true;
            }
          if (line.find ("[   INFO] : ") != std::string::npos)
            {
              result.m_nbInfo = line.substr (12, line.size()-11);
              ret = true;
            }
        }
    }
  
  ifs.close ();
  return ret;
}

std::pair<bool, bool> Report::makeDiffCompUnitReport (CommandLineParser* clp, SymbolTable* st) 
{
  //std::mutex m;
  //m.lock();
  std::string odir = st->getSymbol(clp->getOutputDir());
  std::string alldir =  st->getSymbol(clp->getCompileAllDir());
  std::string unitdir = st->getSymbol(clp->getCompileUnitDir());
  std::string log = st->getSymbol(clp->getDefaultLogFileId()); 
  std::string alllog = odir + alldir + log;
  std::string unitlog = odir + unitdir + log;
  bool readAll = false;
  bool readUnit = false;
  Result readAllResult;
  Result readUnitResult;
  
  while ((!readAll) || (!readUnit)) 
    {
      usleep (1000);
      if (!readAll)
        {
          readAll = parseReportFile(alllog, readAllResult);      
        }
      if (!readUnit)
        {
          readUnit = parseReportFile(unitlog, readUnitResult);      
        }     
    }
  
  clp->printBanner();
  
  std::cout << "|-------|------------------|-------------------|" << std::endl;
  std::cout << "|       |  FILE UNIT COMP  |  ALL COMPILATION  |" << std::endl;
  std::cout << "|-------|------------------|-------------------|" << std::endl;
  std::cout << "| FATAL | " << std::setw (9) << readUnitResult.m_nbFatal   << "        | " << std::setw (9) << readAllResult.m_nbFatal   << "         |" << std::endl;
  std::cout << "| ERROR | " << std::setw (9) << readUnitResult.m_nbError   << "        | " << std::setw (9) << readAllResult.m_nbError   << "         |" << std::endl;
  std::cout << "|WARNING| " << std::setw (9) << readUnitResult.m_nbWarning << "        | " << std::setw (9) << readAllResult.m_nbWarning << "         |" << std::endl;
  std::cout << "| INFO  | " << std::setw (9) << readUnitResult.m_nbInfo    << "        | " << std::setw (9) << readAllResult.m_nbInfo    << "         |" << std::endl;
  std::cout << "| NOTE  | " << std::setw (9) << readUnitResult.m_nbNote    << "        | " << std::setw (9) << readAllResult.m_nbNote    << "         |" << std::endl;
  std::cout << "|-------|------------------|-------------------|" << std::endl;
  std::cout << std::endl;
  std::cout << "FILE UNIT LOG: " << unitlog << std::endl;
  std::cout << "ALL FILES LOG: " << alllog  << std::endl;
  
  std::string diffFile = odir + unitdir + "diff.log";
  
  std::string diffCmd = "diff -r " + odir + unitdir + " " + odir + alldir + " --exclude cache --brief > " + diffFile ;
  
  int retval = system (diffCmd.c_str());
  
  std::ifstream ifs (diffFile.c_str ());
  if (!ifs.bad ())
    {
      std::cout << "\nDIFFS:" << std::endl;
      std::string line;
      while (std::getline (ifs, line))
        {
          if (line.find("diff.log") != std::string::npos)
            {
              continue;
            }
          if (line.find(log.c_str ()) != std::string::npos)
            {
              continue;
            }
          
          line = std::regex_replace(line, std::regex("Files "), "");
          line = std::regex_replace(line, std::regex("differ"), "");
          std::cout << line << std::endl;
        }
    }
  
  clp->printFooter();
  int nbFatal = atoi(readUnitResult.m_nbFatal.c_str()) + atoi(readAllResult.m_nbFatal.c_str());
  //m.unlock();
  return std::make_pair(retval != -1, !nbFatal);
}


