芯机智

 找回密码
 立即注册

扫一扫,访问微社区

搜索
热搜: 活动 交友 discuz
查看: 3020|回复: 12

在linux下c语言之curl发送邮件

[复制链接]

534

主题

624

帖子

6282

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
6282
发表于 2013-3-15 13:42:55 | 显示全部楼层 |阅读模式
[mw_shl_code=c,true]#include "CSendMail.h"

int main()
{
  CSendMail C163sendMail;
  //C163sendMail.AddRecipient("393731869@qq.com");

  /*
  CSendMail C163sendMail(  //create sendmail object with paremeter;
      "missazuozhu",//const std::string & strUser,
      "898781869",//const std::string & strPsw,
      "smtp.163.com",//const std::string & strSmtpServer,
      25,//  int iPort,
      "missazuozhu@163.com"//const std::string & strMailFrom
      );

  for(int i=0; i<10; i++)
  {
    sleep(1);
    C163sendMail.SendMail("魔灵军团", "魔灵军团:www.dnsnat.com 欢迎自由程序员交流");
  }*/

  C163sendMail.SendMail(  //create sendmail object with paremeter;
      "demonelf1", //const std::string & strUser,
      "898781869",   //const std::string & strPsw,
      "smtp.163.com",//  const std::string & strSmtpServer,
      25,//  int iPort,
      "393731869@qq.com",  //const std::string & strMailTo,
      "demonelf1@163.com",//  const std::string & strMailFrom,
      "www.dnsnat.com",  //const std::string & strSubject,
      "魔灵军团: 自由程序员"  //const std::string & strMailBody
      );
  return 0;
}[/mw_shl_code]

[mw_shl_code=cpp,true]/*

* File:   CSendMail.cpp

* Author: root

*

* Created on January 16, 2012, 6:14 PM

*/



#include "CSendMail.h"



CSendMail::CSendMail()

{

    m_strUser = "";

    m_strPsw = "";

    m_strSmtpServer = "";

    m_iPort = -1;

    m_RecipientList.clear();

    m_strMailFrom = "";

    m_MailContent.clear();

    m_iMailContentPos = 0;

}



CSendMail::CSendMail(  //create sendmail object with paremeter;

                const std::string & strUser,

                const std::string & strPsw,

                const std::string & strSmtpServer,

                int iPort,

                const std::string & strMailFrom

            )

{

    m_strUser = strUser;

    m_strPsw = strPsw;

    m_strSmtpServer = strSmtpServer;

    m_iPort = iPort;

    m_RecipientList.clear();

    m_strMailFrom = strMailFrom;

    m_MailContent.clear();

    m_iMailContentPos = 0;

}



CSendMail::CSendMail(const CSendMail& orig)

{

}



CSendMail::~CSendMail()

{

}



size_t CSendMail::read_callback(void* ptr, size_t size, size_t nmemb, void* userp)

{

    CSendMail * pSm = (CSendMail *)userp;



    if(size*nmemb < 1)

        return 0;

    if(pSm->m_iMailContentPos < pSm->m_MailContent.size())

    {

        size_t len;

        len = pSm->m_MailContent[pSm->m_iMailContentPos].length();



        memcpy(ptr, pSm->m_MailContent[pSm->m_iMailContentPos].c_str(), pSm->m_MailContent[pSm->m_iMailContentPos].length());

        pSm->m_iMailContentPos++; /* advance pointer */

        return len;

    }

    return 0;

}



struct timeval CSendMail::tvnow()

{

  /*

  ** time() returns the value of time in seconds since the Epoch.

  */

    struct timeval now;

    now.tv_sec = (long)time(NULL);

    now.tv_usec = 0;

    return now;

}



long CSendMail::tvdiff(timeval newer, timeval older)

{

    return (newer.tv_sec-older.tv_sec)*1000+

        (newer.tv_usec-older.tv_usec)/1000;

}



bool CSendMail::ConstructHead(const std::string & strSubject, const std::string & strContent)

{

    m_MailContent.push_back("MIME-Versioin: 1.0\n");

    std::string strTemp = "To: ";

    for(std::list<std::string >::iterator it = m_RecipientList.begin(); it != m_RecipientList.end();)

    {

        strTemp += *it;

        it++;

        if(it != m_RecipientList.end())

                strTemp += ",";

    }

    strTemp += "\n";

    m_MailContent.push_back(strTemp);

    if(strSubject != "")

    {

        strTemp = "Subject: ";

        strTemp += strSubject;

        strTemp += "\n";

        m_MailContent.push_back(strTemp);

    }

    m_MailContent.push_back("Content-Transfer-Encoding: 8bit\n");

    m_MailContent.push_back("Content-Type: text/html; \n Charset=\"UTF-8\"\n\n");

    if(strContent != "")

    {

        m_MailContent.push_back(strContent);

    }

   

    return true;

}



bool CSendMail::SendMail(const std::string& strSubject, const std::string& strMailBody)

{

    m_MailContent.clear();

    m_iMailContentPos = 0;

    ConstructHead(strSubject, strMailBody);

    bool bRet = true;

    CURL *curl;

    CURLM *mcurl;

    int still_running = 1;

    struct timeval mp_start;

    char mp_timedout = 0;

    struct curl_slist* rcpt_list = NULL;



    curl_global_init(CURL_GLOBAL_DEFAULT);



    curl = curl_easy_init();

    if (!curl)

    {

        printf("Init curl failed!\n");

        return false;

    }



    mcurl = curl_multi_init();

    if (!mcurl)

    {

        printf("Init mcurl failed!\n");

        return false;

    }

    for(std::list<std::string >::iterator it = m_RecipientList.begin(); it != m_RecipientList.end();it++)

    {

        rcpt_list = curl_slist_append(rcpt_list, it->c_str());

    }

   

    if(m_strSmtpServer == "" || m_iPort <= 0)

    {

        printf("smtp server couldn't be empty, or port must be large than 0!\n");

        

        curl_slist_free_all(rcpt_list);

        curl_multi_cleanup(mcurl);

        curl_easy_cleanup(curl);

        curl_global_cleanup();

        return false;

    }

    std::string strUrl = "smtp://" + m_strSmtpServer;

    strUrl += ":";

    char cPort[10];

    memset(cPort, 0, 10);

    sprintf(cPort, "%d", m_iPort);

    strUrl += cPort;

    curl_easy_setopt(curl, CURLOPT_URL, strUrl.c_str());

   

    if(m_strUser != "")

    {

        curl_easy_setopt(curl, CURLOPT_USERNAME, m_strUser.c_str());

    }

    if(m_strPsw != "")

    {

        curl_easy_setopt(curl, CURLOPT_PASSWORD, m_strPsw.c_str());

    }

   

    curl_easy_setopt(curl, CURLOPT_READFUNCTION, &CSendMail::read_callback);

   

    if(m_strMailFrom == "")

    {

        printf("Mail from address couldn't be empty!\n");

        

        curl_slist_free_all(rcpt_list);

        curl_multi_cleanup(mcurl);

        curl_easy_cleanup(curl);

        curl_global_cleanup();

        return false;

    }

    curl_easy_setopt(curl, CURLOPT_MAIL_FROM, m_strMailFrom.c_str());

    curl_easy_setopt(curl, CURLOPT_MAIL_RCPT, rcpt_list);

    curl_easy_setopt(curl, CURLOPT_USE_SSL, (long) CURLUSESSL_ALL);

    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0L);

    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 0L);

    curl_easy_setopt(curl, CURLOPT_READDATA, this);

    curl_easy_setopt(curl, CURLOPT_VERBOSE, 1L);

    curl_easy_setopt(curl, CURLOPT_SSLVERSION, 0L);

    curl_easy_setopt(curl, CURLOPT_SSL_SESSIONID_CACHE, 0L);

    curl_multi_add_handle(mcurl, curl);



    mp_timedout = 0;

    mp_start = tvnow();



    /* we start some action by calling perform right away */

    curl_multi_perform(mcurl, &still_running);



    while (still_running) {

        struct timeval timeout;

        int rc; /* select() return code */



        fd_set fdread;

        fd_set fdwrite;

        fd_set fdexcep;

        int maxfd = -1;



        long curl_timeo = -1;



        FD_ZERO(&fdread);

        FD_ZERO(&fdwrite);

        FD_ZERO(&fdexcep);



        /* set a suitable timeout to play around with */

        timeout.tv_sec = 1;

        timeout.tv_usec = 0;



        curl_multi_timeout(mcurl, &curl_timeo);

        if (curl_timeo >= 0) {

            timeout.tv_sec = curl_timeo / 1000;

            if (timeout.tv_sec > 1)

                timeout.tv_sec = 1;

            else

                timeout.tv_usec = (curl_timeo % 1000) * 1000;

        }



        /* get file descriptors from the transfers */

        curl_multi_fdset(mcurl, &fdread, &fdwrite, &fdexcep, &maxfd);



        /* In a real-world program you OF COURSE check the return code of the

           function calls.  On success, the value of maxfd is guaranteed to be

           greater or equal than -1.  We call select(maxfd + 1, ...), specially in

           case of (maxfd == -1), we call select(0, ...), which is basically equal

           to sleep. */



        rc = select(maxfd + 1, &fdread, &fdwrite, &fdexcep, &timeout);



        if (tvdiff(tvnow(), mp_start) > MULTI_PERFORM_HANG_TIMEOUT) {

            fprintf(stderr, "ABORTING TEST, since it seems "

                    "that it would have run forever.\n");

            bRet = false;

            break;

        }



        switch (rc) {

            case -1:

                /* select error */

                printf("select error\n");

                bRet = false;

                break;

            case 0: /* timeout */

                printf("time out, retry again!\n");

                curl_multi_perform(mcurl, &still_running);

                break;

            default: /* action */

                curl_multi_perform(mcurl, &still_running);

                break;

        }

    }



    curl_multi_remove_handle(mcurl, curl);

    curl_slist_free_all(rcpt_list);

    curl_multi_cleanup(mcurl);

    curl_easy_cleanup(curl);

    curl_global_cleanup();

    return bRet;

}



bool CSendMail::SendMail(const std::string & strSubject, const char* pMailBody, int len)

{

    std::string strMailContent;

    strMailContent.append(pMailBody, len);

   

    return SendMail(strSubject, strMailContent);

}



bool CSendMail::SendMail(const std::string& strUser, const std::string& strPsw, const std::string& strSmtpServer, int iPort, std::list<std::string>& recipientList, const std::string& strMailFrom, const std::string& strSubject, const std::string& strMailBody)

{

    m_strUser = strUser;

    m_strPsw = strPsw;

    m_strSmtpServer = strSmtpServer;

    m_iPort = iPort;

    std::copy(recipientList.begin(), recipientList.end(), m_RecipientList.begin());

    m_strMailFrom = strMailFrom;

   

    return SendMail(strSubject, strMailBody);

   

}



bool CSendMail::SendMail(const std::string& strUser, const std::string& strPsw, const std::string& strSmtpServer, int iPort, std::list<std::string>& recipientList, const std::string& strMailFrom, const std::string& strSubject, const char* pMailBody, int len)

{

    std::string strMailContent;

    strMailContent.append(pMailBody, len);

    return SendMail(strUser, strPsw, strSmtpServer, iPort, recipientList, strMailFrom, strSubject, strMailContent);

}



bool CSendMail::SendMail(const std::string& strUser, const std::string& strPsw, const std::string& strSmtpServer, int iPort, const std::string& strMailTo, const std::string& strMailFrom, const std::string& strSubject, const std::string& strMailBody)

{

    //std::list<std::string> recipientList;

   ClearRecipient();

    m_RecipientList.push_back(strMailTo);

   

    return SendMail(strUser, strPsw, strSmtpServer, iPort, m_RecipientList, strMailFrom, strSubject, strMailBody);

}



bool CSendMail::SendMail(const std::string& strUser, const std::string& strPsw, const std::string& strSmtpServer, int iPort, const std::string& strMailTo, const std::string& strMailFrom, const std::string& strSubject, const char* pMailBody, int len)

{

    std::string strMailContent;

    strMailContent.append(pMailBody, len);

    return SendMail(strUser, strPsw, strSmtpServer, iPort, strMailTo, strMailFrom, strSubject, strMailContent);



}[/mw_shl_code]

[mw_shl_code=c,true]main : CSendMail.o
  g++ main.cpp CSendMail.o -o main -lcurl

CSendMail.o:
  g++ -c CSendMail.cpp

clean:
  rm main CSendMail.o[/mw_shl_code]
在终极的分析中,一切知识都是历史;在抽象的意义下,一切科学都是数学;在理性的基础上,所有的判断都是统计。——C.R. Rao
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|芯机智 ( 京ICP备18048803号 )

GMT+8, 2019-10-15 07:06 , Processed in 0.156241 second(s), 25 queries .

Powered by Discuz! X3.4

© 2001-2017 Comsenz Inc.

快速回复 返回顶部 返回列表