C+첨부 파일 이 포 함 된 메 일 발송 기능 구현

1.테스트 용 주 함수
//
#include "Csmtp.h"
#pragma comment(lib, "Kernel32.lib")
int main()
{
Csmtp mail(
25,
"smtp.126.com",
"[email protected]",//
"pwd",
"[email protected]" //
);
if (!mail.CReateSocket())
{
cout << "ReateSocket failed!" << endl;
return -1;//
}
mail.setTitle("test mail");
mail.setContent("this is content.");
mail.addfile("test1.png"); //
mail.addfile("test2.png"); //
mail.SendMail(); //
return 0;
}
2.Csmtp 클래스 정의
#include <iostream>
#include <string>
#include <vector>
#include <fstream>
#include <WinSock2.h> // Windows
#pragma comment(lib, "ws2_32.lib") /* ws2_32.lib */
// POP3 ( :110) Csmtp ( :25)
using namespace std;
class Csmtp
{
int port;
string domain;
string user;
string pass;
string target;
string title; //
string content; //
HOSTENT* pHostent;
SOCKET sockClient; //
vector <string> filename; //
public:
Csmtp(
int _port, // 25
string _domain, //
string _user, //
string _pass, //
string _target) //
:port(_port),domain(_domain),user(_user),pass(_pass), target(_target){};//
bool CReateSocket();
void setTitle(string tem){title = tem;}
void setContent(string tem){content = tem;}
int SendAttachment(SOCKET &sockClient);
int SendMail();
void addfile(string str){filename.push_back(str);}
};
3.Csmtp 류 의 실현
#include "Csmtp.h"
//#include <afx.h>//
static const char base64Char[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
char* base64Encode(char const* origSigned, unsigned origLength)
{
unsigned char const* orig = (unsigned char const*)origSigned; // in case any input bytes have the MSB set
if (orig == NULL) return NULL;
unsigned const numOrig24BitValues = origLength / 3;
bool havePadding = origLength > numOrig24BitValues * 3;
bool havePadding2 = origLength == numOrig24BitValues * 3 + 2;
unsigned const numResultBytes = 4 * (numOrig24BitValues + havePadding);
char* result = new char[numResultBytes + 3]; // allow for trailing '/0'
// Map each full group of 3 input bytes into 4 output base-64 characters:
unsigned i;
for (i = 0; i < numOrig24BitValues; ++i)
{
result[4 * i + 0] = base64Char[(orig[3 * i] >> 2) & 0x3F];
result[4 * i + 1] = base64Char[(((orig[3 * i] & 0x3) << 4) | (orig[3 * i + 1] >> 4)) & 0x3F];
result[4 * i + 2] = base64Char[((orig[3 * i + 1] << 2) | (orig[3 * i + 2] >> 6)) & 0x3F];
result[4 * i + 3] = base64Char[orig[3 * i + 2] & 0x3F];
}
// Now, take padding into account. (Note: i == numOrig24BitValues)
if (havePadding)
{
result[4 * i + 0] = base64Char[(orig[3 * i] >> 2) & 0x3F];
if (havePadding2)
{
result[4 * i + 1] = base64Char[(((orig[3 * i] & 0x3) << 4) | (orig[3 * i + 1] >> 4)) & 0x3F];
result[4 * i + 2] = base64Char[(orig[3 * i + 1] << 2) & 0x3F];
}
else
{
result[4 * i + 1] = base64Char[((orig[3 * i] & 0x3) << 4) & 0x3F];
result[4 * i + 2] = '=';
}
result[4 * i + 3] = '=';
}
result[numResultBytes] = '\0';
return result;
}
int Csmtp::SendAttachment(SOCKET &sockClient) /* */
{
for (std::vector<string>::iterator iter = filename.begin();iter != filename.end(); iter++)
{
cout << "Attachment is sending・・・ " << endl;
string path=*iter;
ifstream ifs(path, ios::in | ios::binary); //' 2 , 、 '
if (false == ifs.is_open())
{
cout<<" !"<<endl;
return 1;
}
string sendstring;
sendstring = "--@boundary@\r
Content-Type: application/octet-stream; name=\"1.jpg\"\r
";
sendstring += "Content-Disposition: attachment; filename=\"1.jpg\"\r
";
sendstring += "Content-Transfer-Encoding: base64\r
\r
";
send(sockClient, sendstring.c_str(), sendstring.length(), 0);
//infile.read((char*)buffer,sizeof( ));
// get length of file:
ifs.seekg (0, ifs.end);
int length = ifs.tellg();
ifs.seekg (0, ifs.beg);
cout<<"length:"<<length<<endl;
// allocate memory:
char * buffer = new char [length];
// read data as a block:
ifs.read (buffer,length);
ifs.close();
char *pbase;
pbase = base64Encode(buffer, length);
delete[]buffer;
string str(pbase);
delete[]pbase;
str+="\r
";
int err =send(sockClient, str.c_str(), strlen(str.c_str()), 0);
if (err != strlen(str.c_str()))
{
cout << " !" << endl;
return 1;
}
}
return 0;
}
bool Csmtp::CReateSocket()
{
WSADATA wsaData;
WORD wVersionRequested = MAKEWORD(2, 1);
//WSAStarup, WSA(Windows SocKNDs Asynchronous,Windows )
int err = WSAStartup(wVersionRequested, &wsaData);
cout<<"WSAStartup(0:successful):"<<err<<endl;
char namebuf[128]; //
string ip_list;
if(0==gethostname(namebuf,128))
{
struct hostent* pHost; // IP
pHost=gethostbyname(namebuf); //pHost
for (int i=0;pHost!=NULL&&pHost->h_addr_list[i]!=NULL;i++)
{
string tem = inet_ntoa(*(struct in_addr *)pHost->h_addr_list[i]);
ip_list += tem;
ip_list += "
";
}
}
else
{
cout<<" ..."<<endl ;
}
//////////////////////////////////////////////////////////////////////////
title=namebuf;//
content=ip_list; // ip
sockClient = socket(AF_INET, SOCK_STREAM, 0); // socket
pHostent = gethostbyname(domain.c_str()); //
if (pHostent == NULL)
{
printf( " , !
" );
return false;
}
return true;
}
int Csmtp::SendMail()
{
char *ecode;
char buff[500]; //recv
int err = 0;
string message; //
SOCKADDR_IN addrServer; //
addrServer.sin_addr.S_un.S_addr = *((DWORD *)pHostent->h_addr_list[0]); // smtp ip
addrServer.sin_family = AF_INET;
addrServer.sin_port = htons(port); // 25
//int connect (SOCKET s , const struct sockaddr FAR *name , int namelen );
err = connect(sockClient, (SOCKADDR*)&addrServer, sizeof(SOCKADDR)); //
cout<<"connect:"<<err<<endl;
//telnet smtp.126.com 25
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"connect:"<<buff<<endl;
message="ehlo 126.com\r
";
send(sockClient, message.c_str(), message.length(), 0);
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"helo:"<<buff<<endl;
message="auth login \r
";
send(sockClient, message.c_str(), message.length(), 0);
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"auth login:"<<buff<<endl;
//
message=user;
ecode = base64Encode(message.c_str(), strlen(message.c_str()));
message = ecode;
message += "\r
";
delete[]ecode;
send(sockClient, message.c_str(), message.length(), 0);
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"usrname:"<<buff<<endl;
//
message=pass;
ecode = base64Encode(message.c_str(), strlen(message.c_str()));
message = ecode;
delete[]ecode;
message += "\r
";
send(sockClient, message.c_str(), message.length(), 0);
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"password:"<<buff<<endl;
message="mail from:<"+user+">\r
rcpt to:<"+target+">\r
";
send(sockClient, message.c_str(), message.length(), 0);
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"mail from: "<<buff<<endl;
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"rcpt to: "<<buff<<endl;
message="data\r
";//data
send(sockClient, message.c_str(), message.length(), 0);
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"data: "<<buff<<endl;
///-----------------------------------------DATA-------------------------------------
// Csmtp , Csmtp , Content-type BOUNDARY ,
cout<<"-------------------DATA------------------------"<<endl;
//
message="from:"+user+"\r
to:"+target+"\r
subject:"+title+"\r
";
message += "MIME-Version: 1.0\r
";
message += "Content-Type: multipart/mixed;boundary=@boundary@\r
\r
";
send(sockClient, message.c_str(), message.length(), 0);
//
message = "--@boundary@\r
Content-Type: text/plain;charset=\"gb2312\"\r
\r
"+content+"\r
\r
";
send(sockClient, message.c_str(), message.length(), 0);
//------------------------------------------------------------------------------------------------
//
SendAttachment(sockClient);
/* */
message = "--@boundary@--\r
.\r
";
send(sockClient, message.c_str(), message.length(), 0);
buff[recv(sockClient, buff, 500, 0)]='\0';
//cout<<"end_qwertyuiop:"<<buff<<endl;
message="QUIT\r
";
send(sockClient, message.c_str(), message.length(), 0);
buff[recv(sockClient, buff, 500, 0)]='\0';
cout<<"Send mail is finish:"<<buff<<endl;
return 0;
}
이해 하기 쉬 운 간략화 판 클릭 가능->여기,이곳이상 이 바로 본 고의 모든 내용 입 니 다.여러분 의 학습 에 도움 이 되 고 저 희 를 많이 응원 해 주 셨 으 면 좋 겠 습 니 다.