#include "fmPlugin.h"
#include <QtSql/QSqlError>
#include <QtSql/QSqlQuery>
#include <QVariant>
#include <QDebug>
#include <QSettings>
#include <windows.h>
#include <QDir>
#include <QFile>
#include <QCoreApplication>
#include <QLibrary>
#include <QJsonDocument>
#include <QJsonObject>
#include <QJsonArray>

FmPlugin &FmPlugin::GetInstance()
{
    static FmPlugin fmPlugin;
    return fmPlugin;
}

bool FmPlugin::ConnectDb(const QString &host, const QString &username, const QString &password, const QString &dbname, QString &error)
{
    // TODO(用于鲜丰演示)
    return true;

    // 清除之前的连接
    QSqlDatabase::removeDatabase(m_db.connectionName());

    m_db = QSqlDatabase::addDatabase("QODBC");
    m_db.setConnectOptions(QString("SQL_ATTR_LOGIN_TIMEOUT=5;SQL_ATTR_CONNECTION_TIMEOUT=5"));
    m_db.setDatabaseName(QString("Driver={sql server}; server=%1; database=%2; uid=%3; pwd=%4")
                             .arg(host).arg(dbname).arg(username).arg(password));

    if(m_db.open())
    {
       error = QString("success");
       m_db.close();

       return true;
    }else
    {
       error = m_db.lastError().text();

       return false;
    }
}

bool FmPlugin::GetStoreInfo(QString &storeId, QString &posId, QString &cashierId, QDateTime &dateTime, QString &error)
{

   QSettings reg("HKEY_LOCAL_MACHINE\\SOFTWARE\\Hisensoft Co.Ltd\\FoodPos", QSettings::NativeFormat);

   storeId = reg.value("OrgCode").toString();

   posId = "1";
   cashierId = "1";

   if(storeId.isEmpty())
   {
       return false;
   }


   return true;
}

bool FmPlugin::GetOnDutyCashiers(QList<CashierObject> &cashiersList, QString &error)
{
    // TODO(用于鲜丰演示)
    CashierObject obj;
    obj.id = "001";
    obj.name = "鲜丰测试";
    cashiersList.append(obj);
    return true;


    if(!m_db.open())
    {
        error = m_db.lastError().text();
        return false;
    }
    // 获取在班收银员信息
    QSqlQuery query = QSqlQuery(m_db);
    QString queryCashiers("select * from v_km_cashshift;");
    query.prepare(queryCashiers);
    if (!query.exec())
    {
        error = query.lastError().text();
        m_db.close();
        return false;
    }
    while(query.next())
    {
        CashierObject cashierObj;
        cashierObj.id           = query.value(0).toString();
        cashierObj.name         = query.value(1).toString();
        cashierObj.shiftId      = query.value(2).toString();
        cashierObj.shiftName    = query.value(3).toString();
        cashiersList.append(cashierObj);
    }

    error = QString("success");
    m_db.close();
    return true;
}

bool FmPlugin::DoOrderEntry(const OrderObject *orderObject, QString &error)
{
    _GetOrderStr(orderObject);
    QString dirPath = QString("%1/orders").arg(QCoreApplication::applicationDirPath());
    QDir dir;
    dir.mkdir(dirPath);
    QFile file(QString("%1/%2").arg(dirPath, orderObject->order_id));
    if(file.exists())
    {
        return true;
    }

    if(f_UFMSaveSales==NULL)
    {
        QString appDir;
        QSettings reg("HKEY_LOCAL_MACHINE\\SOFTWARE\\Hisensoft Co.Ltd\\FoodPos", QSettings::NativeFormat);
        appDir = reg.value("AppDir").toString();

        m_lib.setFileName(QString("%1/MHiFMSaveSales.dll").arg(appDir));
        if(m_lib.load())
        {
           f_UFMSaveSales = (UFMSaveSales)m_lib.resolve("UFMSaveSales");
           if(f_UFMSaveSales!=NULL)
           {
               error = QString("load UFMSaveSales failed");
           }
        }else
        {
            qDebug() << m_lib.errorString();
            error = QString("load dll failed[%1]").arg(appDir + "/MHiFMSaveSales.dll");
        }
    }
    if(f_UFMSaveSales!=NULL)
    {
        char tmp[100] = {0};
        if(1==f_UFMSaveSales(_GetOrderStr(orderObject).toLocal8Bit().data(), tmp))
        {
            file.open(QIODevice::WriteOnly);
            file.close();
            return true;
        }else
        {
            QJsonObject obj = QJsonDocument::fromJson(QString::fromLocal8Bit(tmp).toUtf8()).object();
            error = obj["Msg"].toString();
        }
    }
    qDebug() << error;
    return false;
}

bool FmPlugin::GetStockInfo(QList<StockObject> &stockList, QString &error)
{
    if(!m_db.open())
    {
        error = m_db.lastError().text();
        return false;
    }
    StockObject stock;
    QSqlQuery query = QSqlQuery(m_db);
    QString queryStock("select * from v_km_clearfood;");
    query.prepare(queryStock);
    if (!query.exec())
    {
        error = query.lastError().text();
        m_db.close();
        return false;
    }
    while(query.next())
    {
        stock.id = query.value(0).toString();
        stock.num = query.value(2).toInt();
        stockList.append(stock);
    }
    error = QString("success");
    m_db.close();
    return true;
}

bool FmPlugin::_InsertInto_p_t_fmwm_custinfo(int &custid)
{
    QSqlQuery query =  QSqlQuery(m_db);
    // 插入顾客信息表
    QString queryInsert("insert into p_t_fmwm_custinfo(cphone, ccust_n, ssex, saddr) \
                         values(?,?,?,?) select @@identity;");
    query.prepare(queryInsert);
    query.bindValue(0, m_orderObject->phone);
    query.bindValue(1, m_orderObject->customer);
    query.bindValue(2, "");
    query.bindValue(3, m_orderObject->address);
    if(!query.exec())
    {
       return false;
    }
    query.next();
    custid = query.value(0).toInt();
    return true;
}

bool FmPlugin::_InsertInto_d_t_food_fmbill0(const QString& cashierId, const QString& cashierName, const QString& shiftId, const QString& shiftName, int custid)
{
    QSqlQuery query = QSqlQuery(m_db);
    // 查询营业日
    QDateTime dbussiness;
    QString queryDateTime("select sys_var_value from sys_t_system where sys_var_id='dBusiness';");
    query.prepare(queryDateTime);
    if (!query.exec())
    {
        m_lastError = query.lastError().text();
        return false;
    }
    query.next();
    dbussiness = query.value(0).toDateTime();

    // 插入到临时表
    QString queryInsert("insert into d_t_food_fmbill0(cbill_c,cbranch_c,dBusiness,"
                         "ccashier_c, ccashier_n, cshift_c, cshift_n,"
                         "iguestnum,dtbilltime,dtsettletime,noughtamt,npayamt,"
                         "ndisamt,sbilltype,fmwmbillid,sprovider,nfreight,icustid)"
                         "values(?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?);");
    query.prepare(queryInsert);
    query.bindValue(0, m_orderObject->order_id);
    query.bindValue(1, m_storeId);
    query.bindValue(2, dbussiness);
    query.bindValue(3, cashierId);
    query.bindValue(4, cashierName);
    query.bindValue(5, shiftId);
    query.bindValue(6, shiftName);
    query.bindValue(7, m_orderObject->remark.mid(m_orderObject->remark.lastIndexOf(':')+1).toInt());
    query.bindValue(8, QDateTime::fromTime_t(m_orderObject->create_time));
    query.bindValue(9, QDateTime::fromTime_t(m_orderObject->create_time));
    query.bindValue(10, _Penny2Dollar(m_orderObject->shop_fee));
    query.bindValue(11, _Penny2Dollar(m_orderObject->shop_fee));
    query.bindValue(12, _Penny2Dollar(m_orderObject->discount_fee));
    query.bindValue(13, QString("\351\200\201\351\244\220\345\215\225"));// 送餐单
    query.bindValue(14, m_orderObject->order_id);
    query.bindValue(15, m_orderObject->channelName);
    query.bindValue(16, m_orderObject->pay_type.compare("在线支付") ? "0" : _Penny2Dollar(m_orderObject->send_fee));
    query.bindValue(17, custid);
    if(!query.exec())
    {
        m_lastError = query.lastError().text();
        return false;
    }
    return true;
}

bool FmPlugin::_InsertInto_d_t_food_fmbills0()
{
    QSqlQuery query = QSqlQuery(m_db);
    // 插入商品详情
    QString queryInsert("insert into d_t_food_fmbills0(cbill_c,cfoodbill,"
                         "cfood_c,cfood_n,nqty,nprc,namt)"
                         "values(?,?,?,?,?,?,?);");
    query.prepare(queryInsert);
    for(int i=0; i<m_orderObject->proList.count(); i++)
    {
        query.bindValue(0, m_orderObject->order_id);
        query.bindValue(1, QString("%1").arg(QString::number(i+1),4,QChar('0')));
        query.bindValue(2, m_orderObject->proList.at(i)->pid);
        query.bindValue(3, m_orderObject->proList.at(i)->name);
        query.bindValue(4, QString::number(m_orderObject->proList.at(i)->productAmount));
        query.bindValue(5, _Penny2Dollar(m_orderObject->proList.at(i)->price));
        query.bindValue(6, _Penny2Dollar(m_orderObject->proList.at(i)->price*m_orderObject->proList.at(i)->productAmount));
        if(!query.exec())
        {
            m_lastError = query.lastError().text();
            return false;
        }
    }
    return true;
}

bool FmPlugin::_InsertInto_d_t_bill_fmpay0()
{
    QSqlQuery query = QSqlQuery(m_db);
    // 插入支付详情
    QString queryInsert("insert into d_t_bill_fmpay0(cbill_c,"
                         "cbillpay,cpay_c,cpay_n,npayamt)"
                         "values(?,?,?,?,?);");
    query.prepare(queryInsert);
    query.bindValue(0, m_orderObject->order_id);
    query.bindValue(1, "01");
    QString cpay_c, cpay_n;
    if(!m_orderObject->pay_type.compare("在线支付"))
    {
        if(!m_orderObject->channel.compare("mtwm"))
        {
            cpay_c = QString("14");
            cpay_n = QString("\347\276\216\345\233\242\345\244\226\345\215\226");//美团外卖
        }else if(!m_orderObject->channel.compare("fmwd"))
        {
            cpay_c = QString("13");
            cpay_n = QString("\345\276\256\344\277\241\345\244\226\345\215\226");//微店外卖
        }
    }else
    {
        cpay_c = QString("01");
        cpay_n = QString("\347\216\260\351\207\221");//现金
    }
    query.bindValue(2, cpay_c);
    query.bindValue(3, cpay_n);
    query.bindValue(4, _Penny2Dollar(m_orderObject->shop_fee));
    if(!query.exec())
    {
        m_lastError = query.lastError().text();
        return false;
    }
    return true;
}

bool FmPlugin::_Exec_pr_fmwm()
{
    QSqlQuery query = QSqlQuery(m_db);
    query.prepare("exec pr_fmwm ?, ? output;");
    query.bindValue(0, m_orderObject->order_id);
    query.bindValue(1, 0, QSql::Out);
    if(!query.exec())
    {
        m_lastError = query.lastError().text();
        return false;
    }
    if(query.boundValue(1).toInt() != 1)
    {
        m_lastError = QString("pr_fmwm result[%1]").arg(query.boundValue(1).toInt());
        return false;
    }
    return true;
}

QString FmPlugin::_Penny2Dollar(int penny)
{
    double dollar = (double)penny/100;
    return QString::number(dollar,'f',2);
}

QString FmPlugin::_GetOrderStr( const OrderObject *orderObject)
{
    QJsonObject rObj;
    float YsTotal = _Penny2Dollar(orderObject->total_fee-orderObject->send_fee-orderObject->service_fee-orderObject->dis_shop_fee).toFloat();
    rObj.insert("BillNo", orderObject->order_id);
    rObj.insert("XsDate", QDateTime::fromTime_t(orderObject->create_time).toString("yyyy-MM-dd hh:mm:ss"));
    rObj.insert("OprtID", 1);
    rObj.insert("OprtCode", "001");
    rObj.insert("YsTotal", QString::number(YsTotal,'f',2));


    float sca = (float)(orderObject->total_fee-orderObject->send_fee-orderObject->service_fee-orderObject->dis_shop_fee)/orderObject->product_fee;
    float SsTotal =0;
    QJsonArray products;
    for(int i=0; i < orderObject->proList.count(); i++)
    {
        QJsonObject tObj;
        tObj.insert("LnNo", i+1);
        tObj.insert("PluCode", orderObject->proList.at(i)->pid);
        tObj.insert("PluName", orderObject->proList.at(i)->name);
        tObj.insert("Price", _Penny2Dollar(orderObject->proList.at(i)->price));
        tObj.insert("XsCount", QString::number(orderObject->proList.at(i)->productAmount,'f', 2));
        if((i+1) == orderObject->proList.count())
        {
            tObj.insert("YsTotal",QString::number(YsTotal-SsTotal,'f',2) );
        }else
        {

            float Ys = _Penny2Dollar((orderObject->proList.at(i)->price*orderObject->proList.at(i)->productAmount)*sca).toFloat();

            tObj.insert("YsTotal", QString::number(Ys,'f',2));
            SsTotal += Ys;
        }

        products.insert(i, tObj);
    }
    rObj.insert("PluDetails", products);

    QJsonArray payDetails;
    QString zfCode = "001";
    QString zfName = "非码外卖";

    QSettings set(QString("%1/config.ini").arg(QCoreApplication::applicationDirPath()), QSettings::IniFormat);
    set.setIniCodec("utf-8");
    if(orderObject->pay == 1)
    {
        zfCode = set.value(QString("payDetails/cash")).toString();
        zfName = "现金";
    }else
    {
        QStringList values  = set.value(QString("payDetails/%1").arg(orderObject->channel)).toString().split('|');
        if(values.count()==2)
        {
            zfCode = values.at(0);
            zfName = values.at(1);
        }
    }

    QJsonObject tObj;
    tObj.insert("SerialNo", 1);
    tObj.insert("ZfCode", zfCode);
    tObj.insert("ZfName", zfName);
    tObj.insert("ZfTotal", QString::number(YsTotal,'f',2));
    tObj.insert("TradeNo", "");
    payDetails.insert(0, tObj);
    rObj.insert("PayDetails", payDetails);

    qDebug() << rObj;
    QJsonDocument doc(rObj);
    return QString(doc.toJson(QJsonDocument::Compact));
}
