Source for file Mail.php

Documentation is available at Mail.php

  1. <?php
  2. /*
  3. * This file is part of Sylar.
  4. *
  5. * Sylar is free software: you can redistribute it and/or modify
  6. * it under the terms of the GNU Lesser General Public License as published by
  7. * the Free Software Foundation, either version 3 of the License, or
  8. * (at your option) any later version.
  9. *
  10. * Sylar is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU Lesser General Public License for more details.
  14. *
  15. * You should have received a copy of the GNU Lesser General Public License
  16. * along with Sylar. If not, see <http://www.gnu.org/licenses/>.
  17. *
  18. * @copyright Copyright Sylar Development Team
  19. * @license http://www.gnu.org/licenses/ GNU Public License V2.0
  20. * @see https://launchpad.net/sylar/
  21. * @see http://www.giano-solutions.com
  22. */
  23. import('sylar.common.system.ConfigBox');
  24. import('sylar.common.locale.Locale');
  25.  
  26. /**
  27. * Mail
  28. *
  29. * Class to send mail in txt and html format
  30. *
  31. * @package Sylar
  32. * @version 1.0
  33. * @since 22/apr/08
  34. * @author Gianluca Giusti [brdp] <g.giusti@giano-solutions.com>
  35. * @copyright Sylar Development Team
  36. */
  37. class Sylar_Mail{
  38. /**
  39. * Sender email address
  40. * @var string
  41. */
  42. private $sFrom;
  43. /**
  44. * Email address for eventually Reply To
  45. * @var string
  46. */
  47. private $sReplyTo;
  48. /**
  49. * Recipient email address array.
  50. *
  51. * The array has this structure:
  52. * $aSend_To = array(
  53. * "Mark Green" => "m.green@exampmail.com",
  54. * "Mark Black" => "m.black@exampmail.com"
  55. * )
  56. *
  57. * The array information will be transformed in:
  58. * Mark Green <m.green@exampmail.com>, Mark Black <m.black@exampmail.com>
  59. *
  60. * @var array
  61. */
  62. private $aSend_To;
  63. /**
  64. * Recipient CC email address array
  65. * array structure is the same of $aSend_To
  66. *
  67. * @see $aSend_To
  68. * @var array
  69. */
  70. private $aSend_CC;
  71. /**
  72. * Recipient BCC email address array
  73. * array structure is the same of $aSend_To
  74. *
  75. * @see $aSend_To
  76. * @var array
  77. */
  78. private $aSend_BCC;
  79.  
  80. /**
  81. * Mail Header informations
  82. *
  83. * @see mail() php function for specific. http://it.php.net/manual/it/function.mail.php
  84. *
  85. * @var string
  86. */
  87. private $sHeader;
  88. /**
  89. * Email message object
  90. * @var string
  91. */
  92. private $sObject;
  93. /**
  94. * Mail Message Text or HTML
  95. * @var string
  96. */
  97. private $sMessage;
  98. /**
  99. * Mail type, can be txt, html or other in the future...
  100. * @var string
  101. */
  102. private $sMailType;
  103. /**
  104. * Constructor
  105. *
  106. * @return void
  107. * @param string $sMailType default is txt
  108. * @param string $sFrom
  109. * @param string $sReplyTo
  110. */
  111. function __construct($sMailType="txt", $sFrom=null, $sReplyTo=null){
  112. try{
  113. // check and set email type
  114. $this->setMailType($sMailType);
  115. // check and set eventually Sender Address
  116. if(!is_null($sFrom)){
  117. $this->setFrom($sFrom);
  118. }
  119. // check and set eventually Sender Address Reply to
  120. if(!is_null($sReplyTo)){
  121. $this->setReplyTo($sReplyTo);
  122. }
  123. }catch (ExceptionInSylar $ex){
  124. throw $ex;
  125. }
  126. }
  127.  
  128. function __destruct() {
  129. # nothing to do
  130. }
  131.  
  132. // Getter and Setter Methods
  133. //__________________________________________________________________________
  134.  
  135.  
  136. /**
  137. * @return void
  138. * @param string $sFrom
  139. */
  140. public function setFrom($sFrom){
  141. $this->sFrom = $sFrom;
  142. }
  143. /**
  144. * @return string
  145. */
  146. public function getFrom(){
  147. return $this->sFrom;
  148. }
  149.  
  150.  
  151. /**
  152. * @return void
  153. * @param string $sFrom
  154. */
  155. public function setReplyTo($sReplyTo){
  156. $this->sReplyTo = $sReplyTo;
  157. }
  158. /**
  159. * @return string
  160. */
  161. public function getReplyTo(){
  162. return $this->sReplyTo;
  163. }
  164.  
  165.  
  166. /**
  167. * @return void
  168. * @param array $sFrom
  169. */
  170. public function setSend_To($aSendTo){
  171. $this->aSend_To = $aSendTo;
  172. }
  173. /**
  174. * @return array
  175. */
  176. public function getSend_To(){
  177. return $this->aSend_To;
  178. }
  179.  
  180.  
  181. /**
  182. * @return void
  183. * @param array $sFrom
  184. */
  185. public function setSend_CC($aSend_CC){
  186. $this->aSend_CC = $aSend_CC;
  187. }
  188. /**
  189. * @return array
  190. */
  191. public function getSend_CC(){
  192. return $this->aSend_CC;
  193. }
  194.  
  195. /**
  196. * @return void
  197. * @param array $sFrom
  198. */
  199. public function setSend_BCC($aSend_BCC){
  200. $this->aSend_BCC = $aSend_BCC;
  201. }
  202. /**
  203. * @return array
  204. */
  205. public function getSend_BCC(){
  206. return $this->aSend_BCC;
  207. }
  208.  
  209.  
  210. /**
  211. * @return void
  212. * @param string $sFrom
  213. */
  214. public function setHeader($sHeader){
  215. $this->sHeader = $sHeader;
  216. }
  217. /**
  218. * @return string
  219. */
  220. public function getHeader(){
  221. return $this->sHeader;
  222. }
  223. /**
  224. * @return void
  225. * @param string $sFrom
  226. */
  227. public function setObject($sObject){
  228. $this->sObject = $sObject;
  229. }
  230. /**
  231. * @return string
  232. */
  233. public function getObject(){
  234. return $this->sObject;
  235. }
  236.  
  237. /**
  238. * @return void
  239. * @param string $sFrom
  240. */
  241. public function setMessage($sMessage){
  242. $this->sMessage = $sMessage;
  243. }
  244. /**
  245. * @return string
  246. */
  247. public function getMessage(){
  248. return $this->sMessage;
  249. }
  250.  
  251. /**
  252. * It also check if specified type exists and is supported
  253. * @return void
  254. * @param string $sFrom
  255. */
  256. public function setMailType($sMailType){
  257. try{
  258. // check and set email type
  259. if($sMailType=="txt" || $sMailType=="html"){
  260. $this->sMailType = $sMailType;
  261. }else{
  262. throw new ExceptionInSylar("Unknown Mail Type: ".$sMailType, 10014 );
  263. }
  264. }catch (ExceptionInSylar $ex){
  265. throw $ex;
  266. }
  267. }
  268. /**
  269. * @return string
  270. */
  271. public function getMailType(){
  272. return $this->sMailType;
  273. }
  274.  
  275.  
  276. // Public Methods
  277. //__________________________________________________________________________
  278. /**
  279. * Send the e-mail
  280. * It prepare header, object and all the other field and send the e-mail
  281. *
  282. * @return void
  283. * @param string $sObject
  284. * @param string $sMessage
  285. * @param string $sCharSet
  286. */
  287. public function send($sObject=null, $sMessage=null, $sCharSet=null){
  288. try{
  289. // Prepare Obj, Message and header
  290. if(!is_null($sObject)){
  291. $this->setObject($sObject);
  292. }
  293. if(!is_null($sMessage)){
  294. $this->setMessage($sMessage);
  295. }
  296. // Send the email.
  297. // TODO
  298. mail(null, $this->getObject(), $this->getMessage(), $this->provideHeader(null, $sCharSet));
  299. }catch (ExceptionInSylar $ex){
  300. throw $ex;
  301. }
  302. }
  303.  
  304. /**
  305. * a temporary address controls...
  306. *
  307. * @todo rewrite this method
  308. *
  309. * @param string $address
  310. * @return boolean
  311. */
  312. public function validateAddress($address){
  313. $valid_tlds = array("arpa", "biz", "com", "edu", "gov", "int", "mil", "net", "org",
  314. "ad", "ae", "af", "ag", "ai", "al", "am", "an", "ao", "aq", "ar", "as", "at", "au",
  315. "aw", "az", "ba", "bb", "bd", "be", "bf", "bg", "bh", "bi", "bj", "bm", "bn", "bo",
  316. "br", "bs", "bt", "bv", "bw", "by", "bz", "ca", "cc", "cf", "cd", "cg", "ch", "ci",
  317. "ck", "cl", "cm", "cn", "co", "cr", "cs", "cu", "cv", "cx", "cy", "cz", "de", "dj",
  318. "dk", "dm", "do", "dz", "ec", "ee", "eg", "eh", "er", "es", "et", "fi", "fj", "fk",
  319. "fm", "fo", "fr", "fx", "ga", "gb", "gd", "ge", "gf", "gh", "gi", "gl", "gm", "gn",
  320. "gp", "gq", "gr", "gs", "gt", "gu", "gw", "gy", "hk", "hm", "hn", "hr", "ht", "hu",
  321. "id", "ie", "il", "in", "io", "iq", "ir", "is", "it", "jm", "jo", "jp", "ke", "kg",
  322. "kh", "ki", "km", "kn", "kp", "kr", "kw", "ky", "kz", "la", "lb", "lc", "li", "lk",
  323. "lr", "ls", "lt", "lu", "lv", "ly", "ma", "mc", "md", "mg", "mh", "mk", "ml", "mm",
  324. "mn", "mo", "mp", "mq", "mr", "ms", "mt", "mu", "mv", "mw", "mx", "my", "mz", "na",
  325. "nc", "ne", "nf", "ng", "ni", "nl", "no", "np", "nr", "nt", "nu", "nz", "om", "pa",
  326. "pe", "pf", "pg", "ph", "pk", "pl", "pm", "pn", "pr", "pt", "pw", "py", "qa", "re",
  327. "ro", "ru", "rw", "sa", "sb", "sc", "sd", "se", "sg", "sh", "si", "sj", "sk", "sl",
  328. "sm", "sn", "so", "sr", "st", "su", "sv", "sy", "sz", "tc", "td", "tf", "tg", "th",
  329. "tj", "tk", "tm", "tn", "to", "tp", "tr", "tt", "tv", "tw", "tz", "ua", "ug", "uk",
  330. "um", "us", "uy", "uz", "va", "vc", "ve", "vg", "vi", "vn", "vu", "wf", "ws", "ye",
  331. "yt", "yu", "za", "zm", "zr", "zw");
  332. // email empty or null
  333. if(is_null($address) || strlen($address)<7)
  334. return false;
  335. // Regular expression
  336. $atom = '[-a-z0-9!#$%&\'*+/=?^_`{|}~]'; // allowed characters for part before "at" character
  337. $domain = '([a-z]([-a-z0-9]*[a-z0-9]+)?)'; // allowed characters for part after "at" character
  338.  
  339. $regex = '^' . $atom . '+' . // One or more atom characters.
  340. '(\.' . $atom . '+)*'. // Followed by zero or more dot separated sets of one or more atom characters.
  341. '@'. // Followed by an "at" character.
  342. '(' . $domain . '{1,63}\.)+'. // Followed by one or max 63 domain characters (dot separated).
  343. $domain . '{2,63}'. // Must be followed by one set consisting a period of two
  344. '$'; // or max 63 domain characters.
  345. if(!eregi($regex, $address)){
  346. return false;
  347. }
  348. // Explode the address on name and domain parts
  349. $name_domain = explode("@", $address);
  350. // There can be only one ;-) I mean... the "@" symbol
  351. if (count($name_domain) != 2)
  352. return false;
  353. // Check the domain parts
  354. $domain_parts = explode(".", $name_domain[1]);
  355. if (count($domain_parts) < 2)
  356. return false;
  357. // Check the TLD ($domain_parts[count($domain_parts) - 1])
  358. if (!in_array($domain_parts[count($domain_parts) - 1], $valid_tlds))
  359. return false;
  360. return true;
  361. }
  362. // Private Methods
  363. //__________________________________________________________________________
  364.  
  365.  
  366. /**
  367. * Return e-mail header
  368. * It prepare and returns the standard e-mail header for txt and html e-mail.
  369. *
  370. * @param string $sMailType
  371. * @param string $sCharSet
  372. * @return string
  373. */
  374. private function provideHeader($sMailType=null, $sCharSet=null){
  375. try{
  376. if(!is_null($sMailType)){
  377. $this->setMailType($sMailType);
  378. }
  379. switch ($this->getMailType()) {
  380. case "txt":
  381. return $this->provideSimpleHeader();
  382. break;
  383. case "html":
  384. return $this->provideHtmlHeader($sCharSet);
  385. break;
  386. // default is TXT
  387. default:
  388. return $this->provideSimpleHeader();
  389. break;
  390. }
  391. }catch (ExceptionInSylar $ex){
  392. throw $ex;
  393. return null;
  394. }
  395. }
  396. /**
  397. * Returns header to use in the txt email
  398. *
  399. * @return string
  400. */
  401. private function provideSimpleHeader(){
  402. try{
  403. $header ="";
  404. // blocking problem
  405. if($this->isEmpty($this->getSend_To())){
  406. throw new ExceptionInSylar("It's impossible to send e-mail to nobody!", 10020);
  407. }else{
  408. $header .= "To: ".$this->prepareAddressList($this->getSend_To())."\r\n";
  409. }
  410.  
  411. // blocking problem
  412. if(is_null($this->getFrom())){
  413. throw new ExceptionInSylar("It's impossible to send e-mail without Sender address specified", 10021);
  414. }else{
  415. $header .= "From: {$this->getFrom()}\r\n";
  416. }
  417.  
  418. // optional information
  419. if(!is_null($this->getReplyTo())){
  420. $header .= "Reply-To: {$this->getReplyTo()}\r\n";
  421. }
  422. // optional information
  423. if(!$this->isEmpty($this->getSend_CC())){
  424. $header .= "Cc: ".$this->prepareAddressList($this->getSend_CC())."\r\n";
  425. }
  426. // optional information
  427. if(!$this->isEmpty($this->getSend_BCC())){
  428. $header .= "Bcc: ".$this->prepareAddressList($this->getSend_BCC())."\r\n";
  429. }
  430. $header .= "X-Mailer: PHP/" . phpversion();
  431. return $header;
  432. }catch (ExceptionInSylar $ex){
  433. throw $ex;
  434. return null;
  435. }
  436. }
  437. /**
  438. * Returns header to use in the html email
  439. *
  440. * @return string
  441. */
  442. private function provideHtmlHeader($sCharSet=null){
  443. try{
  444. $header ="";
  445. // blocking problem
  446. if($this->isEmpty($this->getSend_To())){
  447. throw new ExceptionInSylar("It's impossible to send e-mail to nobody!", 10020);
  448. }else{
  449. $header .= "To: ".$this->prepareAddressList($this->getSend_To())."\r\n";
  450. }
  451.  
  452. // blocking problem
  453. if(is_null($this->getFrom())){
  454. throw new ExceptionInSylar("It's impossible to send e-mail without Sender address specified", 10021);
  455. }else{
  456. $header .= "From: {$this->getFrom()}\r\n";
  457. }
  458.  
  459. // optional information
  460. if(!is_null($this->getReplyTo())){
  461. $header .= "Reply-To: {$this->getReplyTo()}\r\n";
  462. }
  463. // optional information
  464. if(!$this->isEmpty($this->getSend_CC())){
  465. $header .= "Cc: ".$this->prepareAddressList($this->getSend_CC())."\r\n";
  466. }
  467. // optional information
  468. if(!$this->isEmpty($this->getSend_BCC())){
  469. $header .= "Bcc: ".$this->prepareAddressList($this->getSend_BCC())."\r\n";
  470. }
  471. // CharacterSet
  472. if(is_null($sCharSet)){
  473. $sCharSet = Sylar_ConfigBox::getDefaultCharset();
  474. }
  475. $header .= "MIME-Version: 1.0\r\n".
  476. "Content-type: text/html; charset={$sCharSet}\r\n";
  477. return $header;
  478. }catch (ExceptionInSylar $ex){
  479. throw $ex;
  480. return null;
  481. }
  482. }
  483. /**
  484. * Split array in address list
  485. * Split the array in a string that contains all email address using the e-mail standard.
  486. * For example:
  487. * array(
  488. * "Mark Green" => "m.green@exampmail.com",
  489. * "Mark Black" => "m.black@exampmail.com"
  490. * )
  491. *
  492. * become a string as:
  493. * "Mark Green <m.green@exampmail.com>, Mark Black <m.black@exampmail.com>"
  494. *
  495. * @param array $aAddressList
  496. * @return string
  497. */
  498. private function prepareAddressList($aAddressList){
  499. try{
  500. if(!$this->checkAddressList($aAddressList) || $this->isEmpty($aAddressList)){
  501. // List is not OK! Then return null
  502. throw new ExceptionInSylar("Email address list is not OK! ", 10017);
  503. }
  504. $fFirst = true;
  505. $emailList = "";
  506. foreach ($aAddressList as $name=> $email) {
  507. if(!$fFirst){
  508. $emailList .=", ";
  509. }else{
  510. $fFirst = false;
  511. }
  512. $emailList .= "{$name} <{$email}>";
  513. }
  514. return $emailList;
  515.  
  516. }catch (ExceptionInSylar $ex){
  517. throw $ex;
  518. return null;
  519. }
  520. }
  521. /**
  522. * Controls every single email address in the list
  523. *
  524. * @param array $aAddressList
  525. * @param boolean $fVerifyEmailAddress
  526. * @return boolean
  527. */
  528. private function checkAddresses($aAddressList, $fVerifyEmailAddress=false){
  529. try{
  530. if(!$this->checkAddressList($aAddressList)){
  531. throw new ExceptionInSylar("Provided array of email addresses is inconsistent ", 10016);
  532. }
  533. foreach ($aAddressList as $nameAddr => $emailAddr) {
  534. // first elementary controls on email: a@ab.en minimum 7 characters...
  535. if(is_null($nameAddr) || is_null($emailAddr) || strlen($emailAddr)<6){
  536. throw new ExceptionInSylar("Name or email address inconsistent! Name: {$nameAddr} Email: {$emailAddr}", 10015);
  537. }
  538. if($fVerifyEmailAddress){
  539. // Verify address - Call the method to verify email address
  540. if( !$this->validateAddress($emailAddr) ){
  541. throw new ExceptionInSylar("Email address not valid! email: {$emailAddr}", 10022);
  542. }
  543. }
  544. }
  545. return true;
  546. }catch (ExceptionInSylar $ex){
  547. throw $ex;
  548. return false;
  549. }
  550. }
  551. /**
  552. * Controls the address list array
  553. *
  554. * @param array $aAddressList
  555. * @return boolean
  556. */
  557. private function checkAddressList($aAddressList){
  558. try{
  559. if(is_null($aAddressList)){
  560. throw new ExceptionInSylar("Address list array is NULL", 10018);
  561. }
  562. if(!is_array($aAddressList)){
  563. throw new ExceptionInSylar("Address list array is not an array", 10019);
  564. }
  565. return true;
  566. }catch (ExceptionInSylar $ex){
  567. throw $ex;
  568. return false;
  569. }
  570. }
  571. /**
  572. * Verify if address list is empty. Return true if is empty, false otherwise
  573. *
  574. * @param array $aAddressList
  575. * @return boolean
  576. */
  577. private function isEmpty($aAddressList){
  578. try{
  579. if(!$this->checkAddressList($aAddressList)){
  580. throw new ExceptionInSylar("Provided array of email addresses is inconsistent ", 10016);
  581. }
  582. if( $this->countAddresses($aAddressList)>0 ){
  583. return false;
  584. }else{
  585. return true;
  586. }
  587. }catch (ExceptionInSylar $ex){
  588. throw $ex;
  589. return false;
  590. }
  591. }
  592. /**
  593. * count and return the number of email address in the list
  594. * return a negative value on error.
  595. *
  596. * @param array $aAddressList
  597. * @return int
  598. */
  599. private function countAddresses($aAddressList){
  600. try{
  601. if(!$this->checkAddressList($aAddressList)){
  602. throw new ExceptionInSylar("Provided array of email addresses is inconsistent ", 10016);
  603. }
  604. // return the lenght
  605. return count($aAddressList);
  606. }catch (ExceptionInSylar $ex){
  607. throw $ex;
  608. return -1;
  609. }
  610. }
  611. }
  612. ?>

Documentation generated on Thu, 24 Apr 2008 16:14:18 +0200 by phpDocumentor 1.3.0RC3