php通過socket程式設計,以SMTP將郵件傳送到指定的QQ郵箱裡面。
在剛開始先配置好php.ini檔案:
(1)我是在window 7 下面進行配置的。
(2)將擴充套件extension=php_openssl.dll,extension=php_sockets.dll開啟
(3)設定allow_url_fopen = On,SMTP = localhost,smtp_port = 25,
當然sendmail_from,sendmail_path可以不用設定。但在Unix下sendmail_path需要設定
接下來用qq郵箱測試時需要設定:
(1)開啟qq郵箱設定。
(2)然後在賬戶中將pop3/smtp勾選,儲存設定。當然這裡注意自己的郵箱和測試郵箱都要開啟。
這裡簡單介紹一下HTTP狀態含義一邊測試使用,這是我測試瀏覽器顯示的內容:
220 smtp.qq.com Esmtp QQ Mail Server
250-smtp.qq.com
250-PIPELINING
250-SIZE 52428800
250-STARTTLS
250-AUTH LOGIN PLAIN
250-AUTH=LOGIN SMTP使用者驗證
250-MAILCOMPRESS
250 8BITMIME
334 VXNlcm5hbWU6 輸入使用BASE64編碼的使用者名稱
334 UGFzc3dvcmQ6 輸入使用BASE64編碼的密碼
235 Authentication successful 驗證通過
250 Ok
接受者郵件地址
250 Ok 告訴伺服器我要開始傳送郵件資料了
354 End data with.
250 Ok: queued as
郵件傳送成功
下面便是傳送郵件的一個SMTP類,經過本人修改,沒問題了,class.mail.php:
<?php define('SMTP_STATUS_NOT_CONNECTED', 1, TRUE); define('SMTP_STATUS_CONNECTED', 2, TRUE); /** * @desc SMTP 郵件伺服器 * @param 伺服器引數和郵件資訊 */ class p8_smtp { var $connection; var $recipients; var $headers; var $timeout; var $errors; var $status; var $body; var $from; var $host; var $port; var $helo; var $auth; var $user; var $pass; /** * 引數為一個數組 * host SMTP 伺服器的主機 預設:localhost * port SMTP 伺服器的埠 預設:25 * helo 傳送HELO命令的名稱 預設:localhost * user SMTP 伺服器的使用者名稱 預設:空值 * pass SMTP 伺服器的登陸密碼 預設:空值 * timeout 連線超時的時間 預設:5 * @return bool */ function p8_smtp($params = array()) { if(!defined('CRLF')) define('CRLF', "\r\n", TRUE); $this->timeout = 5; $this->status = SMTP_STATUS_NOT_CONNECTED; $this->host = 'localhost'; $this->port = 25; $this->auth = FALSE; $this->user = ''; $this->pass = ''; $this->errors = array(); foreach($params as $key => $value) { $this->$key = $value; } $this->helo = $this->host; // 如果沒有設定使用者名稱則不驗證 $this->auth = ('' == $this->user) ? FALSE : TRUE; } function connect($params = array()) { if(!isset($this->status)) { $obj = new p8_smtp($params); if($obj->connect()) { $obj->status = SMTP_STATUS_CONNECTED; } return $obj; } else { $this->connection = fsockopen($this->host, $this->port, $errno, $errstr, $this->timeout); socket_set_timeout($this->connection, 0, 250000); $greeting = $this->get_data(); if(is_resource($this->connection)) { $this->status = 2; return $this->auth ? $this->ehlo() : $this->helo(); } else { $this->errors[] = 'Failed to connect to server: '.$errstr; return FALSE; } } } /** * 引數為陣列 * recipients 接收人的陣列 * from 發件人的地址,也將作為回覆地址 * headers 頭部資訊的陣列 * body 郵件的主體 */ function send($params = array()) { foreach($params as $key => $value) { $this->set($key, $value); } if($this->is_connected()) { // 伺服器是否需要驗證 if($this->auth) { if(!$this->auth()) return FALSE; } $this->mail($this->from); if(is_array($this->recipients)) { foreach($this->recipients as $value) { $this->rcpt($value); } } else { $this->rcpt($this->recipients); } if(!$this->data()) return FALSE; $headers = str_replace(CRLF.'.', CRLF.'..', trim(implode(CRLF, $this->headers))); $body = str_replace(CRLF.'.', CRLF.'..', $this->body); $body = $body[0] == '.' ? '.'.$body : $body; $this->send_data($headers); $this->send_data(''); $this->send_data($body); $this->send_data('.'); return (substr(trim($this->get_data()), 0, 3) === '250'); } else { $this->errors[] = 'Not connected!'; return FALSE; } } function helo() { if(is_resource($this->connection) AND $this->send_data('HELO '.$this->helo) AND substr(trim($error = $this->get_data()), 0, 3) === '250' ) { return TRUE; } else { $this->errors[] = 'HELO command failed, output: ' . trim(substr(trim($error),3)); return FALSE; } } function ehlo() { if(is_resource($this->connection) AND $this->send_data('EHLO '.$this->helo) AND substr(trim($error = $this->get_data()), 0, 3) === '250' ) { return TRUE; } else { $this->errors[] = 'EHLO command failed, output: ' . trim(substr(trim($error),3)); return FALSE; } } function auth() { if(is_resource($this->connection) AND $this->send_data('AUTH LOGIN') AND substr(trim($error = $this->get_data()),0,3) === '334' AND $this->send_data(base64_encode($this->user)) // Send username AND substr(trim($error = $this->get_data()),0,3) === '334' AND $this->send_data(base64_encode($this->pass)) // Send password AND substr(trim($error = $this->get_data()),0,3) === '235' ) { return TRUE; } else { $this->errors[] = 'AUTH command failed: ' . trim(substr(trim($error),3)); return FALSE; } } function mail($from) { if($this->is_connected() AND $this->send_data('MAIL FROM:<'.$from.'>') AND substr(trim($this->get_data()), 0, 2) === '250' ) { return TRUE; } else { return FALSE; } } function rcpt($to) { if($this->is_connected() AND $this->send_data('RCPT TO:<'.$to.'>') AND substr(trim($error = $this->get_data()), 0, 2) === '25' ) { return TRUE; } else { $this->errors[] = trim(substr(trim($error), 3)); return FALSE; } } function data() { if($this->is_connected() AND $this->send_data('DATA') AND substr(trim($error = $this->get_data()), 0, 3) === '354' ) { return TRUE; } else { $this->errors[] = trim(substr(trim($error), 3)); return FALSE; } } function is_connected() { return (is_resource($this->connection) AND ($this->status === SMTP_STATUS_CONNECTED)); } function send_data($data) { if(is_resource($this->connection)) { return fwrite($this->connection, $data.CRLF, strlen($data)+2); } else { return FALSE; } } function &get_data() { $return = ''; $line = ''; if(is_resource($this->connection)) { while(strpos($return, CRLF) === FALSE OR substr($line,3,1) !== ' ') { $line = fgets($this->connection, 512); echo $line."<br/>"; $return .= $line; } return $return; } else { return FALSE; } } function set($var, $value) { $this->$var = $value; return TRUE; } } // End of class class smtp { var $debug; var $host; var $port; var $auth; var $user; var $pass; function smtp($host = "", $port = 25,$auth = false,$user,$pass){ $this->host=$host; $this->port=$port; $this->auth=$auth; $this->user=$user; $this->pass=$pass; } function sendmail($to,$from, $subject, $content, $T=0){ //$name, $email, $subject, $content, $type=0 $type=1; $name=array($from); $email=array($to); $_CFG['smtp_host']= $this->host; $_CFG['smtp_port']= $this->port; $_CFG['smtp_user']= $this->user; $_CFG['smtp_pass']= $this->pass; $_CFG['name']= $from; $_CFG['smtp_mail']= $from; $subject = "=?UTF-8?B?".base64_encode($subject)."==?="; $content = base64_encode($content); $headers[] = "To:=?gbk?B?".base64_encode($name[0])."?= <$email[0]>"; $headers[] = "From:=?gbk?B?".base64_encode($_CFG['name'])."?= <$_CFG[smtp_mail]>"; $headers[] = "MIME-Version: Blueidea v1.0"; $headers[] = "X-Mailer: 9gongyu Mailer v1.0"; $headers[] = "Subject:$subject"; $headers[] = ($type == 0) ? "Content-Type: text/plain; charset=gbk; format=flowed" : "Content-Type: text/html; charset=utf-8; format=flowed"; $headers[] = "Content-Transfer-Encoding: base64"; $headers[] = "Content-Disposition: inline"; // SMTP 伺服器資訊 $params['host'] = $_CFG['smtp_host']; $params['port'] = $_CFG['smtp_port']; $params['user'] = $_CFG['smtp_user']; $params['pass'] = $_CFG['smtp_pass']; if (empty($params['host']) || empty($params['port'])) { // 如果沒有設定主機和埠直接返回 false return false; } else { // 傳送郵件 $send_params['recipients'] = $email; $send_params['headers'] = $headers; $send_params['from'] = $_CFG['smtp_mail']; $send_params['body'] = $content; /* 用於測試資訊 echo "<pre>"; print_r($params); print_r($send_params); echo "</pre>"; exit; */ $smtp = new p8_smtp($params); if($smtp->connect() AND $smtp->send($send_params)) { return TRUE; } else { return FALSE; } } } } ?>
下面便是測試部分sendmail.php:
<?php
/**
* @desc SMTP 郵件伺服器
* @param 伺服器引數和郵件資訊
*/
header("Content-type:text/html;charset=utf-8");
require_once("class.mail.php");
/**
*伺服器資訊
*/
$MailServer = 'smtp.qq.com'; //SMTP 伺服器
$MailPort = '25'; //SMTP伺服器埠號 預設25
$MailId = '請填寫自己QQ郵箱'; //伺服器郵箱帳號
$MailPw = '自己QQ郵箱密碼'; //伺服器郵箱密碼
/**
*客戶端資訊
*/
$Title = 'TESTMAIL成功'; //郵件標題
$Content = '測試郵件內容'; //郵件內容
$email = '要傳送到的QQ郵箱'; //接收者郵箱
$smtp = new smtp($MailServer,$MailPort,true,$MailId,$MailPw);
$smtp->debug = false;
if($smtp->sendmail($email,$MailId, $Title, $Content, "HTML")){
echo '郵件傳送成功'; //返回結果
} else {
echo '郵件傳送失敗'; //$succeed = 0;
}
?>