From 63d6e6dfc35e6d82c4a64f37c408794c163becd4 Mon Sep 17 00:00:00 2001 From: thomascube <thomas@roundcube.net> Date: Wed, 28 Sep 2011 15:16:41 -0400 Subject: [PATCH] Bump versions to 0.6 stable --- program/steps/mail/compose.inc | 219 +++++++++++++++++++++++++++++++++++++----------------- 1 files changed, 149 insertions(+), 70 deletions(-) diff --git a/program/steps/mail/compose.inc b/program/steps/mail/compose.inc index 531e698..5a1f564 100644 --- a/program/steps/mail/compose.inc +++ b/program/steps/mail/compose.inc @@ -29,7 +29,7 @@ $MESSAGE = NULL; $COMPOSE_ID = get_input_value('_id', RCUBE_INPUT_GET); -$_SESSION['compose'] = $_SESSION['compose_data'][$COMPOSE_ID]; +$_SESSION['compose'] = $_SESSION['compose_data_'.$COMPOSE_ID]; // Nothing below is called during message composition, only at "new/forward/reply/draft" initialization or // if a compose-ID is given (i.e. when the compose step is opened in a new window/tab). @@ -39,14 +39,14 @@ if ($COMPOSE_ID) raise_error(array('code' => 500, 'type' => 'php', 'file' => __FILE__, 'line' => __LINE__, - 'message' => "Invalid session"), true, true); + 'message' => "Invalid compose ID"), true, true); $_SESSION['compose'] = array( 'id' => uniqid(mt_rand()), 'param' => request2param(RCUBE_INPUT_GET), 'mailbox' => $IMAP->get_mailbox_name(), ); - + // process values like "mailto:foo@bar.com?subject=new+message&cc=another" if ($_SESSION['compose']['param']['to']) { // #1486037: remove "mailto:" prefix @@ -59,10 +59,10 @@ $_SESSION['compose']['param'][$f] = $val; } } - + // select folder where to save the sent message $_SESSION['compose']['param']['sent_mbox'] = $RCMAIL->config->get('sent_mbox'); - + // pipe compose parameters thru plugins $plugin = $RCMAIL->plugins->exec_hook('message_compose', $_SESSION['compose']); $_SESSION['compose']['param'] = array_merge($_SESSION['compose']['param'], $plugin['param']); @@ -84,12 +84,12 @@ 'path' => $attach, ); } - + // save attachment if valid if (($attachment['data'] && $attachment['name']) || ($attachment['path'] && file_exists($attachment['path']))) { $attachment = rcmail::get_instance()->plugins->exec_hook('attachment_save', $attachment); } - + if ($attachment['status'] && !$attachment['abort']) { unset($attachment['data'], $attachment['status'], $attachment['abort']); $_SESSION['compose']['attachments'][$attachment['id']] = $attachment; @@ -111,7 +111,7 @@ $OUTPUT->add_label('nosubject', 'nosenderwarning', 'norecipientwarning', 'nosubjectwarning', 'cancel', 'nobodywarning', 'notsentwarning', 'notuploadedwarning', 'savingmessage', 'sendingmessage', 'messagesaved', 'converting', 'editorwarning', 'searching', 'uploading', 'uploadingmany', - 'fileuploaderror', 'autocompletechars'); + 'fileuploaderror'); $OUTPUT->set_env('compose_id', $COMPOSE_ID); @@ -124,7 +124,6 @@ $OUTPUT->set_env('mailbox', $IMAP->get_mailbox_name()); $OUTPUT->set_env('sig_above', $CONFIG['sig_above']); $OUTPUT->set_env('top_posting', $CONFIG['top_posting']); -$OUTPUT->set_env('autocomplete_min_length', $CONFIG['autocomplete_min_length']); // get reference message and set compose mode if ($msg_uid = $_SESSION['compose']['param']['draft_uid']) { @@ -214,6 +213,9 @@ { $_SESSION['compose']['forward_uid'] = $msg_uid; $OUTPUT->set_env('compose_mode', 'forward'); + + if (!empty($_SESSION['compose']['param']['attachment'])) + $MESSAGE->forward_attachment = true; } } @@ -223,9 +225,11 @@ $MESSAGE->identities = $USER->list_identities(); if (count($MESSAGE->identities)) { - foreach ($MESSAGE->identities as $idx => $sql_arr) { - $email = mb_strtolower(rcube_idn_to_utf8($sql_arr['email'])); - $MESSAGE->identities[$idx]['email_ascii'] = $sql_arr['email']; + foreach ($MESSAGE->identities as $idx => $ident) { + $email = mb_strtolower(rcube_idn_to_utf8($ident['email'])); + + $MESSAGE->identities[$idx]['email_ascii'] = $ident['email']; + $MESSAGE->identities[$idx]['ident'] = format_email_recipient($ident['email'], $ident['name']); $MESSAGE->identities[$idx]['email'] = $email; } } @@ -238,65 +242,76 @@ $MESSAGE->compose['from'] = $_SESSION['compose']['param']['from']; } else if (count($MESSAGE->identities)) { - // extract all recipients of the reply-message $a_recipients = array(); - if ($compose_mode == RCUBE_COMPOSE_REPLY && is_object($MESSAGE->headers)) + $a_names = array(); + + // extract all recipients of the reply-message + if (is_object($MESSAGE->headers) && in_array($compose_mode, array(RCUBE_COMPOSE_REPLY, RCUBE_COMPOSE_FORWARD))) { $a_to = $IMAP->decode_address_list($MESSAGE->headers->to); foreach ($a_to as $addr) { - if (!empty($addr['mailto'])) + if (!empty($addr['mailto'])) { $a_recipients[] = strtolower($addr['mailto']); + $a_names[] = $addr['name']; + } } if (!empty($MESSAGE->headers->cc)) { $a_cc = $IMAP->decode_address_list($MESSAGE->headers->cc); foreach ($a_cc as $addr) { - if (!empty($addr['mailto'])) + if (!empty($addr['mailto'])) { $a_recipients[] = strtolower($addr['mailto']); + $a_names[] = $addr['name']; + } } } } $from_idx = null; - $default_identity = 0; + $default_identity = null; $return_path = $MESSAGE->headers->others['return-path']; // Select identity - foreach ($MESSAGE->identities as $idx => $sql_arr) { + foreach ($MESSAGE->identities as $idx => $ident) { // save default identity ID - if ($sql_arr['standard']) { + if ($ident['standard']) { $default_identity = $idx; } - // we need ascii here - $email = $sql_arr['email_ascii']; - $ident = format_email_recipient($email, $sql_arr['name']); - // select identity + // use From header if (in_array($compose_mode, array(RCUBE_COMPOSE_DRAFT, RCUBE_COMPOSE_EDIT))) { - if ($MESSAGE->headers->from == $ident) { + if ($MESSAGE->headers->from == $ident['ident']) { $from_idx = $idx; break; } } - // reply to self, force To header value - else if ($compose_mode == RCUBE_COMPOSE_REPLY && $MESSAGE->headers->from == $ident) { + // reply to yourself + else if ($compose_mode == RCUBE_COMPOSE_REPLY && $MESSAGE->headers->from == $ident['ident']) { $from_idx = $idx; - $MESSAGE->compose['to'] = $MESSAGE->headers->to; break; } - // set identity if it's one of the reply-message recipients - else if (in_array($email, $a_recipients) && ($from_idx === null || $sql_arr['standard'])) { - $from_idx = $idx; - } - // set identity when replying to mailing list - else if (strpos($return_path, str_replace('@', '=', $email).'@') !== false) { - $from_idx = $idx; + // use replied message recipients + else if (($found = array_search($ident['email_ascii'], $a_recipients)) !== false) { + // match identity name, prefer default identity + if ($from_idx === null || ($a_names[$found] && $ident['name'] && $a_names[$found] == $ident['name'])) { + $from_idx = $idx; + } } } - // Still no ID, use first identity + // Fallback using Return-Path + if ($from_idx === null && $return_path) { + foreach ($MESSAGE->identities as $idx => $ident) { + if (strpos($return_path, str_replace('@', '=', $ident['email_ascii']).'@') !== false) { + $from_idx = $idx; + break; + } + } + } + + // Still no ID, use default/first identity if ($from_idx === null) { - $from_idx = $default_identity; + $from_idx = $default_identity !== null ? $default_identity : key(reset($MESSAGE->identities)); } $ident = $MESSAGE->identities[$from_idx]; @@ -333,13 +348,13 @@ $mailfollowup = $MESSAGE->headers->others['mail-followup-to']; $mailreplyto = $MESSAGE->headers->others['mail-reply-to']; - if ($MESSAGE->compose['to']) - $fvalue = $MESSAGE->compose['to']; - else if ($MESSAGE->reply_all == 'list' && $mailfollowup) + if ($MESSAGE->reply_all == 'list' && $mailfollowup) $fvalue = $mailfollowup; else if ($MESSAGE->reply_all == 'list' && preg_match('/<mailto:([^>]+)>/i', $MESSAGE->headers->others['list-post'], $m)) $fvalue = $m[1]; + else if ($MESSAGE->reply_all && $mailfollowup) + $fvalue = $mailfollowup; else if ($mailreplyto) $fvalue = $mailreplyto; else if (!empty($MESSAGE->headers->replyto)) @@ -383,7 +398,7 @@ $mailto = mb_strtolower(rcube_idn_to_utf8($addr_part['mailto'])); if (!in_array($mailto, $a_recipients) - && (empty($MESSAGE->compose['from_email']) || $mailto != $MESSAGE->compose['from_email']) + && ($header == 'to' || empty($MESSAGE->compose['from_email']) || $mailto != $MESSAGE->compose['from_email']) ) { if ($addr_part['name'] && $addr_part['mailto'] != $addr_part['name']) $string = format_email_recipient($mailto, $addr_part['name']); @@ -394,7 +409,7 @@ $a_recipients[] = $addr_part['mailto']; } } - + $fvalue = implode(', ', $fvalue); } @@ -463,9 +478,12 @@ $input = new $field_type($field_attrib); $out = $input->show($MESSAGE->compose[$param]); } - + if ($form_start) $out = $form_start.$out; + + // configure autocompletion + rcube_autocomplete_init(); return $out; } @@ -560,6 +578,13 @@ $body = $_SESSION['compose']['param']['body']; $isHtml = false; } + // forward as attachment + else if ($compose_mode == RCUBE_COMPOSE_FORWARD && $MESSAGE->forward_attachment) { + $isHtml = rcmail_compose_editor_mode(); + $body = ''; + if (empty($_SESSION['compose']['attachments'])) + rcmail_write_forward_attachment($MESSAGE); + } // reply/edit/draft/forward else if ($compose_mode) { $has_html_part = $MESSAGE->has_html_part(); @@ -626,26 +651,26 @@ $body); } } - + $HTML_MODE = $isHtml; - + return $body; } function rcmail_compose_body($attrib) { global $RCMAIL, $CONFIG, $OUTPUT, $MESSAGE, $compose_mode, $LINE_LENGTH, $HTML_MODE, $MESSAGE_BODY; - + list($form_start, $form_end) = get_form_tags($attrib); unset($attrib['form']); - + if (empty($attrib['id'])) $attrib['id'] = 'rcmComposeBody'; $attrib['name'] = '_message'; $isHtml = $HTML_MODE; - + $out = $form_start ? "$form_start\n" : ''; $saveid = new html_hiddenfield(array('name' => '_draft_saveid', 'value' => $compose_mode==RCUBE_COMPOSE_DRAFT ? str_replace(array('<','>'), "", $MESSAGE->headers->messageID) : '')); @@ -678,7 +703,7 @@ // include HTML editor rcube_html_editor(); - + // include GoogieSpell if (!empty($CONFIG['enable_spellcheck'])) { @@ -739,7 +764,7 @@ $OUTPUT->add_label('checking'); $OUTPUT->set_env('spellcheck_langs', join(',', $editor_lang_set)); } - + $out .= "\n".'<iframe name="savetarget" src="program/blank.gif" style="width:0;height:0;border:none;visibility:hidden;"></iframe>'; return $out; @@ -752,8 +777,13 @@ // build reply prefix $from = array_pop($RCMAIL->imap->decode_address_list($MESSAGE->get_header('from'), 1, false)); - $prefix = sprintf("On %s, %s wrote:", - $MESSAGE->headers->date, $from['name'] ? $from['name'] : rcube_idn_to_utf8($from['mailto'])); + $prefix = rcube_label(array( + 'name' => 'mailreplyintro', + 'vars' => array( + 'date' => format_date($MESSAGE->headers->date, $RCMAIL->config->get('date_long')), + 'sender' => $from['name'] ? $from['name'] : rcube_idn_to_utf8($from['mailto']), + ) + )); if (!$bodyIsHtml) { $body = preg_replace('/\r?\n/', "\n", $body); @@ -848,7 +878,7 @@ $prefix .= "</tbody></table><br>"; } - + return $prefix.$body; } @@ -856,7 +886,7 @@ function rcmail_create_draft_body($body, $bodyIsHtml) { global $MESSAGE, $OUTPUT; - + /** * add attachments * sizeof($MESSAGE->mime_parts can be 1 - e.g. attachment, but no text! @@ -871,7 +901,7 @@ if ($cid_map) $body = str_replace(array_keys($cid_map), array_values($cid_map), $body); } - + return $body; } @@ -960,8 +990,61 @@ return $cid_map; } +// Creates an attachment from the forwarded message +function rcmail_write_forward_attachment(&$message) +{ + global $RCMAIL; + + if (strlen($message->subject)) { + $name = mb_substr($message->subject, 0, 64) . '.eml'; + } + else { + $name = 'message_rfc822.eml'; + } + + $mem_limit = parse_bytes(ini_get('memory_limit')); + $curr_mem = function_exists('memory_get_usage') ? memory_get_usage() : 16*1024*1024; // safe value: 16MB + $data = $path = null; + + // don't load too big attachments into memory + if ($mem_limit > 0 && $message->size > $mem_limit - $curr_mem) { + $temp_dir = unslashify($RCMAIL->config->get('temp_dir')); + $path = tempnam($temp_dir, 'rcmAttmnt'); + if ($fp = fopen($path, 'w')) { + $RCMAIL->imap->get_raw_body($message->uid, $fp); + fclose($fp); + } else + return false; + } else { + $data = $RCMAIL->imap->get_raw_body($message->uid); + } + + $attachment = array( + 'group' => $_SESSION['compose']['id'], + 'name' => $name, + 'mimetype' => 'message/rfc822', + 'data' => $data, + 'path' => $path, + 'size' => $path ? filesize($path) : strlen($data), + ); + + $attachment = $RCMAIL->plugins->exec_hook('attachment_save', $attachment); + + if ($attachment['status']) { + unset($attachment['data'], $attachment['status'], $attachment['content_id'], $attachment['abort']); + $_SESSION['compose']['attachments'][$attachment['id']] = $attachment; + return true; + } else if ($path) { + @unlink($path); + } + + return false; +} + + function rcmail_save_attachment(&$message, $pid) { + $rcmail = rcmail::get_instance(); $part = $message->mime_parts[$pid]; $mem_limit = parse_bytes(ini_get('memory_limit')); $curr_mem = function_exists('memory_get_usage') ? memory_get_usage() : 16*1024*1024; // safe value: 16MB @@ -969,7 +1052,6 @@ // don't load too big attachments into memory if ($mem_limit > 0 && $part->size > $mem_limit - $curr_mem) { - $rcmail = rcmail::get_instance(); $temp_dir = unslashify($rcmail->config->get('temp_dir')); $path = tempnam($temp_dir, 'rcmAttmnt'); if ($fp = fopen($path, 'w')) { @@ -991,7 +1073,7 @@ 'size' => $path ? filesize($path) : strlen($data), ); - $attachment = rcmail::get_instance()->plugins->exec_hook('attachment_save', $attachment); + $attachment = $rcmail->plugins->exec_hook('attachment_save', $attachment); if ($attachment['status']) { unset($attachment['data'], $attachment['status'], $attachment['content_id'], $attachment['abort']); @@ -999,7 +1081,7 @@ } else if ($path) { @unlink($path); } - + return false; } @@ -1022,7 +1104,7 @@ unset($attachment['data'], $attachment['status'], $attachment['content_id'], $attachment['abort']); return $attachment; } - + return false; } @@ -1137,23 +1219,17 @@ function rcmail_compose_attachment_form($attrib) { - global $OUTPUT; + global $RCMAIL, $OUTPUT; // add ID if not given if (!$attrib['id']) $attrib['id'] = 'rcmUploadbox'; - // find max filesize value - $max_filesize = parse_bytes(ini_get('upload_max_filesize')); - $max_postsize = parse_bytes(ini_get('post_max_size')); - if ($max_postsize && $max_postsize < $max_filesize) - $max_filesize = $max_postsize; + // Get filesize, enable upload progress bar + $max_filesize = rcube_upload_init(); - $OUTPUT->set_env('max_filesize', $max_filesize); - $max_filesize = show_bytes($max_filesize); - $button = new html_inputfield(array('type' => 'button')); - + $out = html::div($attrib, $OUTPUT->form_tag(array('name' => 'uploadform', 'method' => 'post', 'enctype' => 'multipart/form-data'), html::div(null, rcmail_compose_attachment_field(array('size' => $attrib['attachmentfieldsize']))) . @@ -1164,7 +1240,7 @@ ) ) ); - + $OUTPUT->add_gui_object('uploadbox', $attrib['id']); return $out; } @@ -1297,7 +1373,10 @@ function rcmail_store_target_selection($attrib) { $attrib['name'] = '_store_target'; - $select = rcmail_mailbox_select(array_merge($attrib, array('noselection' => '- '.rcube_label('dontsave').' -'))); + $select = rcmail_mailbox_select(array_merge($attrib, array( + 'noselection' => '- '.rcube_label('dontsave').' -', + 'folder_filter' => 'mail' + ))); return $select->show($_SESSION['compose']['param']['sent_mbox'], $attrib); } -- Gitblit v1.9.1