|  | 
 
| 本帖最后由 iamrwang 于 2018-2-23 08:26 编辑 
 项目需求为客户发送电子邮件。于是申请阿里云邮件推送。阿里云邮件推送有三种邮件发送方式。这里使用api接口发送。于是根据阿里文档编写此发送类,与大家分享。(在使用前请正确配置阿里邮件推送)
 
 libraries\alidm.php
 
 <?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
 
 /**
 * @desc: 阿里云邮件推送Api
 * @copyright 2018.02
 */
 
 class Alidm {
 
 // 常量定义
 // DirectMail API 的服务接入地址
 const URL_DM = 'https://dm.aliyuncs.com';
 // const URL_DM = 'http://dm.aliyuncs.com';
 private $akeyid;
 private $keysecret;
 private $accountname;
 
 private $method = 'POST';
 private $signatureversion = '1.0';
 private $regionid = 'cn-hangzhou';
 private $version = '2015-11-23';
 private $signaturemethod= 'HMAC-SHA1';
 private $replytoaddress = 'true';
 private $addresstype = 1;
 private $clicktrace = 0;
 
 public function __construct($config='')
 {
 if (!empty($config))
 {
 $this->initialize($config);
 }
 }
 
 /**
 * @desc 初始化
 * @access public
 * @param $config array
 **/
 public function initialize($config = array())
 {
 if(isset($config['AccessKeyId']))
 {
 $this->akeyid = $config['AccessKeyId'];
 }
 if(isset($config['AccessKeySecret']))
 {
 $this->keysecret = $config['AccessKeySecret'];
 }
 if(isset($config['method']))
 {
 $this->method = $config['method'];
 }
 if(isset($config['AccountName']))
 {
 $this->accountname = $config['AccountName'];
 $this->addresstype = 1;
 }else{
 $this->accountname = '';
 $this->addresstype = 0;
 }
 if(isset($config['ReplyToAddress']))
 {
 $this->replytoaddress = $config['ReplyToAddress'];
 }
 if(isset($config['ClickTrace']))
 {
 $this->clicktrace = $config['ClickTrace'];
 }
 }
 
 /**
 * @desc 编码
 * @access private
 * @param $string 要编码的字符串
 * @param return string
 **/
 private function percentencode($string)
 {
 $string = urlencode($string);
 $string = preg_replace('/\+/', '%20', $string);
 $string = preg_replace('/\*/', '%2A', $string);
 $string = preg_replace('/%7E/', '~', $string);
 return $string;
 }
 
 /**
 * @desc 计算签名
 * @access private
 * @param $params 要计算签名的参数
 * @return string
 **/
 private function signature($params)
 {
 ksort($params);
 $queryString = '';
 foreach($params as $key => $value)
 {
 $queryString .= '&'.$this->percentencode($key).'='.$this->percentencode($value);
 }
 
 $stringToSign = $this->method.'&%2F&'.$this->percentencode(substr($queryString,1));
 $sign = base64_encode(hash_hmac('sha1', $stringToSign, $this->keysecret.'&', true));
 return $sign;
 }
 
 /**
 * @desc POST 请求
 * @access public
 * @param $params array post数据
 * @param $url string
 * @return array()
 **/
 public function curlpost($params,$url=self::URL_DM)
 {
 $headers = array(
 'Host'=>'dm.aliyuncs.com',
 'Content-Type'=>'application/x-www-form-urlencoded'
 );
 
 $ch = curl_init();
 curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
 //https request
 if (strlen($url) > 5 && strtolower(substr($url, 0, 5)) == "https")
 {
 curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
 curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false);
 }
 curl_setopt($ch, CURLOPT_URL, $url);
 curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
 curl_setopt($ch, CURLOPT_POST, true);
 curl_setopt($ch, CURLOPT_POSTFIELDS, $params);
 curl_setopt($ch, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_0);
 curl_setopt($ch, CURLOPT_TIMEOUT, 5);
 
 $content = curl_exec($ch);
 curl_close($ch);
 $array = $this->xml2array($content);
 return $array;
 }
 
 /**
 * @desc 生成随机数
 * @access public
 * @param $len 长度
 * @return string
 **/
 public function get_nonce_string($len=32)
 {
 return substr(str_shuffle('abcdefghijklmnopqrstuvwxyz0123456789'),0,$len);
 }
 
 // 单一发信(触发邮件)接口
 public function single_send($to,$cont,$subject='',$alias='')
 {
 $params = array();
 // 公共请求参数
 // 返回值的类型,支持 JSON 与 XML.默认为 XML
 // $data['Format'] = 'JSON';
 // API 版本号, cn-hangzhou,则版本对应为 2015-11-23
 $params['Version'] = $this->version;
 // 阿里云颁发给用户的访问服务所用的密钥 ID
 $params['AccessKeyId'] = $this->akeyid;
 // 签名方式
 $params['SignatureMethod'] = $this->signaturemethod;
 // 请求的时间戳
 $params['Timestamp'] = gmdate('Y-m-d\TH:i:s\Z');
 // 签名算法版本
 $params['SignatureVersion'] = $this->signatureversion;
 // 唯一随机数
 $params['SignatureNonce'] = $this->get_nonce_string(8);
 // 机房信息
 $params['RegionId'] = $this->regionid;
 
 // 单一发信接口请求参数
 // 操作接口名
 $params['Action'] = 'SingleSendMail';
 // 管理控制台中配置的发信地址
 $params['AccountName'] = $this->accountname;
 // 使用管理控制台中配置的回信地址
 $params['ReplyToAddress'] = $this->replytoaddress;
 // 0 为随机账号;1 为发信地址
 $params['AddressType'] = $this->addresstype;
 // 目标地址,多个 email 地址可以用逗号分隔,最多100个地址
 $params['ToAddress'] = '';
 if(is_array($to))
 {
 foreach($to as $val)
 {
 if($this->is_email($val))
 {
 $data['ToAddress'] .= ','.$val;
 }
 }
 $params['ToAddress'] = ltrim($data['ToAddress'],',');
 }else{
 $params['ToAddress'] = $this->is_email($to)?$to:'';
 }
 // 发信人昵称
 if($alias)
 {
 $params['FromAlias'] = $alias;
 }
 // 邮件主题
 if($subject)
 {
 $params['Subject'] = $subject;
 }
 // 邮件 html 正文
 $params['HtmlBody'] = $cont;
 // 取值范围 0~1: 1 为打开数据跟踪功能
 if($this->clicktrace)
 {
 $params['ClickTrace'] = 1;
 }
 if($params['ToAddress'])
 {
 // 签名结果串
 $signature = $this->signature($params);
 $params['Signature'] = $signature;
 /*
 $data = '';
 foreach($params as $k=>$v)
 {
 $data .= '&'.$k.'='.$v;
 }
 $res = $this->curlpost(substr($data,1));
 */
 $res = $this->curlpost($params);
 }else{
 $res = FALSE;
 }
 return $res;
 }
 
 // xml 转数组
 protected function xml2array($xml)
 {
 $array = array();
 $tmp = null;
 try{
 $tmp = (array) simplexml_load_string($xml);
 }catch(Exception $e){}
 if($tmp && is_array($tmp)){
 foreach ( $tmp as $k => $v) {
 $array[$k] = (string) $v;
 }
 }
 return $array;
 }
 
 /**
 * Valid Email
 *
 * @param    string
 * @return    bool
 */
 protected function is_email($str)
 {
 if (function_exists('idn_to_ascii') && sscanf($str, '%[^@]@%s', $name, $domain) === 2)
 {
 $str = $name.'@'.idn_to_ascii($domain);
 }
 
 return (bool) filter_var($str, FILTER_VALIDATE_EMAIL);
 }
 
 }
 
 使用方法:
 在 config/email.php中定义配置
 
 $config['dmconf'] = array(    'AccessKeyId'    =>    '阿里AccessKeyId',
 'AccessKeySecret'=>    '阿里AccessKeySecret',
 'method'        =>    'POST',
 'AccountName'    =>    '发件地址',
 // 'ReplyToAddress'=>    TRUE,
 'ClickTrace'    =>    1
 );
 
 邮件推送:
 
 // api 推送
 public function api_mail()
 {
 $emailto = 'xxxxxxxx@163.com';
 $mailcontent = '这是一封由阿里云邮件推送服务发送的测试邮件,邮件生成时间:'.gmdate('Y-m-d H:i:s');
 $subject = '邮件推送测试';
 $alias = '【名称】';
 $this->config->load('email', TRUE);
 $config = $this->config->item('dmconf','email');
 $this->load->library('alidm',$config);
 $res = $this->alidm->single_send($emailto,$mailcontent,$subject,$alias);
 
 var_dump($res);
 }
 
 与大家分享,高手勿喷。
 
 
 
 | 
 |