smtp邮件发送一例


Posted in PHP onOctober 09, 2006

test_smtp.php

<?
require("smtp.php");

$smtp=new smtp_class;

$smtp->host_name="mail.xiaocui.com";
$smtp->localhost="localhost";
$from="webmaster@xiaocui.com";
$to="root@xiaocui.com";
if($smtp->SendMessage(
  $from,
  array(
   $to
  ),
  array(
   "From: $from",
   "To: $to",
   "Subject: Testing Manuel Lemos' SMTP class"
  ),
  "Hello $to,\n\nIt is just to let you know that your SMTP class is working just fine.\n\nBye.\n"))
  echo "Message sent to $to OK.\n";
else
  echo "Cound not send the message to $to.\nError: ".$smtp->error."\n"
?>

smtp.php

<?

class smtp_class
{
var $host_name="";
var $host_port=25;
var $localhost="";
var $timeout=0;
var $error="";
var $debug=1;
var $esmtp=1;
var $esmtp_host="";
var $esmtp_extensions=array();
var $maximum_piped_recipients=100;

/* private variables - DO NOT ACCESS */

var $state="Disconnected";
var $connection=0;
var $pending_recipients=0;

/* Private methods - DO NOT CALL */

Function OutputDebug($message)
{
  echo $message,"<br>\n";
}

Function GetLine()
{
  for($line="";;)
  {
   if(feof($this->connection))
   {
    $this->error="reached the end of stream while reading from socket";
    return(0);
   }
   if(($data=fgets($this->connection,100))==false)
   {
    $this->error="it was not possible to read line from socket";
    return(0);
   }
   $line.=$data;
   $length=strlen($line);
   if($length>=2
   && substr($line,$length-2,2)=="\r\n")
   {
    $line=substr($line,0,$length-2);
    if($this->debug)
     $this->OutputDebug("< $line");
    return($line);
   }
  }
}

Function PutLine($line)
{
  if($this->debug)
   $this->OutputDebug("> $line");
  if(!fputs($this->connection,"$line\r\n"))
  {
   $this->error="it was not possible to write line to socket";
   return(0);
  }
  return(1);
}

Function PutData($data)
{
  if(strlen($data))
  {
   if($this->debug)
    $this->OutputDebug("> $data");
   if(!fputs($this->connection,$data))
   {
    $this->error="it was not possible to write data to socket";
    return(0);
   }
  }
  return(1);
}

Function VerifyResultLines($code,$responses="")
{
  if(GetType($responses)!="array")
   $responses=array();
  Unset($match_code);

  while(($line=$this->GetLine($this->connection)))
  {
   if(IsSet($match_code))
   {
    if(strcmp(strtok($line," -"),$match_code))
    {
     $this->error=$line;
     return(0);
    }
   }
   else
   {
    $match_code=strtok($line," -");
    if(GetType($code)=="array")
    {
     for($codes=0;$codes<count($code) && strcmp($match_code,$code[$codes]);$codes++);
     if($codes>=count($code))
     {
      $this->error=$line;
      return(0);
     }
    }
    else
    {
     if(strcmp($match_code,$code))
     {
      $this->error=$line;
      return(0);
     }
    }
   }
   $responses[]=strtok("");
   if(!strcmp($match_code,strtok($line," ")))
    return(1);
  }
  return(-1);
}

Function FlushRecipients()
{
  if($this->pending_sender)
  {
   if($this->VerifyResultLines("250")<=0)
    return(0);
   $this->pending_sender=0;
  }
  for(;$this->pending_recipients;$this->pending_recipients--)
  {
   if($this->VerifyResultLines(array("250","251"))<=0)
    return(0);
  }
  return(1);
}

/* Public methods */

Function Connect()
{
  $this->error=$error="";
   $this->esmtp_host="";
   $this->esmtp_extensions=array();
  if(!($this->connection=($this->timeout ? fsockopen($this->host_name,$this->host_port,&$errno,&$error,$this->timeout) : fsockopen($this->host_name,$this->host_port))))
  {
   switch($error)
   {
    case -3:
     $this->error="-3 socket could not be created";
     return(0);
    case -4:
     $this->error="-4 dns lookup on hostname \"".$host_name."\" failed";
     return(0);
    case -5:
     $this->error="-5 connection refused or timed out";
     return(0);
    case -6:
     $this->error="-6 fdopen() call failed";
     return(0);
    case -7:
     $this->error="-7 setvbuf() call failed";
     return(0);
    default:
     $this->error=$error." could not connect to the host \"".$this->host_name."\"";
     return(0);
   }
  }
  else
  {
   if(!strcmp($localhost=$this->localhost,"")
   && !strcmp($localhost=getenv("SERVER_NAME"),"")
   && !strcmp($localhost=getenv("HOST"),""))
     $localhost="localhost";
    $success=0;
    if($this->VerifyResultLines("220")>0)
    {
     if($this->esmtp)
     {
      $responses=array();
      if($this->PutLine("EHLO $localhost")
      && $this->VerifyResultLines("250",&$responses)>0)
      {
       $this->esmtp_host=strtok($responses[0]," ");
       for($response=1;$response<count($responses);$response++)
       {
        $extension=strtoupper(strtok($responses[$response]," "));
        $this->esmtp_extensions[$extension]=strtok("");
       }
       $success=1;
      }
     }
     if(!$success
     && $this->PutLine("HELO $localhost")
     && $this->VerifyResultLines("250")>0)
      $success=1;
   }
   if($success)
   {
    $this->state="Connected";
    return(1);
   }
   else
   {
    fclose($this->connection);
    $this->connection=0;
    $this->state="Disconnected";
    return(0);
   }
  }
}

Function MailFrom($sender)
{
  if(strcmp($this->state,"Connected"))
  {
   $this->error="connection is not in the initial state";
   return(0);
  }
  $this->error="";
  if(!$this->PutLine("MAIL FROM: <".$sender.">"))
   return(0);
  if(!IsSet($this->esmtp_extensions["PIPELINING"])
  && $this->VerifyResultLines("250")<=0)
   return(0);
  $this->state="SenderSet";
  if(IsSet($this->esmtp_extensions["PIPELINING"]))
   $this->pending_sender=1;
  $this->pending_recipients=0;
  return(1);
}

Function SetRecipient($recipient)
{
  switch($this->state)
  {
   case "SenderSet":
   case "RecipientSet":
    break;
   default:
    $this->error="connection is not in the recipient setting state";
    return(0);
  }
  $this->error="";
  if(!$this->PutLine("RCPT TO:<".$recipient.">"))
   return(0);
  if(IsSet($this->esmtp_extensions["PIPELINING"]))
  {
   $this->pending_recipients++;
   if($this->pending_recipients>=$this->maximum_piped_recipients)
   {
    if(!$this->FlushRecipients())
     return(0);
   }
  }
  else
  {
   if($this->VerifyResultLines(array("250","251"))<=0)
    return(0);
  }
  $this->state="RecipientSet";
  return(1);
}

Function StartData()
{
  if(strcmp($this->state,"RecipientSet"))
  {
   $this->error="connection is not in the start sending data state";
   return(0);
  }
  $this->error="";
  if(!$this->PutLine("DATA"))
   return(0);
  if($this->pending_recipients)
  {
   if(!$this->FlushRecipients())
    return(0);
  }
  if($this->VerifyResultLines("354")<=0)
   return(0);
  $this->state="SendingData";
  return(1);
}

Function PrepareData($data,&$output)
{
  $length=strlen(&$data);
  for($output="",$position=0;$position<$length;)
  {
   $next_position=$length;
   for($current=$position;$current<$length;$current++)
   {
    switch($data[$current])
    {
     case "\n":
      $next_position=$current+1;
      break 2;
     case "\r":
      $next_position=$current+1;
      if($data[$next_position]=="\n")
       $next_position++;
      break 2;
    }
   }
   if($data[$position]==".")
    $output.=".";
   $output.=substr(&$data,$position,$current-$position)."\r\n";
   $position=$next_position;
  }
}

Function SendData($data)
{
  if(strcmp($this->state,"SendingData"))
  {
   $this->error="connection is not in the sending data state";
   return(0);
  }
  $this->error="";
  return($this->PutData(&$data));
}

Function EndSendingData()
{
  if(strcmp($this->state,"SendingData"))
  {
   $this->error="connection is not in the sending data state";
   return(0);
  }
  $this->error="";
  if(!$this->PutLine("\r\n.")
  || $this->VerifyResultLines("250")<=0)
   return(0);
  $this->state="Connected";
  return(1);
}

Function ResetConnection()
{
  switch($this->state)
  {
   case "Connected":
    return(1);
   case "SendingData":
    $this->error="can not reset the connection while sending data";
    return(0);
   case "Disconnected":
    $this->error="can not reset the connection before it is established";
    return(0);
  }
  $this->error="";
  if(!$this->PutLine("RSET")
  || $this->VerifyResultLines("250")<=0)
   return(0);
  $this->state="Connected";
  return(1);
}

Function Disconnect($quit=1)
{
  if(!strcmp($this->state,"Disconnected"))
  {
   $this->error="it was not previously established a SMTP connection";
   return(0);
  }
  $this->error="";
  if(!strcmp($this->state,"Connected")
  && $quit
  && (!$this->PutLine("QUIT")
  || $this->VerifyResultLines("221")<=0))
   return(0);
  fclose($this->connection);
  $this->connection=0;
  $this->state="Disconnected";
  return(1);
}

Function SendMessage($sender,$recipients,$headers,$body)
{
  if(($success=$this->Connect()))
  {
   if(($success=$this->MailFrom($sender)))
   {
    for($recipient=0;$recipient<count($recipients);$recipient++)
    {
     if(!($success=$this->SetRecipient($recipients[$recipient])))
      break;
    }
    if($success
    && ($success=$this->StartData()))
    {
     for($header_data="",$header=0;$header<count($headers);$header++)
      $header_data.=$headers[$header]."\r\n";
     if(($success=$this->SendData($header_data."\r\n")))
     {
      $this->PrepareData($body,&$body_data);
      $success=$this->SendData($body_data);
     }
     if($success)
      $success=$this->EndSendingData();
    }
   }
   $disconnect_success=$this->Disconnect($success);
   if($success)
    $success=$disconnect_success;
  }
  return($success);
}

};

?>

PHP 相关文章推荐
最简单的PHP程序--记数器
Oct 09 PHP
dede3.1分页文字采集过滤规则详说(图文教程)续四
Apr 03 PHP
PHP中如何判断AJAX提交的数据
Feb 05 PHP
php计划任务之ignore_user_abort函数实现方法
Jan 08 PHP
php+mysql实现的二级联动菜单效果详解
May 10 PHP
thinkPHP分组后模板无法加载问题解决方法
Jul 12 PHP
PHP实现生成带背景的图形验证码功能
Oct 03 PHP
详解PHP用substr函数截取字符串中的某部分
Dec 03 PHP
php获取网站根目录物理路径的几种方法(推荐)
Mar 04 PHP
PHP defined()函数的使用图文详解
Jul 20 PHP
php实现微信小程序授权登录功能(实现流程)
Nov 13 PHP
PHP文件打开关闭及读写操作示例解析
Aug 06 PHP
图片存储与浏览一例(Linux+Apache+PHP+MySQL)
Oct 09 #PHP
PHP+javascript液晶时钟
Oct 09 #PHP
一个分页的论坛
Oct 09 #PHP
一个简易需要注册的留言版程序
Oct 09 #PHP
使用数据库保存session的方法
Oct 09 #PHP
COM in PHP (winows only)
Oct 09 #PHP
Banner程序
Oct 09 #PHP
You might like
PHP 中文处理技巧
2010/04/25 PHP
php preg_filter执行一个正则表达式搜索和替换
2012/02/27 PHP
smarty获得当前url的方法分享
2014/02/14 PHP
PHP各种异常和错误的拦截方法及发生致命错误时进行报警
2016/01/19 PHP
PHP获取ttf格式文件字体名的方法示例
2019/03/06 PHP
JavaScript 变量基础知识
2009/11/07 Javascript
一些常用且实用的原生JavaScript函数
2010/09/08 Javascript
基于JQuery的一个简单的鼠标跟随提示效果
2010/09/23 Javascript
JavaScript中的isXX系列是否继续使用的分析
2011/04/16 Javascript
使用jquery动态加载javascript以减少服务器压力
2012/10/29 Javascript
使用JavaScript+canvas实现图片裁剪
2015/01/30 Javascript
JS数组合并push与concat区别分析
2015/12/17 Javascript
原生js代码实现图片放大境效果
2016/10/30 Javascript
将json转换成struts参数的方法
2016/11/08 Javascript
你真的了解BOM中的history对象吗
2017/02/13 Javascript
jquery表单验证实例仿Toast提示效果
2017/03/03 Javascript
详解使用WebPack搭建React开发环境
2019/08/06 Javascript
编写一个javascript元循环求值器的方法
2020/04/14 Javascript
[19:15]DK战队纪录片
2014/09/02 DOTA
[10:39]DOTA2上海特级锦标赛音乐会纪录片
2016/03/21 DOTA
python3写的简单本地文件上传服务器实例
2018/06/04 Python
python爬虫 基于requests模块发起ajax的get请求实现解析
2019/08/20 Python
Python数据持久化存储实现方法分析
2019/12/21 Python
利用Python批量识别电子账单数据的方法
2021/02/08 Python
介绍CSS3使用技巧5个
2009/04/02 HTML / CSS
Pandora德国官网:购买潘多拉手链、戒指、项链和耳环
2020/02/20 全球购物
Belstaff英国官方在线商店:Belstaff.co.uk
2021/02/09 全球购物
颇特女士香港官网:NET-A-PORTER香港
2021/03/08 全球购物
UNIX操作系统结构由哪几部分组成
2016/02/17 面试题
高校教师自荐信范文
2014/03/13 职场文书
文明寄语大全
2014/04/11 职场文书
节能环保标语
2014/06/12 职场文书
追悼会答谢词
2015/01/05 职场文书
优秀学生主要事迹怎么写
2015/11/04 职场文书
九年级英语教学反思
2016/02/15 职场文书
Java循环队列与非循环队列的区别总结
2021/06/22 Java/Android