/** * Sends mail via SMTP using PhpSMTP (Author: * Chris Ryan). Returns bool. Returns false if there is a * bad MAIL FROM, RCPT, or DATA input. * @access private * @return bool */ function SmtpSend($header, $body) { include_once $this->PluginDir . "class.smtp.php"; $error = ""; $bad_rcpt = array(); $errorx = ''; if (!$this->SmtpConnect()) { return false; } if ($this->SMIME) { $header = ''; $body = $this->Body; } $smtp_from = $this->Sender == "" ? $this->From : $this->Sender; if (!$this->smtp->Mail($smtp_from)) { $error = $this->Lang("from_failed") . $smtp_from; $this->SetError($error); $this->smtp->Reset(); return false; } // Attempt to send attach all recipients $to_count = count($this->to); for ($i = 0; $i < $to_count; ++$i) { if (!$this->smtp->Recipient($this->to[$i][0])) { $bad_rcpt[] = $this->to[$i][0]; } } $cc_count = count($this->cc); for ($i = 0; $i < $cc_count; ++$i) { if (!$this->smtp->Recipient($this->cc[$i][0])) { $bad_rcpt[] = $this->cc[$i][0]; } } $bcc_count = count($this->bcc); for ($i = 0; $i < $bcc_count; ++$i) { if (!$this->smtp->Recipient($this->bcc[$i][0])) { $bad_rcpt[] = $this->bcc[$i][0]; } } if ($errorx != '') { $error = $errorx; $error = $this->Lang("recipients_failed") . ' ' . $errorx; $this->SetError($error); $this->smtp->Reset(); return false; } if (count($bad_rcpt) > 0) { //Postfix version 2.3.8-2 $smtp_code_error = substr($this->smtp->error['smtp_msg'], 0, 5); //Postfix version 2.1.5-9 $array_error = explode(":", $this->smtp->error['smtp_msg']); $bad_rcpt_count = count($bad_rcpt); for ($i = 0; $i < $bad_rcpt_count; ++$i) { if ($i != 0) { $error .= ", "; } $error .= $bad_rcpt[$i]; } if ($smtp_code_error == '5.7.1' || trim($array_error[2]) == 'Access denied') { $error = $this->Lang("not_allowed") . $error; } else { $error = $this->Lang("recipients_failed") . $error; } $this->SetError($error); $this->smtp->Reset(); return false; } // Vai verificar se deve cifrar a msg ...... if (count($this->Certs_crypt) > 0) { // Vai cifrar a msg antes de enviar ...... include_once "../security/classes/CertificadoB.php"; $teste1 = array(); $aux_cifra1 = $header . $body; // Início relocação dos headers // Esta relocação dos headers podem causar problemas. $match = 0; $pattern = '/^Disposition\\-Notification\\-To:.*\\n/m'; $match = preg_match($pattern, $aux_cifra1, $teste1); if (!empty($match)) { $aux_cifra1 = preg_replace($pattern, '', $aux_cifra1, 1); // retira o Disposition-Notification-To $match = 0; $teste2 = array(); $pattern = '/^MIME\\-Version:.*\\n/m'; $match = preg_match($pattern, $aux_cifra1, $teste2); $aux_cifra1 = preg_replace($pattern, $teste1[0] . $teste2[0], $aux_cifra1, 1); // Adiciona Disposition-Notification-To logo acima de MIME-Version } // Fim relocação dos headers // Vai partir em duas partes a msg. A primeira parte he a dos headers, e a segunda vai ser criptografada ... $pos_content_type = strpos($aux_cifra1, 'Content-Type:'); $pos_MIME_Version = strpos($aux_cifra1, 'MIME-Version: 1.0' . chr(0xd) . chr(0xa)); $valx_len = 19; if ($pos_MIME_Version === False) { $pos_MIME_Version = strpos($aux_cifra1, 'MIME-Version: 1.0' . chr(0xa)); $valx_len = 18; } if ($pos_MIME_Version >= $pos_content_type) { // nao deve enviar a msg..... O header MIME-Version com posicao invalida ...... $this->SetError('Formato dos headers da msg estao invalidos.(CD-17) - A'); $this->smtp->Reset(); return false; } $aux_cifra2 = array(); $aux_cifra2[] = substr($aux_cifra1, 0, $pos_MIME_Version - 1); $aux_cifra2[] = substr($aux_cifra1, $pos_MIME_Version + $valx_len); /* // este explode pode ser fonte de problemas ....... $aux_cifra2 = explode('MIME-Version: 1.0' . chr(0x0A), $aux_cifra1); // Pode ocorrer um erro se nao tiver o header MIME-Version ..... if(count($aux_cifra2) != 2 ) { $aux_cifra2 = explode('MIME-Version: 1.0' . chr(0x0D) . chr(0x0A), $aux_cifra1); if(count($aux_cifra2) != 2 ) { // nao deve enviar a msg..... nao tem o header MIME-Version ...... $this->SetError('Formato dos headers da msg estao invalidos.(CD-17) - ' . count($aux_cifra2)); $this->smtp->Reset(); return false; } } */ $certificado = new certificadoB(); $h = array(); $aux_body = $certificado->encriptar($aux_cifra2[1], $this->Certs_crypt, $h); if (!$aux_body) { $this->SetError('Ocorreu um erro. A msg nao foi enviada. (CD-18)'); $this->smtp->Reset(); return false; } // salvar sem cifra...... //$smtpSent = $this->smtp->Data($aux_cifra2[0] . $aux_body); // salva a msg sifrada. neste caso deve ter sido adicionado o certificado do autor da msg...... $header = $aux_cifra2[0]; $body = $aux_body; $smtpSent = $this->smtp->Data($header . $body); } else { $smtpSent = $this->smtp->Data($header . $body); } if (!$smtpSent) { $this->SetError($this->Lang("data_not_accepted") . ' ' . $this->smtp->error['error'] . ',' . $this->smtp->error['smtp_code'] . ',' . $this->smtp->error['smtp_msg']); $this->smtp->Reset(); return false; } if ($this->SMTPKeepAlive == true) { $this->smtp->Reset(); } else { $this->SmtpClose(); } if ($this->SaveMessageInFolder) { $username = $_SESSION['phpgw_info']['expressomail']['user']['userid']; $password = $_SESSION['phpgw_info']['expressomail']['user']['passwd']; $imap_server = $_SESSION['phpgw_info']['expressomail']['email_server']['imapServer']; $imap_port = $_SESSION['phpgw_info']['expressomail']['email_server']['imapPort']; if ($_SESSION['phpgw_info']['expressomail']['email_server']['imapTLSEncryption'] == 'yes') { $imap_options = '/tls/novalidate-cert'; } else { $imap_options = '/notls/novalidate-cert'; } $mbox_stream = imap_open("{" . $imap_server . ":" . $imap_port . $imap_options . "}" . $this->SaveMessageInFolder, $username, $password); ## # @AUTHOR Rodrigo Souza dos Santos # @DATE 2008/09/11 # @BRIEF Adding arbitrarily the BCC field. You may need to # check if this field already exists in the header. ## if (count($this->bcc) > 0) { $target = stripos($header, 'subject'); $header = substr($header, 0, $target) . $this->AddrAppend("Bcc", $this->bcc) . substr($header, $target); } $new_headerx = str_replace(chr(0xa), chr(0xd) . chr(0xa), $header); $new_bodyx = str_replace(chr(0xa), chr(0xd) . chr(0xa), $body); $new_header = str_replace(chr(0xd) . chr(0xd) . chr(0xa), chr(0xd) . chr(0xa), $new_headerx); $new_body = str_replace(chr(0xd) . chr(0xd) . chr(0xa), chr(0xd) . chr(0xa), $new_bodyx); if ($this->SaveMessageAsDraft) { imap_append($mbox_stream, "{" . $imap_server . ":" . $imap_port . "}" . $this->SaveMessageInFolder, $new_header . $new_body, "\\Seen \\Draft"); return true; } else { imap_append($mbox_stream, "{" . $imap_server . ":" . $imap_port . "}" . $this->SaveMessageInFolder, $new_header . $new_body, "\\Seen"); } } return $smtpSent; }
function send_mail($params) { require_once dirname(__FILE__) . '/../../services/class.servicelocator.php'; require_once dirname(__FILE__) . '/../../prototype/api/controller.php'; $mailService = ServiceLocator::getService('mail'); include_once "class.db_functions.inc.php"; $db = new db_functions(); $fromaddress = $params['input_from'] ? explode(';', $params['input_from']) : ""; $message_attachments_contents = isset($params['message_attachments_content']) ? $params['message_attachments_content'] : false; ## # @AUTHOR Rodrigo Souza dos Santos # @DATE 2008/09/17$fileName # @BRIEF Checks if the user has permission to send an email with the email address used. ## if (is_array($fromaddress) && $fromaddress[1] != $_SESSION['phpgw_info']['expressomail']['user']['email']) { $deny = true; foreach ($_SESSION['phpgw_info']['expressomail']['user']['shared_mailboxes'] as $key => $val) { if (array_key_exists('mail', $val) && $val['mail'][0] == $fromaddress[1]) { $deny = false and end($_SESSION['phpgw_info']['expressomail']['user']['shared_mailboxes']); } } if ($deny) { return "The server denied your request to send a mail, you cannot use this mail address."; } } $params['input_to'] = mb_convert_encoding($params['input_to'], "ISO-8859-1", "UTF-8, ISO-8859-1"); $params['input_cc'] = mb_convert_encoding($params['input_cc'], "ISO-8859-1", "UTF-8, ISO-8859-1"); $params['input_cco'] = mb_convert_encoding($params['input_cco'], "ISO-8859-1", "UTF-8, ISO-8859-1"); if (substr($params['input_to'], -1) == ',') { $params['input_to'] = substr($params['input_to'], 0, -1); } if (substr($params['input_cc'], -1) == ',') { $params['input_cc'] = substr($params['input_cc'], 0, -1); } if (substr($params['input_cco'], -1) == ',') { $params['input_cco'] = substr($params['input_cco'], 0, -1); } /*Wraps the text dividing the emails as from ">,"*/ $toaddress = $db->getAddrs(preg_split('/>,/', preg_replace('/>,/', '>>,', $params['input_to']))); $ccaddress = $db->getAddrs(preg_split('/>,/', preg_replace('/>,/', '>>,', $params['input_cc']))); $ccoaddress = $db->getAddrs(preg_split('/>,/', preg_replace('/>,/', '>>,', $params['input_cco']))); if ($toaddress["False"] || $ccaddress["False"] || $ccoaddress["False"]) { return $this->parse_error("Invalid Mail:", $toaddress["False"] ? $toaddress["False"] : ($ccaddress["False"] ? $ccaddress["False"] : $ccoaddress["False"])); } $toaddress = implode(',', $toaddress); $ccaddress = implode(',', $ccaddress); $ccoaddress = implode(',', $ccoaddress); if ($toaddress == "" && $ccaddress == "" && $ccoaddress == "") { return $this->parse_error("Invalid Mail:", $params['input_to'] ? $params['input_to'] : ($params['input_cc'] ? $params['input_cc'] : $params['input_cco'])); } $toaddress = preg_replace('/<\\s+/', '<', $toaddress); $toaddress = preg_replace('/\\s+>/', '>', $toaddress); $ccaddress = preg_replace('/<\\s+/', '<', $ccaddress); $ccaddress = preg_replace('/\\s+>/', '>', $ccaddress); $ccoaddress = preg_replace('/<\\s+/', '<', $ccoaddress); $ccoaddress = preg_replace('/\\s+>/', '>', $ccoaddress); $replytoaddress = $params['input_reply_to']; $subject = mb_convert_encoding($params['input_subject'], "ISO-8859-1", "UTF-8, ISO-8859-1"); $return_receipt = $params['input_return_receipt']; $is_important = $params['input_important_message']; $encrypt = $params['input_return_cripto']; $signed = $params['input_return_digital']; $params['attachments'] = mb_convert_encoding($params['attachments'], "UTF7-IMAP", "UTF-8, ISO-8859-1, UTF7-IMAP"); $message_attachments = $params['message_attachments']; $user_info = $_SESSION['phpgw_info']['expressomail']['user']; $sent_from = '"' . $user_info['fullname'] . '" <' . $user_info['email'] . '>'; if ($fromaddress) { $sent_from = $fromaddress; if (is_array($sent_from)) { $sent_from = '"' . $sent_from[0] . '" <' . $sent_from[1] . '>'; } } $loginfo = "|# Subject: {$subject} #|# FROM: {$sent_from} #|# TO: {$toaddress} #|# CC: {$ccaddress} #|# BCC: {$ccoaddress} #|# REPLY_TO: {$replytoaddress}"; // Valida numero Maximo de Destinatarios if ($_SESSION['phpgw_info']['expresso']['expressoMail']['expressoAdmin_maximum_recipients'] > 0) { $sendersNumber = count(explode(',', $params['input_to'])); if ($params['input_cc']) { $sendersNumber += count(explode(',', $params['input_cc'])); } if ($params['input_cco']) { $sendersNumber += count(explode(',', $params['input_cco'])); } $userMaxmimumSenders = $db->getMaximumRecipientsUser($this->username); if ($userMaxmimumSenders) { if ($sendersNumber > $userMaxmimumSenders) { return $this->functions->getLang('Number of recipients greater than allowed'); } } else { $ldap = new ldap_functions(); $groupsToUser = $ldap->get_user_groups($this->username); $groupMaxmimumSenders = $db->getMaximumRecipientsGroup($groupsToUser); if ($groupMaxmimumSenders > 0) { if ($sendersNumber > $groupMaxmimumSenders) { return $this->functions->getLang('Number of recipients greater than allowed'); } } else { if ($sendersNumber > $_SESSION['phpgw_info']['expresso']['expressoMail']['expressoAdmin_maximum_recipients']) { return $this->functions->getLang('Number of recipients greater than allowed'); } } } } //Fim Valida numero maximo de destinatarios //Valida envio de email para shared accounts if ($_SESSION['phpgw_info']['expresso']['expressoMail']['expressoMail_block_institutional_comunication'] == 'true') { $ldap = new ldap_functions(); $arrayF = explode(';', $params['input_from']); /* * Verifica se o remetente n?o ? uma conta compartilhada */ if (!$ldap->isSharedAccountByMail($arrayF[1])) { $groupsToUser = $ldap->get_user_groups($this->username); $sharedAccounts = $ldap->returnSharedsAccounts($toaddress, $ccaddress, $ccoaddress); /* * Pega o UID do remetente */ $uidFrom = $ldap->mail2uid($arrayF[1]); /* * Remove a conta compartilhada caso o uid do remetente exista na conta compartilhada */ foreach ($sharedAccounts as $key => $value) { if ($value) { $acl = $this->getaclfrombox($value); } if (array_key_exists($uidFrom, $acl)) { unset($sharedAccounts[$key]); } } /* * Caso ainda exista contas compartilhadas, verifica se existe alguma exce??o para estas contas */ if (count($sharedAccounts) > 0) { $accountsBlockeds = $db->validadeSharedAccounts($this->username, $groupsToUser, $sharedAccounts); } /* * Retorna as contas compartilhadas bloqueadas */ if (count($accountsBlockeds) > 0) { $return = ''; foreach ($accountsBlockeds as $accountBlocked) { $return .= $accountBlocked . ', '; } $return = substr($return, 0, -2); return $this->functions->getLang('you are blocked from sending mail to the following addresses') . ': ' . $return; } } } // Fim Valida envio de email para shared accounts // TODO - implementar tratamento SMIME no novo serviço de envio de emails e retirar o AND false abaixo if ($params['smime'] and false) { $body = $params['smime']; $mail->SMIME = true; // A MSG assinada deve ser testada neste ponto. // Testar o certificado e a integridade da msg.... include_once dirname(__FILE__) . "/../../security/classes/CertificadoB.php"; $erros_acumulados = ''; $certificado = new certificadoB(); $validade = $certificado->verificar($body); if (!$validade) { foreach ($certificado->erros_ssl as $linha_erro) { $erros_acumulados .= $linha_erro; } } else { // Testa o CERTIFICADO: se o CPF he o do usuario logado, se pode assinar msgs e se nao esta expirado... if ($certificado->apresentado) { if ($certificado->dados['EXPIRADO']) { $erros_acumulados .= 'Certificado expirado.'; } $this->cpf = isset($GLOBALS['phpgw_info']['server']['certificado_atributo_cpf']) && $GLOBALS['phpgw_info']['server']['certificado_atributo_cpf'] != '' ? $_SESSION['phpgw_info']['expressomail']['user'][$GLOBALS['phpgw_info']['server']['certificado_atributo_cpf']] : $this->username; if ($certificado->dados['CPF'] != $this->cpf) { $erros_acumulados .= ' CPF no certificado diferente do logado no expresso.'; } if (!($certificado->dados['KEYUSAGE']['digitalSignature'] && $certificado->dados['EXTKEYUSAGE']['emailProtection'])) { $erros_acumulados .= ' Certificado nao permite assinar mensagens.'; } } else { ${$erros_acumulados} .= 'Nao foi possivel usar o certificado para assinar a msg'; } } if (!$erros_acumulados == '') { return $erros_acumulados; } } else { //Compatibilização com Outlook, ao encaminhar a mensagem $body = mb_ereg_replace('<!--\\[', '<!-- [', base64_decode($params['body'])); $body = str_replace("<", "&yzwkx;", $body); //Alterar as Entities padrão das tags < > para compatibilizar com o Expresso $body = str_replace(">", "&xzwky;", $body); $body = str_replace("%nbsp;", " ", $body); //$body = preg_replace("/\n/"," ",$body); //$body = preg_replace("/\r/","" ,$body); $body = html_entity_decode($body, ENT_QUOTES, 'ISO-8859-1'); $body = str_replace("&yzwkx;", "<", $body); $body = str_replace("&xzwky;", ">", $body); } $attachments = $_FILES; $forwarding_attachments = $params['forwarding_attachments']; $local_attachments = $params['local_attachments']; //Test if must be saved in shared folder and change if necessary if ($fromaddress[2] == 'y') { //build shared folder path $newfolder = "user" . $this->imap_delimiter . $fromaddress[3] . $this->imap_delimiter . $this->imap_sentfolder; if ($this->folder_exists($newfolder)) { $has_new_folder = false; $folder = $newfolder; } else { $name_folder = $this->imap_sentfolder; $base_path = "user" . $this->imap_delimiter . $fromaddress[3]; $arr_new_folder['newp'] = $name_folder; $arr_new_folder['base_path'] = $base_path; $this->create_mailbox($arr_new_folder); $has_new_folder = true; $folder = $newfolder; } } else { $has_new_folder = false; $folder = $params['folder']; } $folder = mb_convert_encoding($folder, 'UTF7-IMAP', 'ISO-8859-1'); $folder = preg_replace('/INBOX[\\/.]/i', 'INBOX' . $this->imap_delimiter, $folder); $folder_name = $params['folder_name']; // TODO - tratar assinatura e remover o AND false if ($signed && !$params['smime'] and false) { $mail->Mailer = "smime"; $mail->SignedBody = true; } $from = $fromaddress ? '"' . $fromaddress[0] . '" <' . $fromaddress[1] . '>' : '"' . $_SESSION['phpgw_info']['expressomail']['user']['fullname'] . '" <' . $_SESSION['phpgw_info']['expressomail']['user']['email'] . '>'; $mailService->setFrom(mb_convert_encoding($from, "ISO-8859-1", "UTF-8, ISO-8859-1")); $mailService->addHeaderField('Reply-To', !!$replytoaddress ? $replytoaddress : $from); $bol = $this->add_recipients('to', $toaddress, $mailService); if (!$bol) { return $this->parse_error("Invalid Mail:", $toaddress); } $bol = $this->add_recipients('cc', $ccaddress, $mailService); if (!$bol) { return $this->parse_error("Invalid Mail:", $ccaddress); } $allow = $_SESSION['phpgw_info']['server']['expressomail']['allow_hidden_copy']; if ($allow) { //$mailService->addBcc($ccoaddress); $bol = $this->add_recipients('cco', $ccoaddress, $mailService); if (!$bol) { return $this->parse_error("Invalid Mail:", $ccoaddress); } } //Implementação para o In-Reply-To e References $msg_numb = $params['messageNum']; $msg_folder = $params['messageFolder']; $this->mbox = $this->open_mbox($msg_folder); $header = $this->get_header($msg_numb); $header_ = imap_fetchheader($this->mbox, $msg_numb, FT_UID); $pattern = '/^[ \\t]*Disposition-Notification-To:.*/mi'; if (preg_match($pattern, $header_, $fields)) { $return['DispositionNotificationTo'] = base64_encode(trim(str_ireplace('Disposition-Notification-To:', '', $fields[0]))); } $message_id = $header->message_id; $references = array(); if ($message_id != "") { $mailService->addHeaderField('In-Reply-To', $message_id); if (isset($header->references)) { array_push($references, $header->references); } array_push($references, $message_id); $mailService->addHeaderField('References', $references); } $mailService->setSubject($subject); $isHTML = isset($params['type']) && $params['type'] == 'html' ? true : false; // TODO - tratar mensagem criptografada e remover o AND false abaixo if ($encrypt && $signed && $params['smime'] || $encrypt && !$signed and false) { // a msg deve ser enviada cifrada... $email = $this->add_recipients_cert($toaddress . ',' . $ccaddress . ',' . $ccoaddress); $email = explode(",", $email); // Deve ser testado se foram obtidos os certificados de todos os destinatarios. // Deve ser verificado um numero limite de destinatarios. // Deve ser verificado se os certificados sao validos. // Se uma das verificacoes falhar, nao enviar o e-mail e avisar o usuario. // O array $mail->Certs_crypt soh deve ser preenchido se os certificados passarem nas verificacoes. $numero_maximo = $_SESSION['phpgw_info']['user']['preferences']['expressoMail']['num_max_certs_to_cipher']; // Este valor dever ser configurado pelo administrador do site .... $erros_acumulados = ""; $aux_mails = array(); $mail_list = array(); if (count($email) > $numero_maximo) { $erros_acumulados .= "Excedido o numero maximo (" . $numero_maximo . ") de destinatarios para uma msg cifrada...." . chr(0xa); return $erros_acumulados; } // adiciona o email do remetente. eh para cifrar a msg para ele tambem. Assim vai poder visualizar a msg na pasta enviados.. $email[] = $_SESSION['phpgw_info']['expressomail']['user']['email']; foreach ($email as $item) { $certificate = $db->get_certificate(strtolower($item)); if (!$certificate) { $erros_acumulados .= "Chamada com parametro invalido. e-Mail nao pode ser vazio." . chr(0xa); return $erros_acumulados; } if (array_key_exists("dberr1", $certificate)) { $erros_acumulados .= "Ocorreu um erro quando pesquisava certificados dos destinatarios para cifrar a msg." . chr(0xa); return $erros_acumulados; } if (array_key_exists("dberr2", $certificate)) { $erros_acumulados .= $item . ' : Nao pode cifrar a msg. Certificado nao localizado.' . chr(0xa); //continue; } /* Retirado este teste para evitar mensagem de erro duplicada. if (!array_key_exists("certs", $certificate)) { $erros_acumulados .= $item . ' : Nao pode cifrar a msg. Certificado nao localizado.' . chr(0x0A); continue; } */ include_once dirname(__FILE__) . "/../../security/classes/CertificadoB.php"; foreach ($certificate['certs'] as $registro) { $c1 = new certificadoB(); $c1->certificado($registro['chave_publica']); if ($c1->apresentado) { $c2 = new Verifica_Certificado($c1->dados, $registro['chave_publica']); if (!$c1->dados['EXPIRADO'] && !$c2->revogado && $c2->status) { $aux_mails[] = $registro['chave_publica']; $mail_list[] = strtolower($item); } else { if ($c1->dados['EXPIRADO'] || $c2->revogado) { $db->update_certificate($c1->dados['SERIALNUMBER'], $c1->dados['EMAIL'], $c1->dados['AUTHORITYKEYIDENTIFIER'], $c1->dados['EXPIRADO'], $c2->revogado); } $erros_acumulados .= $item . ': ' . $c2->msgerro . chr(0xa); foreach ($c2->erros_ssl as $linha) { $erros_acumulados .= $linha . chr(0xa); } $erros_acumulados .= 'Emissor: ' . $c1->dados['EMISSOR'] . chr(0xa); $erros_acumulados .= $c1->dados['CRLDISTRIBUTIONPOINTS'] . chr(0xa); } } else { $erros_acumulados .= $item . ' : Nao pode cifrar a msg. Certificado invalido.' . chr(0xa); } } if (!in_array(strtolower($item), $mail_list) && !empty($erros_acumulados)) { return $erros_acumulados; } } $mail->Certs_crypt = $aux_mails; } $attachment = json_decode($params['attachments'], TRUE); $message_size_total = 0; // se possui anexos, inserir informação no log if (count($attachment) > 0) { $loginfo .= "#|# ATTACH: "; } foreach ($attachment as &$value) { if ((int) $value > 0) { $att = Controller::read(array('id' => $value, 'concept' => 'mailAttachment')); if ($att['disposition'] == 'embedded' && $isHTML) { $body = str_replace('"../prototype/getArchive.php?mailAttachment=' . $att['id'] . '"', '"' . mb_convert_encoding($att['name'], 'ISO-8859-1', 'UTF-8,ISO-8859-1') . '"', $body); $mailService->addStringImage(base64_decode($att['source']), $att['type'], mb_convert_encoding($att['name'], 'ISO-8859-1', 'UTF-8,ISO-8859-1')); $loginfo .= "[" . $att['name'] . ":" . $att['size'] . "]"; } else { $mailService->addStringAttachment(base64_decode($att['source']), mb_convert_encoding($att['name'], 'ISO-8859-1', 'UTF-8,ISO-8859-1'), $att['type'], 'base64', isset($att['disposition']) ? $att['disposition'] : 'attachment'); $loginfo .= "[" . $att['name'] . ":" . $att['size'] . "]"; } $message_size_total += $att['size']; unset($att); } else { $value = json_decode($value, true); if ($value["folder"] == "archiver") { $value['folder'] = "INBOX/Trash"; } switch ($value['type']) { case 'imapPart': $att = $this->getForwardingAttachment(mb_convert_encoding($value['folder'], 'ISO-8859-1', 'UTF7-IMAP'), $value['uid'], $value['part']); if (strstr($body, 'src="./inc/get_archive.php?msgFolder=' . $value['folder'] . '&msgNumber=' . $value['uid'] . '&indexPart=' . $value['part'] . '"') !== false) { $body = str_ireplace('src="./inc/get_archive.php?msgFolder=' . $value['folder'] . '&msgNumber=' . $value['uid'] . '&indexPart=' . $value['part'] . '"', 'src="' . $att['name'] . '"', $body); $mailService->addStringImage($att['source'], $att['type'], mb_convert_encoding($att['name'], 'ISO-8859-1', 'UTF-8,ISO-8859-1')); } else { $mailService->addStringAttachment($att['source'], mb_convert_encoding($att['name'], 'ISO-8859-1', 'UTF-8,ISO-8859-1'), $att['type'], 'base64', isset($att['disposition']) ? $att['disposition'] : 'attachment'); $loginfo .= "[" . $att['name'] . ":" . $att['fsize'] . "]"; } $message_size_total += $att['fsize']; //Adiciona o tamanho do anexo a variavel que controlao tamanho da msg. unset($att); break; case 'imapMSG': $mbox_stream = $this->open_mbox(mb_convert_encoding($value['folder'], 'ISO-8859-1', 'UTF7-IMAP')); $rawmsg = $this->getRawHeader($value['uid']) . "\r\n\r\n" . $this->getRawBody($value['uid']); $mailService->addStringAttachment($rawmsg, mb_convert_encoding(base64_decode($value['name']), 'ISO-8859-1', 'UTF-8,ISO-8859-1'), 'message/rfc822', '7bit', 'attachment'); /*envia o anexo para o email*/ $message_size_total += mb_strlen($rawmsg); //Adiciona o tamanho do anexo a variavel que controlao tamanho da msg. unset($rawmsg); //TODO: tem como fazer log deste tipo de anexo? break; default: break; } } } $message_size_total += strlen($params['body']); /* Tamanho do corpo da mensagem. */ //////////////////////////////////////////////////////////////////////////////////////////////////// /** * Faz a validação pelo tamanho máximo de mensagem permitido para o usuário. Se o usuário não estiver em nenhuma regra, usa o tamanho padrão. */ $default_max_size_rule = $db->get_default_max_size_rule(); if (!$default_max_size_rule) { $default_max_size_rule = str_replace("M", "", ini_get('upload_max_filesize')) * 1024 * 1024; /* hack para não bloquear o envio de email quando não for configurado um tamanho padrão */ } else { foreach ($default_max_size_rule as $i => $value) { $default_max_size_rule = $value['config_value']; } } $default_max_size_rule = $default_max_size_rule * 1024 * 1024; /* Tamanho da regra padrão, em bytes */ $id_user = $_SESSION['phpgw_info']['expressomail']['user']['userid']; $ldap = new ldap_functions(); $groups_user = $ldap->get_user_groups($id_user); $size_rule_by_group = array(); foreach ($groups_user as $k => $value_) { $rule_in_group = $db->get_rule_by_user_in_groups($k); if ($rule_in_group != "") { array_push($size_rule_by_group, $rule_in_group); } } $n_rule_groups = 0; $maior_valor_regra_grupo = 0; foreach ($size_rule_by_group as $i => $value) { if (is_array($value[0])) { ++$n_rule_groups; if ($value[0]['email_max_recipient'] > $maior_valor_regra_grupo) { $maior_valor_regra_grupo = $value[0]['email_max_recipient']; } } } if ($default_max_size_rule) { $size_rule = $db->get_rule_by_user($_SESSION['phpgw_info']['expressomail']['user']['userid']); if (!$size_rule && $n_rule_groups == 0) { if ($message_size_total > $default_max_size_rule) { return $this->functions->getLang("Message size greateruler than allowed (Default rule)") . " (" . $default_max_size_rule / 1024 / 1024 . " Mb)"; } } else { if (count($size_rule) > 0) { $regra_mais_permissiva = 0; foreach ($size_rule as $i => $value) { if ($regra_mais_permissiva < $value['email_max_recipient']) { $regra_mais_permissiva = $value['email_max_recipient']; } } $regra_mais_permissiva = $regra_mais_permissiva * 1024 * 1024; if ($message_size_total > $regra_mais_permissiva) { return $this->functions->getLang("Message size greater than allowed (Rule By User)"); } } else { $maior_valor_regra_grupo = $maior_valor_regra_grupo * 1024 * 1024; if ($message_size_total > $maior_valor_regra_grupo) { return $this->functions->getLang("Message size greater than allowed (Rule By Group)"); } } } } /** * Fim da validação do tamanho da regra do tamanho de mensagem. */ //////////////////////////////////////////////////////////////////////////////////////////////////// if ($isHTML) { $this->rfc2397ToEmbeddedAttachment($mailService, $body); $defaultStyle = ''; if (isset($_SESSION['phpgw_info']['user']['preferences']['expressoMail']['font_family_editor']) && $_SESSION['phpgw_info']['user']['preferences']['expressoMail']['font_family_editor']) { $defaultStyle .= ' font-family:' . $_SESSION['phpgw_info']['user']['preferences']['expressoMail']['font_family_editor'] . ';'; } if (isset($_SESSION['phpgw_info']['user']['preferences']['expressoMail']['font_size_editor']) && $_SESSION['phpgw_info']['user']['preferences']['expressoMail']['font_size_editor']) { $defaultStyle .= ' font-size:' . $_SESSION['phpgw_info']['user']['preferences']['expressoMail']['font_size_editor'] . ';'; } $body = '<span class="' . $defaultStyle . '">' . $body . '</span>'; $mailService->setBodyHtml($body); } else { $mailService->setBodyText(mb_convert_encoding($body, 'ISO-8859-1', 'UTF-8,ISO-8859-1')); } $mailService->addHeaderField('Message-ID', "<" . md5(uniqid(time())) . "@" . $_SERVER['SERVER_NAME'] . ">\n"); if ($is_important) { $mailService->addHeaderField('Importance', 'High'); } if ($return_receipt) { $mailService->addHeaderField('Disposition-Notification-To', $_SESSION['phpgw_info']['expressomail']['user']['email']); } $mailService->addHeaderField('Date', date("r")); if ($folder != 'null') { $mbox_stream = $this->open_mbox($folder); @imap_append($mbox_stream, "{" . $this->imap_server . ":" . $this->imap_port . "}" . $folder, $mailService->getMessage(), "\\Seen"); } $sent = $mailService->send(); if ($sent !== true) { return $this->parse_error($sent); } else { if ($signed && !$params['smime']) { return $sent; } if ($_SESSION['phpgw_info']['server']['expressomail']['expressoMail_enable_log_messages'] == "True") { $userid = $_SESSION['phpgw_info']['expressomail']['user']['userid']; $userip = $_SESSION['phpgw_info']['expressomail']['user']['session_ip']; $now = date("d/m/y H:i:s"); $addrs = $toaddress . $ccaddress . $ccoaddress; $sent = trim($sent); error_log("{$now} - {$userip} - {$sent} [{$subject}] - {$userid} => {$addrs}\r\n", 3, "/home/expressolivre/mail_senders.log"); } if ($params['uids_save']) { $this->delete_msgs(array('folder' => $params['save_folder'], 'msgs_number' => $params['uids_save'])); } //return array("success" => true, "folder" => $folder_list); Logger::info('expressomail', 'sendmsg', $loginfo); return array("success" => true, "load" => $has_new_folder); } }