mirror of
https://github.com/fusionpbx/fusionpbx.git
synced 2025-12-30 17:13:49 +00:00
* remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove class_exists wrapper for class definitions * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove include statement of class file * remove closing tag * remove invalid method params * remove closing tag * remove closing tag * Update auto_loader to load each class file in the project Update the auto_loader class to use an include statement on each file in the project to load the class within the file. This will allow mismatched names within the file to be loaded and mapped according to the declaration instead of the filename. The class is then checked against the parsed classes from the PHP engine so that namespaces are available and mapped to the file they were declared in. An update was also made to the search algorithm used to find a file that was not already loaded by collapsing the array to have only valid matches to increase performance on a cache miss. Logging within the auto_loader has been moved to a function. Multiple files were modified to allow the include statement. When the class has the `if(class_exists())` statement, the auto_loader is called to check for the class. This caused an infinite loop scenario so all wrappers have been removed. The auto_loader will now break the loop by directly modifying the internal classes array instead of trying to restart with the 'reload_classes' method. - APCu is used to cache classes so any loading of the classes is done only once. To clear the APCu cache, restart php-fpm or call the auto_loader::clear_cache() function. - Cache file is used when APCu is not available. To clear the cache remove it from the tmp folder or call the auto_loader::clear_cache() function. - All classes must no longer have a class_exists wrapper to benefit from the performance boost. - Classes should not be directly included when the auto_loader is used. * remove include statement of class file * Update destinations.php
639 lines
21 KiB
PHP
639 lines
21 KiB
PHP
<?php
|
|
/*-
|
|
* Copyright (c) 2022 - 2023 Mark J Crane <markjcrane@fusionpbx.com>
|
|
*
|
|
* Redistribution and use in source and binary forms, with or without
|
|
* modification, are permitted provided that the following conditions
|
|
* are met:
|
|
* 1. Redistributions of source code must retain the above copyright
|
|
* notice, this list of conditions and the following disclaimer.
|
|
* 2. Redistributions in binary form must reproduce the above copyright
|
|
* notice, this list of conditions and the following disclaimer in the
|
|
* documentation and/or other materials provided with the distribution.
|
|
*
|
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS "AS IS" AND
|
|
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
|
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
|
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
|
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
|
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
|
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
|
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
|
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
|
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
|
* SUCH DAMAGE.
|
|
*/
|
|
|
|
/**
|
|
* email class
|
|
*
|
|
*/
|
|
class email {
|
|
|
|
/**
|
|
* declare the variables
|
|
*/
|
|
private $app_name;
|
|
private $app_uuid;
|
|
private $name;
|
|
|
|
public $domain_uuid;
|
|
public $method;
|
|
public $recipients;
|
|
public $subject;
|
|
public $body;
|
|
public $from_address;
|
|
public $from_name;
|
|
public $priority;
|
|
public $debug_level;
|
|
public $attachments;
|
|
public $read_confirmation;
|
|
public $error;
|
|
public $response;
|
|
private $settings;
|
|
|
|
/**
|
|
* called when the object is created
|
|
*/
|
|
public function __construct($params = []) {
|
|
//assign the variables
|
|
$this->app_name = 'email';
|
|
$this->name = 'email';
|
|
$this->app_uuid = '7a4fef67-5bf8-436a-ae25-7e3c03afcf96';
|
|
$this->priority = 0;
|
|
$this->debug_level = 3;
|
|
$this->read_confirmation = false;
|
|
|
|
//set the domain_uuid
|
|
$this->domain_uuid = $params['domain_uuid'] ?? $_SESSION['domain_uuid'] ?? '';
|
|
|
|
if (isset($params['settings'])) {
|
|
$this->settings = $params['settings'];
|
|
}
|
|
|
|
//set the database from the settings object if available
|
|
if ($this->settings instanceof settings && !isset($this->database)) {
|
|
$this->database = $this->settings->database();
|
|
}
|
|
|
|
//ensure we have a valid database object
|
|
if (!($this->database instanceof database)) {
|
|
$this->database = $params['database'] ?? database::new();
|
|
}
|
|
|
|
//ensure we have a valid settings object
|
|
if (!($this->settings) instanceof settings) {
|
|
$this->settings = new settings(['database' => $this->database, 'domain_uuid' => $this->domain_uuid]);
|
|
}
|
|
|
|
}
|
|
|
|
/**
|
|
* parse raw emails
|
|
*/
|
|
public function parse($message) {
|
|
//includes
|
|
require_once('resources/pop3/mime_parser.php');
|
|
require_once('resources/pop3/rfc822_addresses.php');
|
|
if (file_exists($_SERVER["PROJECT_ROOT"]."/app/emails/email_transcription.php")) {
|
|
require_once($_SERVER["PROJECT_ROOT"]."/app/emails/email_transcription.php");
|
|
}
|
|
|
|
//parse the email message
|
|
$mime = new mime_parser_class;
|
|
$mime->decode_bodies = 1;
|
|
$parameters = array(
|
|
//'File'=>$message_file,
|
|
|
|
// Read a message from a string instead of a file
|
|
'Data' => $message,
|
|
|
|
// Save the message body parts to a directory
|
|
// 'SaveBody' => '/tmp',
|
|
|
|
// Do not retrieve or save message body parts
|
|
// 'SkipBody' => 1,
|
|
);
|
|
$success = $mime->Decode($parameters, $decoded);
|
|
unset($parameters);
|
|
|
|
if (!$success) {
|
|
echo "MIME message decoding error: ".HtmlSpecialChars($mime->error)."\n";
|
|
}
|
|
else {
|
|
|
|
//get the headers
|
|
$this->headers = json_decode($decoded[0]["Headers"]["x-headers:"], true);
|
|
$this->subject = $decoded[0]["Headers"]["subject:"];
|
|
$this->from_name = $decoded[0]["ExtractedAddresses"]["from:"][0]["name"];
|
|
$this->from_address = $decoded[0]["ExtractedAddresses"]["from:"][0]["address"];
|
|
$this->reply_to = $decoded[0]["Headers"]["reply-to:"];
|
|
$this->recipients = $decoded[0]["ExtractedAddresses"]["to:"];
|
|
$this->date = $decoded[0]["Headers"]["date:"];
|
|
|
|
//debug information
|
|
//view_array($decoded[0]);
|
|
//view_array($this);
|
|
//view_array($this->recipients);
|
|
|
|
//get the body
|
|
$this->body = ''; //$parts_array["Parts"][0]["Headers"]["content-type:"];
|
|
|
|
//get the body
|
|
$this->body = '';
|
|
$this->content_type = $decoded[0]['Headers']['content-type:'];
|
|
if (substr($this->content_type, 0, 15) == "multipart/mixed" || substr($this->content_type, 0, 21) == "multipart/alternative") {
|
|
foreach ($decoded[0]["Parts"] as $row) {
|
|
$body_content_type = $row["Headers"]["content-type:"];
|
|
if (substr($body_content_type, 0, 9) == "text/html") {
|
|
$this->body = $row["Body"];
|
|
}
|
|
if (substr($body_content_type, 0, 10) == "text/plain") {
|
|
$body_plain = $row["Body"];
|
|
$this->body = $body_plain;
|
|
}
|
|
}
|
|
}
|
|
else {
|
|
$content_type_array = explode(";", $content_type);
|
|
$this->body = $decoded[0]["Body"];
|
|
//if ($content_type_array[0] == "text/html" || $content_type_array[0] == "text/plain") {
|
|
// $body = $row["Body"];
|
|
//}
|
|
}
|
|
|
|
//get the attachments and add to the email
|
|
$x = 0;
|
|
foreach ($decoded[0]["Parts"] as $parts_array) {
|
|
//image/tiff;name="testfax.tif"
|
|
//text/plain; charset=ISO-8859-1; format=flowed
|
|
$content_type = $parts_array["Parts"][0]["Headers"]["content-type:"];
|
|
|
|
//base64, 7bit
|
|
$content_transfer_encoding = $parts_array["Parts"][0]["Headers"]["content-transfer-encoding:"];
|
|
|
|
//inline;filename="testfax.tif"
|
|
$content_disposition = $parts_array["Parts"][0]["Headers"]["content-disposition"];
|
|
|
|
//testfax.tif
|
|
$file = $parts_array["FileName"];
|
|
|
|
//inline
|
|
$filedisposition = $parts_array["FileDisposition"];
|
|
|
|
$body_part = $parts_array["BodyPart"];
|
|
$body_length = $parts_array["BodyLength"];
|
|
|
|
if (!empty($file)) {
|
|
//get the file information
|
|
$file_ext = pathinfo($file, PATHINFO_EXTENSION);
|
|
$file_name = substr($file, 0, (strlen($file) - strlen($file_ext))-1 );
|
|
$encoding = "base64"; //base64_decode
|
|
|
|
switch ($file_ext){
|
|
case "wav":
|
|
$mime_type = "audio/x-wav";
|
|
break;
|
|
case "mp3":
|
|
$mime_type = "audio/x-mp3";
|
|
break;
|
|
case "pdf":
|
|
$mime_type = "application/pdf";
|
|
break;
|
|
case "tif":
|
|
$mime_type = "image/tiff";
|
|
break;
|
|
case "tiff":
|
|
$mime_type = "image/tiff";
|
|
break;
|
|
default:
|
|
$mime_type = "binary/octet-stream";
|
|
break;
|
|
}
|
|
|
|
//add attachment(s)
|
|
$this->attachments[$x]['type'] = 'string';
|
|
$this->attachments[$x]['name'] = $file;
|
|
$this->attachments[$x]['value'] = $parts_array["Body"];
|
|
|
|
//increment the id
|
|
$x++;
|
|
}
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
/**
|
|
* send emails
|
|
*/
|
|
public function send() {
|
|
|
|
//set the send_method if not already set
|
|
if (!isset($this->method)) {
|
|
if ($this->settings->get('email_queue','enabled', true)) {
|
|
$this->method = 'queue';
|
|
}
|
|
else {
|
|
$this->method = 'direct';
|
|
}
|
|
}
|
|
|
|
//add the email to the queue
|
|
if ($this->method == 'queue') {
|
|
|
|
//add the email_queue_uuid
|
|
$email_queue_uuid = uuid();
|
|
|
|
//set the email from address and name
|
|
$email_from = $this->from_address;
|
|
if (!empty($this->from_name)) {
|
|
$email_from = $this->from_name.'<'.$email_from.'>';
|
|
}
|
|
|
|
//prepare the array
|
|
$array['email_queue'][0]['email_queue_uuid'] = $email_queue_uuid;
|
|
$array['email_queue'][0]['domain_uuid'] = $this->domain_uuid;
|
|
$array['email_queue'][0]['hostname'] = gethostname();
|
|
$array['email_queue'][0]['email_date'] = 'now()';
|
|
$array['email_queue'][0]['email_from'] = $email_from;
|
|
$array['email_queue'][0]['email_to'] = $this->recipients;
|
|
$array['email_queue'][0]['email_subject'] = $this->subject;
|
|
$array['email_queue'][0]['email_body'] = $this->body;
|
|
$array['email_queue'][0]['email_status'] = 'waiting';
|
|
$array['email_queue'][0]['email_retry_count'] = null;
|
|
//$array['email_queue'][0]['email_action_before'] = $email_action_before;
|
|
//$array['email_queue'][0]['email_action_after'] = $email_action_after;
|
|
|
|
//add email attachments
|
|
if (is_array($this->attachments) && sizeof($this->attachments) > 0) {
|
|
$y = 0;
|
|
foreach ($this->attachments as $attachment) {
|
|
//set the name of the file, determine extension
|
|
if ($attachment['path'] && $attachment['name']) {
|
|
if (file_exists($attachment['path'] && $attachment['name'])) {
|
|
$attachment['type'] = strtolower(pathinfo($attachment['name'], PATHINFO_EXTENSION));
|
|
}
|
|
}
|
|
else if ($attachment['value']) {
|
|
//old method
|
|
if (strlen($attachment['value']) < 255 && file_exists($attachment['value'])) {
|
|
$attachment['name'] = $attachment['name'] != '' ? $attachment['name'] : basename($attachment['value']);
|
|
$attachment['path'] = pathinfo($attachment['value'], PATHINFO_DIRNAME);
|
|
$attachment['type'] = strtolower(pathinfo($attachment['value'], PATHINFO_EXTENSION));
|
|
}
|
|
}
|
|
|
|
//set the mime type
|
|
switch ($attachment['type']) {
|
|
case "jpg":
|
|
case "jpeg":
|
|
$attachment['mime_type'] = 'image/jpeg';
|
|
break;
|
|
case "gif":
|
|
$attachment['mime_type'] = 'image/gif';
|
|
break;
|
|
case "png":
|
|
$attachment['mime_type'] = 'image/png';
|
|
break;
|
|
case "pdf":
|
|
$attachment['mime_type'] = 'application/pdf';
|
|
break;
|
|
case "tif":
|
|
case "tiff":
|
|
$attachment['mime_type'] = 'image/tiff';
|
|
break;
|
|
case "mp3":
|
|
$attachment['mime_type'] = 'audio/mpeg';
|
|
break;
|
|
case "wav":
|
|
$attachment['mime_type'] = 'audio/x-wav';
|
|
break;
|
|
case "opus":
|
|
$attachment['mime_type'] = 'audio/opus';
|
|
break;
|
|
case "ogg":
|
|
$attachment['mime_type'] = 'audio/ogg';
|
|
break;
|
|
default:
|
|
$attachment['mime_type'] = 'binary/octet-stream';
|
|
}
|
|
|
|
//add the attachments to the array
|
|
$array['email_queue_attachments'][$y]['email_queue_attachment_uuid'] = uuid();
|
|
$array['email_queue_attachments'][$y]['email_queue_uuid'] = $email_queue_uuid;
|
|
$array['email_queue_attachments'][$y]['domain_uuid'] = $this->domain_uuid;
|
|
$array['email_queue_attachments'][$y]['email_attachment_mime_type'] = $attachment['mime_type'];
|
|
$array['email_queue_attachments'][$y]['email_attachment_type'] = $attachment['type'];
|
|
$array['email_queue_attachments'][$y]['email_attachment_name'] = $attachment['name'];
|
|
$array['email_queue_attachments'][$y]['email_attachment_path'] = $attachment['path'];
|
|
$array['email_queue_attachments'][$y]['email_attachment_base64'] = $attachment['base64'];
|
|
$y++;
|
|
}
|
|
}
|
|
|
|
//add temporary permissions
|
|
$p = permissions::new();
|
|
$p->add("email_queue_add", 'temp');
|
|
$p->add("email_queue_attachment_add", 'temp');
|
|
|
|
//save the dialplan
|
|
$this->database->app_name = 'email';
|
|
$this->database->app_uuid = 'e24b5dab-3bcc-42e8-99c1-19b0c558c2d7';
|
|
$this->database->save($array);
|
|
//$dialplan_response = $this->database->message;
|
|
unset($array);
|
|
|
|
//remove temporary permissions
|
|
$p->delete("dialplan_add", 'temp');
|
|
$p->delete("dialplan_detail_add", 'temp');
|
|
|
|
//return a human readable response for debugging
|
|
if ($this->database->message['message'] == 'OK') {
|
|
return "Added to queue";
|
|
} else {
|
|
//return the SQL server message
|
|
return $this->database->message['message'];
|
|
}
|
|
}
|
|
|
|
//send the email directly
|
|
if ($this->method == 'direct') {
|
|
/*
|
|
RECIPIENTS NOTE:
|
|
|
|
Pass in a single email address...
|
|
|
|
user@domain.com
|
|
|
|
Pass in a comma or semi-colon delimited string of e-mail addresses...
|
|
|
|
user@domain.com,user2@domain2.com,user3@domain3.com
|
|
user@domain.com;user2@domain2.com;user3@domain3.com
|
|
|
|
Pass in a simple array of email addresses...
|
|
|
|
Array (
|
|
[0] => user@domain.com
|
|
[1] => user2@domain2.com
|
|
[2] => user3@domain3.com
|
|
)
|
|
|
|
Pass in a multi-dimentional array of addresses (delivery, address, name)...
|
|
|
|
Array (
|
|
[0] => Array (
|
|
[delivery] => to
|
|
[address] => user@domain.com
|
|
[name] => user 1
|
|
)
|
|
[1] => Array (
|
|
[delivery] => cc
|
|
[address] => user2@domain2.com
|
|
[name] => user 2
|
|
)
|
|
[2] => Array (
|
|
[delivery] => bcc
|
|
[address] => user3@domain3.com
|
|
[name] => user 3
|
|
)
|
|
)
|
|
|
|
ATTACHMENTS NOTE:
|
|
|
|
Pass in as many files as necessary in an array in the following format...
|
|
|
|
Array (
|
|
[0] => Array (
|
|
[mime_type] => image/jpeg (will be determined by file extension, if empty)
|
|
[name] => filename.ext
|
|
[path] => /source/folder/ (not used if base64 content)
|
|
[base64] => file content as base64 (not used if name and path set)
|
|
[cid] => content id of file attachment (only used if referencing attached files in body content)
|
|
)
|
|
[1] => Array (
|
|
...
|
|
)
|
|
)
|
|
|
|
ERROR RESPONSE:
|
|
|
|
Error messages are stored in the variable passed into $this->error BY REFERENCE
|
|
*/
|
|
|
|
try {
|
|
//include the phpmailer classes
|
|
include_once("resources/phpmailer/class.phpmailer.php");
|
|
include_once("resources/phpmailer/class.smtp.php");
|
|
|
|
//use the email default settings
|
|
if (!empty($this->settings->get('email','smtp_hostname'))) {
|
|
$smtp['hostname'] = $this->settings->get('email','smtp_hostname');
|
|
}
|
|
$smtp['host'] = (!empty($this->settings->get('email','smtp_host')) ? $this->settings->get('email','smtp_host'): '127.0.0.1');
|
|
if (!empty($this->settings->get('email','smtp_port'))) {
|
|
$smtp['port'] = (int)$this->settings->get('email','smtp_port');
|
|
}
|
|
else {
|
|
$smtp['port'] = 0;
|
|
}
|
|
$smtp['secure'] = $this->settings->get('email','smtp_secure');
|
|
$smtp['auth'] = $this->settings->get('email','smtp_auth');
|
|
$smtp['username'] = $this->settings->get('email','smtp_username');
|
|
$smtp['password'] = $this->settings->get('email','smtp_password');
|
|
$smtp['from'] = $this->settings->get('voicemail','smtp_from') ?? $this->settings->get('email','smtp_from');
|
|
$smtp['from_name'] = $this->settings->get('voicemail','smtp_from_name') ?? $this->settings->get('email','smtp_from_name');
|
|
$smtp['validate_certificate'] = $this->settings->get('email','smtp_validate_certificate', true);
|
|
$smtp['crypto_method'] = $this->settings->get('email','smtp_crypto_method') ?? null;
|
|
|
|
//override the domain-specific smtp server settings, if any
|
|
$sql = "select domain_setting_subcategory, domain_setting_value ";
|
|
$sql .= "from v_domain_settings ";
|
|
$sql .= "where domain_uuid = :domain_uuid ";
|
|
$sql .= "and (domain_setting_category = 'email' or domain_setting_category = 'voicemail') ";
|
|
$sql .= "and domain_setting_enabled = 'true' ";
|
|
$parameters['domain_uuid'] = $this->domain_uuid;
|
|
$result = $this->database->select($sql, $parameters, 'all');
|
|
if (is_array($result) && @sizeof($result) != 0) {
|
|
foreach ($result as $row) {
|
|
if ($row['domain_setting_value'] != '') {
|
|
$smtp[str_replace('smtp_','',$row["domain_setting_subcategory"])] = $row['domain_setting_value'];
|
|
}
|
|
}
|
|
}
|
|
unset($sql, $parameters, $result, $row);
|
|
|
|
//value adjustments
|
|
$smtp['auth'] = ($smtp['auth'] == "true") ? true : false;
|
|
$smtp['password'] = ($smtp['password'] != '') ? $smtp['password'] : null;
|
|
$smtp['secure'] = ($smtp['secure'] != "none") ? $smtp['secure'] : null;
|
|
$smtp['username'] = ($smtp['username'] != '') ? $smtp['username'] : null;
|
|
|
|
//create the email object and set general settings
|
|
$mail = new PHPMailer();
|
|
$mail->IsSMTP();
|
|
if (!empty($smtp['hostname'])) {
|
|
$mail->Hostname = $smtp['hostname'];
|
|
}
|
|
$mail->Host = $smtp['host'];
|
|
if (is_numeric($smtp['port'])) {
|
|
$mail->Port = $smtp['port'];
|
|
}
|
|
|
|
if ($smtp['auth'] == "true") {
|
|
$mail->SMTPAuth = true;
|
|
$mail->Username = $smtp['username'];
|
|
$mail->Password = $smtp['password'];
|
|
}
|
|
else {
|
|
$mail->SMTPAuth = false;
|
|
}
|
|
|
|
$smtp_secure = true;
|
|
if ($smtp['secure'] == "") {
|
|
$mail->SMTPSecure = 'none';
|
|
$mail->SMTPAutoTLS = false;
|
|
$smtp_secure = false;
|
|
}
|
|
elseif ($smtp['secure'] == "none") {
|
|
$mail->SMTPSecure = 'none';
|
|
$mail->SMTPAutoTLS = false;
|
|
$smtp_secure = false;
|
|
}
|
|
else {
|
|
$mail->SMTPSecure = $smtp['secure'];
|
|
}
|
|
|
|
if ($smtp_secure && isset($smtp['validate_certificate']) && !$smtp['validate_certificate']) {
|
|
//bypass certificate check e.g. for self-signed certificates
|
|
$smtp_options['ssl']['verify_peer'] = false;
|
|
$smtp_options['ssl']['verify_peer_name'] = false;
|
|
$smtp_options['ssl']['allow_self_signed'] = true;
|
|
}
|
|
|
|
//used to set the SSL version
|
|
if ($smtp_secure && isset($smtp['crypto_method'])) {
|
|
$smtp_options['ssl']['crypto_method'] = $smtp['crypto_method'];
|
|
}
|
|
|
|
//add SMTP Options if the array exists
|
|
if (is_array($smtp_options)) {
|
|
$mail->SMTPOptions = $smtp_options;
|
|
}
|
|
|
|
$this->from_address = ($this->from_address != '') ? $this->from_address : $smtp['from'];
|
|
$this->from_name = ($this->from_name != '') ? $this->from_name : $smtp['from_name'];
|
|
$mail->SetFrom($this->from_address, $this->from_name);
|
|
$mail->AddReplyTo($this->from_address, $this->from_name);
|
|
$mail->Subject = $this->subject;
|
|
$mail->MsgHTML($this->body);
|
|
$mail->Priority = $this->priority;
|
|
if ($this->read_confirmation) {
|
|
$mail->AddCustomHeader('X-Confirm-Reading-To: '.$this->from_address);
|
|
$mail->AddCustomHeader('Return-Receipt-To: '.$this->from_address);
|
|
$mail->AddCustomHeader('Disposition-Notification-To: '.$this->from_address);
|
|
}
|
|
if (is_numeric($this->debug_level) && $this->debug_level > 0) {
|
|
$mail->SMTPDebug = $this->debug_level;
|
|
}
|
|
$mail->Timeout = 20; //set the timeout (seconds)
|
|
$mail->SMTPKeepAlive = true; //don't close the connection between messages
|
|
|
|
//add the email recipients
|
|
$address_found = false;
|
|
if (!is_array($this->recipients)) { // must be a single or delimited recipient address(s)
|
|
$this->recipients = str_replace(' ', '', $this->recipients);
|
|
$this->recipients = str_replace(',', ';', $this->recipients);
|
|
$this->recipients = explode(';', $this->recipients); // convert to array of addresses
|
|
}
|
|
|
|
foreach ($this->recipients as $this->recipient) {
|
|
if (is_array($this->recipient)) { // check if each recipient has multiple fields
|
|
if ($this->recipient["address"] != '' && valid_email($this->recipient["address"])) { // check if valid address
|
|
switch ($this->recipient["delivery"]) {
|
|
case "cc" : $mail->AddCC($this->recipient["address"], ($this->recipient["name"]) ? $this->recipient["name"] : $this->recipient["address"]); break;
|
|
case "bcc" : $mail->AddBCC($this->recipient["address"], ($this->recipient["name"]) ? $this->recipient["name"] : $this->recipient["address"]); break;
|
|
default : $mail->AddAddress($this->recipient["address"], ($this->recipient["name"]) ? $this->recipient["name"] : $this->recipient["address"]);
|
|
}
|
|
$address_found = true;
|
|
}
|
|
}
|
|
else if ($this->recipient != '' && valid_email($this->recipient)) { // check if recipient value is simply (only) an address
|
|
$mail->AddAddress($this->recipient);
|
|
$address_found = true;
|
|
}
|
|
}
|
|
|
|
if (!$address_found) {
|
|
$this->error = "No valid e-mail address provided.";
|
|
return false;
|
|
}
|
|
|
|
//add email attachments
|
|
if (is_array($this->attachments) && sizeof($this->attachments) > 0) {
|
|
foreach ($this->attachments as $attachment) {
|
|
|
|
//add the attachments
|
|
if (file_exists($attachment['path'].'/'.$attachment['name'])) {
|
|
$mail->AddAttachment($attachment['path'].'/'.$attachment['name'], $attachment['name'], 'base64', $attachment['mime_type']);
|
|
}
|
|
else {
|
|
if ($attachment['base64']) {
|
|
if ($attachment['cid']) {
|
|
$mail->addStringEmbeddedImage(base64_decode($attachment['base64']), $attachment['cid'], $attachment['name'], 'base64', $attachment['mime_type']);
|
|
}
|
|
else {
|
|
$mail->AddStringAttachment(base64_decode($attachment['base64']), $attachment['name'], 'base64', $attachment['mime_type']);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
//save output to a buffer
|
|
ob_start();
|
|
|
|
//send the email
|
|
$mail_status = $mail->Send();
|
|
|
|
//get the output buffer
|
|
$this->response = ob_get_clean();
|
|
|
|
//send the email
|
|
if (!$mail_status) {
|
|
if (isset($mail->ErrorInfo) && !empty($mail->ErrorInfo)) {
|
|
$this->error = $mail->ErrorInfo;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
//cleanup the mail object
|
|
$mail->ClearAddresses();
|
|
$mail->SmtpClose();
|
|
unset($mail);
|
|
return true;
|
|
|
|
}
|
|
catch (Exception $e) {
|
|
$this->error = $mail->ErrorInfo;
|
|
return false;
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
}
|
|
|
|
|
|
/*
|
|
$email = new email;
|
|
$email->recipients = $recipients;
|
|
$email->subject = $email_subject;
|
|
$email->body = $email_body;
|
|
$email->from_address = $email_from_address;
|
|
$email->from_name = $email_from_name;
|
|
$email->attachments = $email_attachments;
|
|
$response = $mail->error;
|
|
$sent = $email->send();
|
|
*/
|