SMTP.CPP
上传用户:sanlisteel
上传日期:2008-06-19
资源大小:98k
文件大小:6k
- // SMTP.cpp: implementation of the CSMTP class.
- //
- //////////////////////////////////////////////////////////////////////
- #include "stdafx.h"
- #include "SMTP.h"
- #ifdef _DEBUG
- #undef THIS_FILE
- static char THIS_FILE[]=__FILE__;
- #define new DEBUG_NEW
- #endif
- CSMTP::response_code CSMTP::response_table[] =
- {
- // GENERIC_SUCCESS
- { 250, _T( "SMTP服务器错误" ) },
- // CONNECT_SUCCESS
- { 220, _T( "SMTP服务器不可用" ) },
- // DATA_SUCCESS
- { 354, _T( "SMTP服务器不能接收数据" ) },
- // QUIT_SUCCESS
- { 221, _T( "SMTP没有中止会话" ) }
- };
- //////////////////////////////////////////////////////////////////////
- // Construction/Destruction
- //////////////////////////////////////////////////////////////////////
- CSMTP::CSMTP( LPCTSTR szSMTPServerName, UINT nPort )
- {
- ASSERT( szSMTPServerName != NULL );
- AfxSocketInit(); //初始化Windows Sockets类的使用
- m_sSMTPServerHostName = szSMTPServerName;
- m_nPort = nPort;
- m_bConnected = FALSE;
- m_sError = _T( "OK" );
- response_buf = NULL;
- }
- CSMTP::~CSMTP()
- {
- Disconnect(); //断开连接
- }
- CString CSMTP::GetServerHostName()
- {
- return m_sSMTPServerHostName;
- }
- //建立到服务器的连接
- BOOL CSMTP::Connect()
- {
- CString sHello;
- TCHAR local_host[ 80 ];
- if( m_bConnected )
- return TRUE;
-
- try
- {
- response_buf = new TCHAR[ RESPONSE_BUFFER_SIZE ];
- if( response_buf == NULL )
- {
- m_sError = _T( "内存不足!" );
- return FALSE;
- }
- }
- catch( CException *e ) //使用基类进行捕捉
- {
- response_buf = NULL;
- m_sError = _T( "内存不足!" );
- delete e;
- return FALSE;
- }
- if( !m_wsSMTPServer.Create() )
- {
- m_sError = _T( "无法创建套接字!" );
- delete response_buf;
- response_buf = NULL;
- return FALSE;
- }
- if( !m_wsSMTPServer.Connect( GetServerHostName(), GetPort() ) )
- {
- m_sError = _T( "无法连接到服务器" );
- m_wsSMTPServer.Close();
- delete response_buf;
- response_buf = NULL;
- return FALSE;
- }
- if( !get_response( CONNECT_SUCCESS ) )
- {
- m_sError = _T( "服务器没有响应" );
- m_wsSMTPServer.Close();
- delete response_buf;
- response_buf = NULL;
- return FALSE;
- }
- gethostname( local_host, 80 ); //得到本地机器标准主机名
- sHello.Format( _T( "HELO %srn" ), local_host );
- m_wsSMTPServer.Send( (LPCTSTR)sHello, sHello.GetLength() ); //建立连接后发送数据
- if( !get_response( GENERIC_SUCCESS ) )
- {
- m_wsSMTPServer.Close();
- delete response_buf;
- response_buf = NULL;
- return FALSE;
- }
- m_bConnected = TRUE;
- return TRUE;
- }
- //断开连接
- BOOL CSMTP::Disconnect()
- {
- BOOL ret;
- if( !m_bConnected )
- return TRUE;
- CString sQuit = _T( "QUITrn" );
- m_wsSMTPServer.Send( (LPCTSTR)sQuit, sQuit.GetLength() );
- ret = get_response( QUIT_SUCCESS );
- m_wsSMTPServer.Close();
- if( response_buf != NULL )
- {
- delete[] response_buf;
- response_buf = NULL;
- }
- m_bConnected = FALSE;
- return ret;
- }
- //取得SMTP服务器端口号
- UINT CSMTP::GetPort()
- {
- return m_nPort;
- }
- //取得错误信息
- CString CSMTP::GetLastError()
- {
- return m_sError;
- }
- //发邮件到服务器
- BOOL CSMTP::SendMessage(CMailMessage * msg)
- {
- ASSERT( msg != NULL );
- if( !m_bConnected )
- {
- m_sError = _T( "必须首先创建连接!" );
- return FALSE;
- }
- if( FormatMailMessage( msg ) == FALSE )
- {
- return FALSE;
- }
- if( transmit_message( msg ) == FALSE )
- {
- return FALSE;
- }
- return TRUE;
- }
- //格式化邮件信息
- BOOL CSMTP::FormatMailMessage( CMailMessage* msg )
- {
- ASSERT( msg != NULL );
- if( msg->GetNumRecipients() == 0 )
- {
- m_sError = _T( "No Recipients" );
- return FALSE;
- }
- msg->FormatMessage();
- return TRUE;
- }
- //配置服务器
- void CSMTP::SetServerProperties( LPCTSTR szSMTPServerName, UINT nPort)
- {
- ASSERT( szSMTPServerName != NULL );
- if( szSMTPServerName == NULL )
- return;
- m_sSMTPServerHostName = szSMTPServerName;
- m_nPort = nPort;
- }
- //获得邮件体得到发送内容
- CString CSMTP::cook_body(CMailMessage * msg)
- {
- ASSERT( msg != NULL );
- CString sTemp;
- CString sCooked = _T( "" );
- LPTSTR szBad = _T( "rn.rn" );
- LPTSTR szGood = _T( "rn..rn" );
- int nPos;
- int nStart = 0;
- int nBadLength = strlen( szBad );
- sTemp = msg->m_sBody;
- if( sTemp.Left( 3 ) == _T( ".rn" ) )
- sTemp = _T( "." ) + sTemp;
- while( (nPos = sTemp.Find( szBad )) > -1 )
- {
- sCooked = sTemp.Mid( nStart, nPos );
- sCooked += szGood;
- sTemp = sCooked + sTemp.Right( sTemp.GetLength() - (nPos + nBadLength) );
- }
- return sTemp;
- }
- //发送邮件
- BOOL CSMTP::transmit_message(CMailMessage * msg)
- {
- CString sFrom;
- CString sTo;
- CString sTemp;
- CString sEmail;
- CString sSubject;
- ASSERT( msg != NULL );
- if( !m_bConnected )
- {
- m_sError = _T( "必须首先创建连接!" );
- return FALSE;
- }
- sFrom.Format( _T( "MAIL From: <%s>rn" ), (LPCTSTR)msg->m_sFrom );
- m_wsSMTPServer.Send( (LPCTSTR)sFrom, sFrom.GetLength() );
- if( !get_response( GENERIC_SUCCESS ) )
- return FALSE;
-
- for( int i = 0; i < msg->GetNumRecipients(); i++ )
- {
- msg->GetRecipient( sEmail, sTemp, i );
- sTo.Format( _T( "RCPT TO: <%s>rn" ), (LPCTSTR)sEmail );
- m_wsSMTPServer.Send( (LPCTSTR)sTo, sTo.GetLength() );
- get_response( GENERIC_SUCCESS );
- }
- sTemp = _T( "DATArn" );
- m_wsSMTPServer.Send( (LPCTSTR)sTemp, sTemp.GetLength() );
- if( !get_response( DATA_SUCCESS ) )
- {
- return FALSE;
- }
- sSubject.Format( _T( "SUBJECT: <%s>rn" ), (LPCTSTR)msg->m_sSubject );
- m_wsSMTPServer.Send( (LPCTSTR)sSubject, sSubject.GetLength() );
- // m_wsSMTPServer.Send( (LPCTSTR)msg->m_sHeader, msg->m_sHeader.GetLength() );
- sTemp = cook_body( msg );
- m_wsSMTPServer.Send( (LPCTSTR)sTemp, sTemp.GetLength() );
- sTemp = _T( "rn.rn" );
- m_wsSMTPServer.Send( (LPCTSTR)sTemp, sTemp.GetLength() );
- if( !get_response( GENERIC_SUCCESS ) )
- {
- return FALSE;
- }
- return TRUE;
- }
- //得到服务器响应
- BOOL CSMTP::get_response( UINT response_expected )
- {
- ASSERT( response_expected >= GENERIC_SUCCESS );
- ASSERT( response_expected < LAST_RESPONSE );
- CString sResponse;
- UINT response;
- response_code* pResp;
- if( m_wsSMTPServer.Receive( response_buf, RESPONSE_BUFFER_SIZE ) == SOCKET_ERROR )
- {
- m_sError = _T( "套接字错误!" );
- return FALSE;
- }
- sResponse = response_buf;
- sscanf( (LPCTSTR)sResponse.Left( 3 ), _T( "%d" ), &response );
- pResp = &response_table[ response_expected ];
- if( response != pResp->nResponse )
- {
- m_sError.Format( _T( "%d:%s" ), response, (LPCTSTR)pResp->sMessage );
- return FALSE;
- }
- return TRUE;
- }