
/***********************************************************
*  Email server settings
***********************************************************/
// #define SMTPSERVER "smtp.office365.com"  // hotmail.com or live.com
// #define SMTPSERVER "smtp.gmail.com"  // gmail


class emails
{
    public:
        emails();
        void sendEmail(std::string subject, std::string message);  // send email
        void startupEmails();  // run at startup
        void updateSMTP(short userID, std::string server, short provider, short port, std::string user, std::string pass, std::string aEmail, std::string r1, std::string r2, std::string r3, short r2e, short r3e, short enable);
        std::string base64_encode(const std::string &in);  // encode strings
        std::string base64_decode(const std::string &in);  // decode strings
    private:
        short emailEnabled = 0;
	    std::string smtpServer = "";  // 
	    unsigned int smtpPort = 587;  // 
	    std::string smtpUser = "";  // 
	    std::string smtpPass = "";  // 
        typedef unsigned char uchar;
        std::string adminEmail = "";
        std::string recipient1 = "";
        std::string recipient2 = "";
        std::string recipient3 = "";
        short recipient2Enabled = 0;
        short recipient3Enabled = 0;
};
emails::emails(){}

void emails::sendEmail(std::string subject, std::string message)
{
    if (emailEnabled == 1)
    {
        if (smtpPass != "") {  // has a password
            const char *server = smtpServer.c_str();
            const char *user = smtpUser.c_str();
            const char *pass = smtpPass.c_str();
            const char *to = recipient1.c_str();
            const char *cc = recipient2.c_str();
            const char *bcc = recipient3.c_str();
            // std::cout << "Hello World ------------" << std::endl;

            const char* errmsg;
            /* Initialize email and send */
            quickmail_initialize();
            quickmail mailobj = quickmail_create(user, subject.c_str());
            quickmail_add_to (mailobj, to);
            if (recipient2Enabled == 1) {quickmail_add_cc (mailobj, cc);}
            if (recipient3Enabled == 1) {quickmail_add_cc (mailobj, bcc);}
            quickmail_set_body(mailobj, message.c_str());
            // printf("Attaching: %s...\n", fname);
            // quickmail_add_attachment_file(mailobj, fname, NULL);
            // std::cout << "sending message ------------" << std::endl;
            if ((errmsg = quickmail_send(mailobj, server, smtpPort, user, pass)) != NULL) {
            // if ((errmsg = quickmail_send_secure(mailobj, SMTPSERVER, SMTPPORT, SMTPUSER, SMTPPASS)) != NULL) {
                fprintf(stderr, "Error sending e-mail: %s\n", errmsg);
            }
            quickmail_destroy(mailobj);
            
            // std::cout << "Message sent ------------" << std::endl;
        }
    }
}

std::string emails::base64_encode(const std::string &in) {  // encode strings
    std::string out = "";

    int val = 0, valb = -6;
    for (uchar c : in) {
        val = (val << 8) + c;
        valb += 8;
        while (valb >= 0) {
            out.push_back("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"[(val>>valb)&0x3F]);
            valb -= 6;
        }
    }
    if (valb>-6) out.push_back("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"[((val<<8)>>(valb+8))&0x3F]);
    while (out.size()%4) out.push_back('=');
    return out;
}

std::string emails::base64_decode(const std::string &in) {  // decode strings
    std::string out= "";

    std::vector<int> T(256,-1);
    for (int i=0; i<64; i++) T["ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"[i]] = i;

    int val=0, valb=-8;
    for (uchar c : in) {
        if (T[c] == -1) break;
        val = (val << 6) + T[c];
        valb += 6;
        if (valb >= 0) {
            out.push_back(char((val>>valb)&0xFF));
            valb -= 8;
        }
    }
    return out;
}

void emails::updateSMTP(short userID, std::string server, short provider, short port, std::string user, std::string pass, std::string aEmail, std::string r1, std::string r2, std::string r3, short r2e, short r3e, short enable) {
    // std::cout << " " << std::endl;
    // std::cout << "updateSMTP------------------------------" << std::endl;
    
    // std::cout << "userID ------------ " << userID << std::endl;
    // std::cout << "server ------------ " << server << std::endl;
    // std::cout << "port   ------------ " << port << std::endl;
    // std::cout << "provider  --------- " << provider << std::endl;
    // std::cout << "user   ------------ " << user << std::endl;
    // std::cout << "pass   ------------ " << pass << std::endl;
    // std::cout << "aEmail ------------ " << aEmail << std::endl;
    // std::cout << "r1     ------------ " << r1 << std::endl;
    // std::cout << "r2     ------------ " << r2 << std::endl;
    // std::cout << "r3     ------------ " << r3 << std::endl;
    // std::cout << "r2e    ------------ " << r2e << std::endl;
    // std::cout << "r3e    ------------ " << r3e << std::endl;
    // std::cout << "enable ------------ " << enable << std::endl;
    
    smtpServer = server;
    smtpPort = port;
    smtpUser = user;
    adminEmail = aEmail;
    recipient1 = r1;
    recipient2 = r2;
    recipient2Enabled = r2e;
    recipient3 = r3;
    recipient3Enabled = r3e;
    emailEnabled = enable;

    connectMysql();
    std::string query = "UPDATE users SET adminEmail ='" + aEmail + "', email1 ='" + r1 + "',\
        email2 ='" + r2 + "', email3 ='" + r3 + "', email2Enabled ='" + to_string(r2e) + "',\
        email3Enabled ='" + to_string(r3e) + "' WHERE userID = '" + to_string(userID) + "'";

    mysql_query(conn, query.c_str());  // run query

    if (pass == "NULL") {  // no password change
        query = "UPDATE systemSettings SET emailEnabled ='" + to_string(enable) + "', smtpServer ='" + server + "', smtpProvider ='" + to_string(provider) + "', smtpPort ='" + to_string(port) + "',\
        smtpUser ='" + user + "' WHERE userID = '" + to_string(userID) + "'";
    }
    else {  // new password
        smtpPass = pass;
        smtpPass = base64_encode(smtpPass);
        query = "UPDATE systemSettings SET emailEnabled ='" + to_string(enable) + "', smtpServer ='" + server + "', smtpProvider ='" + to_string(provider) + "', smtpPort ='" + to_string(port) + "',\
        smtpUser ='" + user + "', smtpPass ='" + smtpPass + "' WHERE userID = '" + to_string(userID) + "'";
    }

    mysql_query(conn, query.c_str());  // run query
    mysql_disconnect(); 
}

void emails::startupEmails() {  // run at startup
    std::cout << " " << std::endl;
    std::cout << "startupEmails------------------------------" << std::endl;

    MYSQL_RES *res;
    MYSQL_ROW row;

    connectMysql();
    std::string query = "SELECT emailEnabled FROM systemSettings WHERE userID = 1";
    mysql_query(conn, query.c_str());  // run query
    res = mysql_use_result(conn);

    while ((row = mysql_fetch_row(res)) != NULL)
    {
        emailEnabled = atoi(row[0]);
    }
    mysql_free_result(res);

    // if (emailEnabled == 1)
    // {
        // connectMysql();
        query = "SELECT smtpServer, smtpPort, smtpUser, smtpPass FROM systemSettings WHERE userID = 1";
        mysql_query(conn, query.c_str());  // run query
        res = mysql_use_result(conn);

        while ((row = mysql_fetch_row(res)) != NULL)
        {
            smtpServer = row[0];
            smtpPort = atoi(row[1]);
            smtpUser = row[2];
            smtpPass = row[3];
        }
        mysql_free_result(res);

        query = "SELECT adminEmail, email1, email2, email2Enabled, email3, email3Enabled FROM users WHERE userID = 1";
        mysql_query(conn, query.c_str());  // run query
        res = mysql_use_result(conn);

        while ((row = mysql_fetch_row(res)) != NULL)
        {
            adminEmail = row[0];
            recipient1 = row[1];
            recipient2 = row[2];
            recipient2Enabled = atoi(row[3]);
            recipient3 = row[4];
            recipient3Enabled = atoi(row[5]);
        }
        mysql_free_result(res);
        mysql_disconnect(); 

        smtpPass = base64_decode(smtpPass);
    // }
    
    std::cout << "emailEnabled---------- " << emailEnabled << std::endl;
    std::cout << "smtpServer------------ " << smtpServer << std::endl;
    std::cout << "smtpPort-------------- " << smtpPort << std::endl;
    std::cout << "smtpUser-------------- " << smtpUser << std::endl;
    std::cout << "adminEmail------------ " << adminEmail << std::endl;
    std::cout << "recipient1------------ " << recipient1 << std::endl;
    std::cout << "recipient2------------ " << recipient2 << std::endl;
    std::cout << "recipient2Enabled----- " << recipient2Enabled << std::endl;
    std::cout << "recipient3------------ " << recipient3 << std::endl;
    std::cout << "recipient3Enabled----- " << recipient3Enabled << std::endl;
    std::cout << "----------------------------------------" << std::endl;
}

emails emails;
