C++实现发送邮件和附件功能

本文实例为大家分享了C++实现发送邮件和附件的具体代码,供大家参考,具体内容如下

头文件

/*************************
*发送邮件模块头文件
*可以发送文本和附件(支持多个附件一起发送)
**************************/
#pragma once
struct sMailInfo //邮件信息
{
 char* m_pcUserName;//用户登录邮箱的名称
 char* m_pcUserPassWord;//用户登录邮箱的密码
 char* m_pcSenderName;//用户发送时显示的名称
 char* m_pcSender;//发送者的邮箱地址
 char* m_pcReceiver;//接收者的邮箱地址
 char* m_pcTitle;//邮箱标题
 char* m_pcBody;//邮件文本正文
 char* m_pcIPAddr;//服务器的IP
 char* m_pcIPName;//服务器的名称(IP与名称二选一,优先取名称)
 sMailInfo(){memset(this,0,sizeof(sMailInfo));}
};
class CSendMail
{
public:
 CSendMail(void);
 ~CSendMail(void); 

public:
 bool SendMail(sMailInfo &smailInfo);//发送邮件,需要在发送的时候初始化邮件信息
 void AddFilePath(char * pcFilePath);//添加附件的决定路径到附件列表中
 void DeleteFilePath(char* pcFilePath);//删除附件路径,如果有的话
 void DeleteAllPath(void);//删除全部附件的路径 

protected:
 void GetFileName(char* fileName,char* filePath);//从附件的路径中获取文件名称
 void Char2Base64(char* pBuff64,char* pSrcBuff,int iLen);//把char类型转换成Base64类型
 bool CReateSocket(SOCKET &sock);//建立socket连接
 bool Logon(SOCKET &sock);//登录邮箱,主要进行发邮件前的准备工作
 int GetFileData(char* FilePath);//由文件路径获取附件内容 

 bool SendHead(SOCKET &sock);//发送邮件头
 bool SendTextBody(SOCKET &sock);//发送邮件文本正文
 bool SendFileBody(SOCKET &sock);//发送邮件附件
 bool SendEnd(SOCKET &sock);//发送邮件结尾
protected:
 CList<char*,char*> m_pcFilePathList;//记录附件路径 

 char m_cSendBuff[4096];//发送缓冲区
 char m_cReceiveBuff[1024];
 char* m_pcFileBuff;//指向附件内容
 sMailInfo m_sMailInfo;
}; 

模块实现文件

/****************************
* 发送邮件模块
*可以发送文本和附件(支持多个附件一起发送)
*Date:2011-12-01
******************************/
#include "StdAfx.h"
#include "SendMail.h"
#include "winsock2.h"
#pragma comment(lib,"WSOCK32") 

CSendMail::CSendMail(void)
{
 m_pcFileBuff=NULL;
 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 memset(m_cReceiveBuff,0,sizeof(m_cReceiveBuff));
} 

CSendMail::~CSendMail(void)
{
 DeleteAllPath();
} 

void CSendMail::Char2Base64(char* pBuff64,char* pSrcBuff,int iLen)
{
 //1 1 1 1 1 1 1 1
 // 分配给pBuff64 ↑ 分配给pBuff64+1
 //   point所在的位置
 static char Base64Encode[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";//base64所映射的字符表
 int point;//每一个源字符拆分的位置,可取2,4,6;初始为2
 point=2;
 int i;
 int iIndex;//base64字符的索引
 char n=0;//上一个源字符的残留值
 for(i=0;i<iLen;i++)
 {
  if(point==2)
  {
   iIndex=((*pSrcBuff)>>point)&0x3f;//取得pSrcBuff的高point位
  }
  else if (point==4)
  {
   iIndex=((*pSrcBuff)>>point)&0xf;//取得pSrcBuff的高point位
  }
  else if(point==6)
  {
   iIndex=((*pSrcBuff)>>point)&0x3;//取得pSrcBuff的高point位
  }
  iIndex+=n;//与pSrcBuff-1的低point结合组成Base64的索引
  *pBuff64++=Base64Encode[iIndex];//由索引表得到pBuff64
  n=((*pSrcBuff)<<(6-point));//计算源字符中的残留值
  n=n&0x3f;//确保n的最高两位为0
  point+=2;//源字符的拆分位置上升2
  if(point==8)//如果拆分位置为8说明pSrcBuff有6位残留,可以组成一个完整的Base64字符,所以直接再组合一次
  {
   iIndex=(*pSrcBuff)&0x3f;//提取低6位,这就是索引了
   *pBuff64++=Base64Encode[iIndex];//
   n=0;//残留值为0
   point=2;//拆分位置设为2
  }
  pSrcBuff++; 

 }
 if(n!=0)
 {
  *pBuff64++=Base64Encode[n];
 }
 if(iLen%3==2)//如果源字符串长度不是3的倍数要用'='补全
 {
  *pBuff64='=';
 }
 else if(iLen%3==1)
 {
  *pBuff64++='=';
  *pBuff64='=';
 }
} 

void CSendMail::AddFilePath(char * pcFilePath)//添加附件路径
{
 if(pcFilePath==NULL)
 {
  return;
 }
 int i;
 char* temp;
 for(i=0;i<m_pcFilePathList.GetCount();i++)
 {
  temp=m_pcFilePathList.GetAt(m_pcFilePathList.FindIndex(i));
  if(strcmp(pcFilePath,temp)==0)//如果已经存在就不用再添加了
  {
   return;
  }
 }
 m_pcFilePathList.AddTail(pcFilePath);
} 

void CSendMail::DeleteFilePath(char* pcFilePath)//删除附件路径
{
 int i;
 char* temp;
 for(i=0;i<m_pcFilePathList.GetCount();i++)
 {
  temp=m_pcFilePathList.GetAt(m_pcFilePathList.FindIndex(i));
  if(strcmp(temp,pcFilePath)==0)//找到并删除它,如果没找到就算了
  {
   m_pcFilePathList.RemoveAt(m_pcFilePathList.FindIndex(i));
   delete[] temp;
   return;
  }
 }
} 

void CSendMail::DeleteAllPath(void)
{
 m_pcFilePathList.RemoveAll();
} 

int CSendMail::GetFileData(char* FilePath)
{
 m_pcFileBuff=NULL;
 if(FilePath==NULL)
 {
  return 0;
 }
 CFile f;
 int len; 

 USES_CONVERSION;
 if(!f.Open(A2W(FilePath),CFile::modeRead|CFile::modeNoTruncate|CFile::typeBinary))
 {
  return 0;
 }
 len=(int)f.GetLength();
 m_pcFileBuff=new char[len+1];
 memset(m_pcFileBuff,0,len+1);
 f.Read(m_pcFileBuff,len); 

 f.Close();
 return len;
} 

void CSendMail::GetFileName(char* fileName,char* filePath)
{
 if(filePath==NULL || fileName==NULL)
 {
  return;
 }
 int i;
 for(i=0;i<(int)strlen(filePath);i++)
 {
  if(filePath[strlen(filePath)-1-i]=='\\')
  {
   memcpy(fileName,&filePath[strlen(filePath)-i],i);
   return;
  }
 }
} 

bool CSendMail::CReateSocket(SOCKET &sock)
{
 WORD wVersionRequested;
 WSADATA wsaData;
 int err;
 wVersionRequested = MAKEWORD( 2, 2 );
 err = WSAStartup( wVersionRequested, &wsaData );
 if ( err != 0 )
 {
  return false;
 }
 if ( LOBYTE( wsaData.wVersion ) != 2 ||
  HIBYTE( wsaData.wVersion ) != 2 )
 {
  WSACleanup( );
  return false;
 }
 sock = socket(AF_INET,SOCK_STREAM,IPPROTO_IP);
 if (sock == INVALID_SOCKET)
 {
  return false;
 } 

 sockaddr_in servaddr;
 memset(&servaddr,0,sizeof(sockaddr_in));
 servaddr.sin_family = AF_INET;
 servaddr.sin_port = htons(25);//发邮件一般都是25端口
 if(m_sMailInfo.m_pcIPName=="")
 {
  servaddr.sin_addr.s_addr = inet_addr(m_sMailInfo.m_pcIPAddr);//直接使用IP地址
 }
 else
 {
  struct hostent *hp=gethostbyname(m_sMailInfo.m_pcIPName);//使用名称
  servaddr.sin_addr.s_addr=*(int*)(*hp->h_addr_list);
 } 

 int ret = connect(sock,(sockaddr*)&servaddr,sizeof(servaddr));//建立连接
 if (ret == SOCKET_ERROR)
 {
  return false;
 } 

 return true;
} 

bool CSendMail::Logon(SOCKET &sock)
{
 recv(sock,m_cReceiveBuff,1024,0); 

 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 sprintf_s(m_cSendBuff,"HELO []\r\n");
 send(sock,m_cSendBuff,strlen(m_cSendBuff),0);//开始会话
 recv(sock,m_cReceiveBuff,1024,0);
 if(m_cReceiveBuff[0]!='2' || m_cReceiveBuff[1]!='5' || m_cReceiveBuff[2]!='0')
 {
  return false;
 } 

 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 sprintf_s(m_cSendBuff,"AUTH LOGIN\r\n");
 send(sock,m_cSendBuff,strlen(m_cSendBuff),0);//请求登录
 recv(sock,m_cReceiveBuff,1024,0);
 if(m_cReceiveBuff[0]!='3' || m_cReceiveBuff[1]!='3' || m_cReceiveBuff[2]!='4')
 {
  return false;
 } 

 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 Char2Base64(m_cSendBuff,m_sMailInfo.m_pcUserName,strlen(m_sMailInfo.m_pcUserName));
 m_cSendBuff[strlen(m_cSendBuff)]='\r';
 m_cSendBuff[strlen(m_cSendBuff)]='\n';
 send(sock,m_cSendBuff,strlen(m_cSendBuff),0);//发送用户名
 recv(sock,m_cReceiveBuff,1024,0);
 if(m_cReceiveBuff[0]!='3' || m_cReceiveBuff[1]!='3' || m_cReceiveBuff[2]!='4')
 {
  return false;
 } 

 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 Char2Base64(m_cSendBuff,m_sMailInfo.m_pcUserPassWord,strlen(m_sMailInfo.m_pcUserPassWord));
 m_cSendBuff[strlen(m_cSendBuff)]='\r';
 m_cSendBuff[strlen(m_cSendBuff)]='\n';
 send(sock,m_cSendBuff,strlen(m_cSendBuff),0);//发送用户密码
 recv(sock,m_cReceiveBuff,1024,0);
 if(m_cReceiveBuff[0]!='2' || m_cReceiveBuff[1]!='3' || m_cReceiveBuff[2]!='5')
 {
  return false;
 }
 return true;//登录成功
} 

bool CSendMail::SendHead(SOCKET &sock)
{
 int rt;
 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 sprintf_s(m_cSendBuff,"MAIL FROM:<%s>\r\n",m_sMailInfo.m_pcSender);
 rt=send(sock,m_cSendBuff,strlen(m_cSendBuff),0); 

 if(rt!=strlen(m_cSendBuff))
 {
  return false;
 }
 recv(sock,m_cReceiveBuff,1024,0); 

 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 sprintf_s(m_cSendBuff,"RCPT TO:<%s>\r\n",m_sMailInfo.m_pcReceiver);
 rt=send(sock,m_cSendBuff,strlen(m_cSendBuff),0);
 if(rt!=strlen(m_cSendBuff))
 {
  return false;
 }
 recv(sock,m_cReceiveBuff,1024,0); 

 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 memcpy(m_cSendBuff,"DATA\r\n",strlen("DATA\r\n"));
 rt=send(sock,m_cSendBuff,strlen(m_cSendBuff),0);
 if(rt!=strlen(m_cSendBuff))
 {
  return false;
 }
 recv(sock,m_cReceiveBuff,1024,0); 

 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 sprintf_s(m_cSendBuff,"From:\"%s\"<%s>\r\n",m_sMailInfo.m_pcSenderName,m_sMailInfo.m_pcSender);
 sprintf_s(&m_cSendBuff[strlen(m_cSendBuff)],150,"To:\"INVT.COM.CN\"<%s>\r\n",m_sMailInfo.m_pcReceiver);
 sprintf_s(&m_cSendBuff[strlen(m_cSendBuff)],150,"Subject:%s\r\nMime-Version: 1.0\r\nContent-Type: multipart/mixed; boundary=\"INVT\"\r\n\r\n",m_sMailInfo.m_pcTitle);
 rt=send(sock,m_cSendBuff,strlen(m_cSendBuff),0);
 if(rt!=strlen(m_cSendBuff))
 {
  return false;
 } 

 return true;
} 

bool CSendMail::SendTextBody(SOCKET &sock)
{
 int rt;
 memset(m_cSendBuff,0,sizeof(m_cSendBuff));
 sprintf_s(m_cSendBuff,"--INVT\r\nContent-Type: text/plain;\r\n charset=\"gb2312\"\r\n\r\n%s\r\n\r\n",m_sMailInfo.m_pcBody);
 rt=send(sock,m_cSendBuff,strlen(m_cSendBuff),0);
 if(rt!=strlen(m_cSendBuff))
 {
  return false;
 }
 else
 {
  return true;
 }
} 

bool CSendMail::SendFileBody(SOCKET &sock)
{
 int i;
 char* filePath;
 int rt;
 int len;
 int pt=0;
 char fileName[128];
 for(i=0;i<m_pcFilePathList.GetCount();i++)
 {
  pt=0;
  memset(fileName,0,128);
  filePath=m_pcFilePathList.GetAt(m_pcFilePathList.FindIndex(i));
  len=GetFileData(filePath);
  GetFileName(fileName,filePath); 

  sprintf_s(m_cSendBuff,"--INVT\r\nContent-Type: application/octet-stream;\r\n name=\"%s\"\r\nContent-Transfer-Encoding: base64\r\nContent-Disposition: attachment;\r\n filename=\"%s\"\r\n\r\n",fileName,fileName);
  send(sock,m_cSendBuff,strlen(m_cSendBuff),0);
  while (pt<len)
  {
   memset(m_cSendBuff,0,sizeof(m_cSendBuff));
   Char2Base64(m_cSendBuff,&m_pcFileBuff[pt],min(len-pt,3000));
   m_cSendBuff[strlen(m_cSendBuff)]='\r';
   m_cSendBuff[strlen(m_cSendBuff)]='\n';
   rt=send(sock,m_cSendBuff,strlen(m_cSendBuff),0);
   pt+=min(len-pt,3000);
   if(rt!=strlen(m_cSendBuff))
   {
    return false;
   }
  }
  if(len!=0)
  {
   delete [] m_pcFileBuff;
  }
 } 

 return true;
} 

bool CSendMail::SendEnd(SOCKET &sock)
{
 sprintf_s(m_cSendBuff,"--INVT--\r\n.\r\n");
 send(sock,m_cSendBuff,strlen(m_cSendBuff),0); 

 sprintf_s(m_cSendBuff,"QUIT\r\n");
 send(sock,m_cSendBuff,strlen(m_cSendBuff),0);
 closesocket(sock);
 WSACleanup();
 return true;
} 

bool CSendMail::SendMail(sMailInfo &smailInfo)
{
 memcpy(&m_sMailInfo,&smailInfo,sizeof(smailInfo));
 if(m_sMailInfo.m_pcBody==NULL
  || m_sMailInfo.m_pcIPAddr==NULL
  || m_sMailInfo.m_pcIPName==NULL
  || m_sMailInfo.m_pcReceiver==NULL
  || m_sMailInfo.m_pcSender==NULL
  || m_sMailInfo.m_pcSenderName==NULL
  || m_sMailInfo.m_pcTitle==NULL
  || m_sMailInfo.m_pcUserName==NULL
  || m_sMailInfo.m_pcUserPassWord==NULL)
 {
  return false;
 }
 SOCKET sock;
 if(!CReateSocket(sock))//建立连接
 {
  return false;
 } 

 if(!Logon(sock))//登录邮箱
 {
  return false;
 } 

 if(!SendHead(sock))//发送邮件头
 {
  return false;
 } 

 if(!SendTextBody(sock))//发送邮件文本部分
 {
  return false;
 } 

 if(!SendFileBody(sock))//发送附件
 {
  return false;
 } 

 if(!SendEnd(sock))//结束邮件,并关闭sock
 {
  return false;
 } 

 return true;
} 

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • C++实现邮件群发的方法

    本文实例讲述了C++实现邮件群发的方法.分享给大家供大家参考.具体如下: 关于生成随机QQ邮箱不精确的问题,在之后版本打算另写一个采集器插件进行帐号采集,所以,这个软件只用来进行内容发送,邮箱进行随机生成 如果你已经有采集来的QQ号,请复制到SendList.txt 替换内容即可 可以直接复制HTML代码到邮件内容,保存即可.目前邮件内容最大设置为10000字节,如果有增大的必要,欢迎提交留言. 这是我学习后VC编程中涉及到多线程,socket,及一些WINDOWS API的宗合应用 使用说明:

  • C++发送邮件实现代码

    本文实例为大家分享了C++发送邮件的具体代码,供大家参考,具体内容如下 首先,别忘了要设置发送邮箱的smtp,例如,假设你需要用网易邮箱,你需要去你的163邮箱设置开启smtp(有的邮箱还需要设置授权码).接着就可以用以下代码发送邮件了: // SendMail.h #ifndef _SEND_MAIL_H_ #define _SEND_MAIL_H_ #include <windows.h> #include <stdio.h> #include <WinSock.h>

  • C++发邮件简单实例详解

    C++发邮件用的是阻塞式socket模型,发送完数据后需要接收返回值,才能接着发送. 本程序不发送邮件附件,发附件的实例:C++实现含附件的邮件发送功能 #include <iostream> #include <string> #include <WinSock2.h> //适用平台 Windows using namespace std; #pragma comment(lib, "ws2_32.lib") /*链接ws2_32.lib动态链接库

  • C++实现含附件的邮件发送功能

    C++实现邮件发送程序在vs2013测试通过,一共3个文件,发邮件的程序封装为Csmtp 类. 1.测试用的主函数 // #include "Csmtp.h" #pragma comment(lib, "Kernel32.lib") int main() { Csmtp mail( 25, "smtp.126.com", "username@126.com",// 来源邮箱 "pwd", "use

  • C++实现发送邮件和附件功能

    本文实例为大家分享了C++实现发送邮件和附件的具体代码,供大家参考,具体内容如下 头文件 /************************* *发送邮件模块头文件 *可以发送文本和附件(支持多个附件一起发送) **************************/ #pragma once struct sMailInfo //邮件信息 { char* m_pcUserName;//用户登录邮箱的名称 char* m_pcUserPassWord;//用户登录邮箱的密码 char* m_pcS

  • python实现发送邮件及附件功能

    今天给大伙说说python发送邮件,官方的多余的话自己去百度好了,还有一大堆文档说实话不到万不得已的时候一般人都不会去看,回归主题: 本人是mac如果没有按照依赖模块的请按照下面的截图安装 导入模块如果没有错误,表示已经安装成功. Python发送一个未知MIME类型的文件附件其基本思路如下: 1. 构造MIMEMultipart对象做为根容器 2. 构造MIMEText对象做为邮件显示内容并附加到根容器 3. 构造MIMEBase对象做为文件附件内容并附加到根容器 a. 读入文件内容并格式化

  • thinkphp实现发送邮件密码找回功能实例

    本文实例讲述了thinkphp实现发送邮件密码找回功能的方法.分享给大家供大家参考.具体实现方法如下: 首先下载mail.class.php类文件,配置文件中定义下列参数: 复制代码 代码如下: 'MAIL_ADDRESS' => 'ivzhu@qq.com', // 邮箱地址  'MAIL_SMTP' => 'smtp.qq.com', // 邮箱SMTP服务器  'MAIL_LOGINNAME' => 'mail@qq.com', // 邮箱登录帐号  'MAIL_PASSWORD'

  • javascript实现添加附件功能的方法

    在邮件中我们经常用到添加附件,现在简单的应用下: 效果图: 实现原理: 采用table标签的,主要思想:采用table标签方式 1.点击文字之后,就自动创建(原先是自己/创建,现在拿到table对象之后,可以insertRow() insertCell())创建行和列 2.删除的时候通过父节点来移除 核心代码: function creatMail(){ var tab=document.getElementById("tabid"); var tr=tab.insertRow();/

  • Django实现发送邮件找回密码功能

    在各大网站上,一定都遇到过找回密码的问题,通常采用的方式是通过发送带有验证码的邮件进行身份验证,本文将介绍通过Django实现邮件找回密码功能. 找回密码流程 功能流程: 1.首先在用户登录界面,添加"忘记密码"链接 2.生成随机验证码,发送邮件到用户信息中填写邮箱 3.在重置密码页面,验证填写验证码是否需匹配 4.重置密码成功,重新进入到登录页面 技术点: 1.发送邮件使用Django内置的django.core.mail实现 2.重置密码页面验证验证码填写是否匹配,提前将发送的验证

  • python3通过qq邮箱发送邮件以及附件

    本文实例为大家分享了python3通过qq邮箱发送邮件以及附件的具体代码,供大家参考,具体内容如下 开启qq邮箱的smtp服务 代码: import smtplib from email.mime.text import MIMEText from email.mime.multipart import MIMEMultipart def Mailer(to_list,th1=None,Subject=None,unipath=None): mail_host = 'smtp.qq.com' #

  • python smtplib模块实现发送邮件带附件sendmail

    本文实例为大家分享了python smtplib实现发送邮件的具体代码,供大家参考,具体内容如下 #!/usr/bin/env python # -*- coding: UTF-8 -*- from email.mime.multipart import MIMEMultipart from email.mime.base import MIMEBase from email.mime.text import MIMEText from email.utils import COMMASPACE

  • 使用jquery Ajax实现上传附件功能

    用过jquery的Ajax的人肯定都知道,Ajax的默认编码方式是"application/x-www-form-urlencoded",此编码方式只能编码文本类型的数据,因此Ajax发送请求的时候,会把data序列化成 一个个String类型的键值对,此种传输数据的方式能够满足大部分应用场景,然而当传输的数据里有附件的时候,此序列化机制便是我们的绊脚石.Ajax本身的序列化机制的硬伤归其原因在于在html4的时代,没有FileReader接口,在页面里无法读取File(Blob)文件

  • jquery实现动态添加附件功能

    本文实例为大家分享了jquery实现动态添加附件的具体代码,供大家参考,具体内容如下 创建HTML页面 项目中实现的原代码,无删减直接贴上.具体请参考"添加附件"按钮相关操作. 注意引入:cardRansomManage.js,ajaxfileupload.js. <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DT

  • python实现微信发送邮件关闭电脑功能

    Python 通过微信邮件实现电脑关机,供大家参考,具体内容如下 通过手机微信发送QQ邮件给sina邮箱,然后利用python的pop3定时检查sina邮箱的邮件主题以及邮件来源,并在电脑执行相应的命令行实现关机. Email_test[V1.0] import poplib import os import time from email.parser import Parser from email.header import decode_header from email.utils i

随机推荐