/*
 *   Copyright (C) 2012 Vladislav Sitalo <root@stvad.org>
 *
 *   This program is free software; you can redistribute it and/or modify
 *   it under the terms of the GNU General Public License version 2,
 *   or (at your option) any later version, as published by the Free
 *   Software Foundation
 *
 *   This program 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 this program; if not, write to the
 *   Free Software Foundation, Inc.,
 *   51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
 */

#include "sphinxcontrol.h"
#include <simonscenarios/modelmetadata.h>
#include <simonutils/fileutils.h>
#include <simonrecognizer/sphinxrecognitionconfiguration.h>
#include <simonrecognizer/sphinxrecognizer.h>

#include <KDebug>
#include <QDir>
#include <KStandardDirs>
#include <KLocale>


SphinxControl::SphinxControl(const QString& username, QObject* parent) : RecognitionControl(username, RecognitionControl::SPHINX, parent)
{
  recog = new SphinxRecognizer();
}

bool SphinxControl::initializeRecognition(const QString &modelPath)
{
  kDebug() << "Initializing to " << modelPath << m_lastModel;
  if (modelPath != m_lastModel) { //already initialized / tried to initialize with this exact model
    m_lastModel = modelPath;
    kDebug() << "Initializing";
    uninitialize();
    m_startRequests = 0;

    QString path = KStandardDirs::locateLocal("tmp", "/simond/"+username+"/sphinx/");
    if(!QDir(path).entryInfoList(QDir::NoDotAndDotDot | QDir::System | QDir::Hidden  | QDir::AllDirs | QDir::Files, QDir::DirsFirst).isEmpty())
    {
      kDebug() << "Removing old data from working dir";
      FileUtils::removeDirRecursive(path);
      path = KStandardDirs::locateLocal("tmp", "/simond/"+username+"/sphinx/");
    }

    kDebug() << "Unpacking model to working dir";
    if (!FileUtils::unpackAll(modelPath, path))
    {
      return false;
    }

    QFile metadataFile(path+QLatin1String("metadata.xml"));
    if(!metadataFile.open(QIODevice::ReadOnly))
    {
      emit recognitionError(i18n("Failed to read metadata from \"%1\"", path+QLatin1String("metadata.xml")),
                            getBuildLog());
      return NULL;
    }
    ModelMetadata metadata;
    QDomDocument DomDocument;
    DomDocument.setContent(&metadataFile);
    metadata.deserializeXml(DomDocument.documentElement());

    metadataFile.close();

    modelName = metadata.name();
  }
  kDebug() << "Emitting recognition ready";
  emit recognitionReady();
  return true;
}

RecognitionConfiguration *SphinxControl::setupConfig()
{
  kDebug() << "Setting config up";
  QString dirPath = KStandardDirs::locateLocal("tmp", "/simond/"+username+"/sphinx/");

  return new SphinxRecognitionConfiguration(dirPath, dirPath+modelName+QLatin1String(".jsgf"),
                                            dirPath+modelName+QLatin1String(".dic"), DEFAULT_SAMPRATE);
}

void SphinxControl::emitError(const QString &error)
{
  emit recognitionError(error, getBuildLog());
}
