<?php
/**
 * @file
 * HTML Mail using PHPMailer. Messaging method plug-in.
 */

// Include messaging mail library
require_once drupal_get_path('module', 'messaging') . '/messaging.mail.inc';

/**
 * Implementation of hook_menu().
 */
function messaging_phpmailer_menu() {
  $items = array();
  
  $items['admin/messaging/settings/method/phpmailer'] = array(
    'title' => 'PHPMailer',
    'description' => 'Configure PHPMailer.',
    'page callback' => 'drupal_get_form',
    'page arguments' => array('messaging_phpmailer_settings_form'),
    'access arguments' => array('administer messaging'),
    'type' => MENU_LOCAL_TASK,   
  );

  return $items;
}

/**
 * Implementation of hook_messaging
 */
function messaging_phpmailer_messaging($op = 'info') {
  switch($op) {
    case 'send methods':
      $info['phpmailer'] = array(
        'title' => 'PHPMailer',
        'name' => t('HTML Mail'),
        'group' => 'mail',
        'destination' => 'mail',
        'send callback' => 'messaging_phpmailer_send_msg',
        'type' => MESSAGING_TYPE_SEND,
        'glue' => "<br>", // don't use <br/> nor <br /> for maximum HTML email client compatibility
        'footer' => "<br><br>--",
        'description' => t('Send HTML e-mails using PHPMailer'),
      );
      return $info;
  }
}

/**
 * Settings form callback
 */
function messaging_phpmailer_settings_form($form_state) {
  $form['messaging_phpmailer_smtp_server'] = array(
    '#title' => t('SMTP server'),
    '#type' => 'textfield',
    '#default_value' => variable_get('messaging_phpmailer_smtp_server', ini_get('SMTP')),
  );
  $form['messaging_phpmailer_auth'] = array(
    '#type'        => 'fieldset',
    '#title'       => t('SMTP Authentication'),
    '#description' => t('Leave blank if your SMTP server does not require authentication.'),
  );
  $form['messaging_phpmailer_auth']['messaging_phpmailer_smtp_username'] = array(
    '#type'          => 'textfield',
    '#title'         => t('Username'),
    '#default_value' => variable_get('messaging_phpmailer_smtp_username', ''),
    '#description'   => t('SMTP Username.'),
  );
  $form['messaging_phpmailer_auth']['messaging_phpmailer_smtp_password'] = array(
    '#type'          => 'textfield',
    '#title'         => t('Password'),
    '#default_value' => variable_get('messaging_phpmailer_smtp_password', ''),
    '#description'   => t('SMTP password.'),
  );
  $form['messaging_phpmailer_attach'] = array(
      '#title' => t('Include attachments'),
      '#type' => 'checkbox',
      '#default_value' => variable_get('messaging_phpmailer_attach', 0),
      '#description' => t('If enabled, attachments will be included with outgoing messages.')
  );  
  $form['messaging_phpmailer_debug'] = array(
      '#title' => t('Debug mode'),
      '#type' => 'radios',
      '#options' => array(t('Disabled'), t('Enabled')),
      '#default_value' => variable_get('messaging_phpmailer_debug', 0),
      '#description' => t('If enabled, PHPMailer debugging will be activated and all messages logged to watchdog.')
  );
  return system_settings_form($form);
}

/**
 * Implementation of hook_theme()
 */
function messaging_phpmailer_theme() {
  return array(
    'messaging_phpmailer' => array(
      'arguments' => array('mail' => NULL),
    ),
  );
}

/**
 * Send mail message to user account. Supports bulk sending
 *
 * @param $destination
 *   Single email address
 * @param $message
 *   Message array
 */
function messaging_phpmailer_send_msg($destination, $message, $params = array()) {
  $mail = messaging_mail_prepare($destination, $message, $params);
  
  return messaging_phpmailer_drupal_mail($mail);
}

/**
 * Load the PHPMailer library.
 *
 * @return
 *   TRUE if the PHPMailer library is loaded, FALSE otherwise.
 */
function messaging_phpmailer_load_library() {
  if (!class_exists('PHPMailer')) {
    // First, try using libraries module.
    if (module_exists('libraries')) {
      // Let's see if PHPMailer is really available from libraries.
      $phpmailer_library = './'. libraries_get_path('phpmailer') .'/class.phpmailer.php';
      if (file_exists($phpmailer_library)) {
        include_once $phpmailer_library;
      }
    }
    // If PHPMailer is not already loaded, then try from module subdirectory.
    if (!class_exists('PHPMailer')) {
      $phpmailer_library = './'. drupal_get_path('module', 'messaging_phpmailer') .'/PHPMailer/class.phpmailer.php';
      if (file_exists($phpmailer_library)) {
        include_once $phpmailer_library;
      }
    }
  }
  // Tell the caller if PHPMailer class exists.
  return class_exists('PHPMailer');
}

/**
 * Send a message via PHPMailer.
 * This function mimics drupal_mail. We do not use drupal_mail instead because we want
 * to be able to send mail with both PHPMailer and MIMEMail.
 */
function messaging_phpmailer_drupal_mail($message) {
  if (!messaging_phpmailer_load_library()) {
    watchdog('messaging', 'Could not locate PHPMailer library.', array(), WATCHDOG_ERROR);
    return FALSE;
  }
  $mail = new PHPMailer();
  $mail->IsSMTP(); // telling the class to use SMTP
  $mail->CharSet = 'utf-8';
  $mail->ContentType = 'text/html';
  
    // Set the authentication settings.
  $username = variable_get('messaging_phpmailer_smtp_username', '');
  $password = variable_get('messaging_phpmailer_smtp_password', '');

  // If username and password are given, use SMTP authentication.
  if ($username && $password) {
    $mail->SMTPAuth = TRUE;
    $mail->Username = $username;
    $mail->Password = $password;
  }
  
  $host = variable_get('messaging_phpmailer_smtp_server', ini_get('SMTP'));
  if ($host) {
    $mail->Host = $host; // SMTP server
  }
  else {
    watchdog('messaging', 'SMTP server cannot be reached.', array(), WATCHDOG_ERROR);
    return FALSE;
  }

  // Theme the mail message
  list($subject, $body) = theme('messaging_phpmailer', $message);

  // Add some headers. Look for rfc2822 "From" formatting (ex: "name" <foo@bar.com>)
  $matches = array();
  preg_match('/["\']?(.*)["\']? <(.*)>/', $message['headers']['From'], $matches);
  if (!empty($matches[1])) {
    $from['name'] = $matches[1];
  }
  if (!empty($matches[2])) {
    $from['email'] = $matches[2];
  }
  $mail->From = !empty($from['email']) ? $from['email'] : $message['headers']['From'];
  $mail->FromName = !empty($from['name']) ? $from['name'] : '';
  $mail->AddAddress($message['to']);

  if(!empty($message['headers']['Message-ID'])) {
    $mail->MessageID = $message['headers']['Message-ID'];
  }
  if(!empty($message['headers']['Reply-To'])) {
    $mail->AddReplyTo($message['headers']['Reply-To']);
  }
  // Strip HTML out of $body for plaintext equivalent of HTML email.
  $mail->AltBody = drupal_html_to_text($body);

  // The subject has been already filtered by messaging module
  $mail->Subject = $subject;
  $mail->Body = str_replace("\r", '', $body);

  if(!empty($message['attachments']) && variable_get('messaging_phpmailer_attach', 0)){
    foreach($message['attachments'] as $attachment) {
      $mail->AddAttachment($attachment->filepath, $attachment->filename, 'base64', $attachment->filemime);
    }
  }
  
  // If enabled debug option, log everything...
  if (variable_get('messaging_phpmailer_debug', 0)) {
    $mail->SMTPDebug = TRUE;
    watchdog('messaging', 'PHPMailer debug message: '. $mail->Send() . ' - ' . $mail->ErrorInfo);    
  }
  else {
    return $mail->Send();
  }
}

/**
 * Default theme messaging_phpmailer
 */
function theme_messaging_phpmailer($mail) {
  return array($mail['subject'], $mail['body']);
}
