Changeset c321a955 in github
- Timestamp:
- Jan 16, 2012 10:14:41 AM (16 months ago)
- Branches:
- master, HEAD, courier-fix, dev-browser-capabilities, pdo, release-0.8
- Children:
- a2c4956
- Parents:
- 8764b6e
- Files:
-
- 2 added
- 1 deleted
- 37 edited
-
bin/msgexport.sh (modified) (3 diffs)
-
index.php (modified) (3 diffs)
-
installer/rcube_install.php (modified) (2 diffs)
-
program/include/iniset.php (modified) (1 prop)
-
program/include/main.inc (modified) (11 diffs)
-
program/include/rcmail.php (modified) (22 diffs)
-
program/include/rcube_charset.php (added)
-
program/include/rcube_config.php (modified) (1 diff)
-
program/include/rcube_imap.php (modified) (190 diffs)
-
program/include/rcube_imap_cache.php (modified) (15 diffs)
-
program/include/rcube_message.php (modified) (8 diffs)
-
program/include/rcube_result_index.php (modified) (9 diffs)
-
program/include/rcube_result_thread.php (modified) (21 diffs)
-
program/include/rcube_shared.inc (modified) (1 diff)
-
program/include/rcube_storage.php (added)
-
program/include/rcube_template.php (modified) (1 diff, 1 prop)
-
program/lib/utf7.inc (deleted)
-
program/localization/en_US/messages.inc (modified) (1 diff)
-
program/steps/mail/check_recent.inc (modified) (5 diffs)
-
program/steps/mail/compose.inc (modified) (7 diffs)
-
program/steps/mail/copy.inc (modified) (1 diff)
-
program/steps/mail/folders.inc (modified) (3 diffs)
-
program/steps/mail/func.inc (modified) (19 diffs)
-
program/steps/mail/get.inc (modified) (4 diffs)
-
program/steps/mail/getunread.inc (modified) (2 diffs)
-
program/steps/mail/headers.inc (modified) (1 diff)
-
program/steps/mail/list.inc (modified) (6 diffs)
-
program/steps/mail/mark.inc (modified) (8 diffs)
-
program/steps/mail/move_del.inc (modified) (8 diffs)
-
program/steps/mail/pagenav.inc (modified) (1 diff)
-
program/steps/mail/search.inc (modified) (6 diffs)
-
program/steps/mail/sendmail.inc (modified) (5 diffs)
-
program/steps/mail/show.inc (modified) (6 diffs)
-
program/steps/mail/viewsource.inc (modified) (2 diffs)
-
program/steps/settings/edit_folder.inc (modified) (5 diffs)
-
program/steps/settings/folders.inc (modified) (16 diffs)
-
program/steps/settings/func.inc (modified) (4 diffs)
-
program/steps/settings/save_folder.inc (modified) (6 diffs)
-
program/steps/settings/save_prefs.inc (modified) (1 diff)
-
tests/mailfunc.php (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
-
bin/msgexport.sh
r1c4f23d rc321a955 32 32 global $IMAP; 33 33 34 $IMAP->set_mailbox($mbox); 34 $IMAP->set_folder($mbox); 35 36 $index = $IMAP->index($mbox, null, 'ASC'); 37 $count = $index->countMessages(); 38 $index = $index->get(); 35 39 36 40 vputs("Getting message list of {$mbox}..."); 37 vputs( $IMAP->messagecount()."messages\n");41 vputs("$count messages\n"); 38 42 39 43 if ($filename) … … 49 53 $out = STDOUT; 50 54 51 for ($ count = $IMAP->messagecount(), $i=1; $i <=$count; $i++)55 for ($i = 0; $i < $count; $i++) 52 56 { 53 $headers = $IMAP->get_ headers($i, null, false);57 $headers = $IMAP->get_message_headers($index[$i]); 54 58 $from = current(rcube_mime::decode_address_list($headers->from, 1, false)); 55 59 56 60 fwrite($out, sprintf("From %s %s UID %d\n", $from['mailto'], $headers->date, $headers->uid)); 57 fwrite($out, $IMAP->conn->fetchPartHeader($mbox, $i)); 58 fwrite($out, $IMAP->conn->handlePartBody($mbox, $i)); 61 fwrite($out, $IMAP->print_raw_body($headers->uid)); 59 62 fwrite($out, "\n\n\n"); 60 63 61 progress_update($i , $count);64 progress_update($i+1, $count); 62 65 } 63 66 vputs("\ncomplete.\n"); … … 117 120 118 121 $filename = null; 119 $mailboxes = $args['mbox'] == '*' ? $IMAP->list_ mailboxes(null) : array($args['mbox']);122 $mailboxes = $args['mbox'] == '*' ? $IMAP->list_folders(null) : array($args['mbox']); 120 123 121 124 foreach ($mailboxes as $mbox) -
index.php
rfdff340 rc321a955 49 49 50 50 // check DB connections and exit on failure 51 if ($err_str = $ DB->is_error()) {51 if ($err_str = $RCMAIL->db->is_error()) { 52 52 raise_error(array( 53 53 'code' => 603, … … 129 129 } 130 130 else { 131 $error_code = (isset($RCMAIL->imap) && is_object($RCMAIL->imap)) ? $RCMAIL->imap->get_error_code() : 1;132 133 $OUTPUT->show_message($error_code < -1 ? ' imaperror' : (!$auth['valid'] ? 'invalidrequest' : 'loginfailed'), 'warning');131 $error_code = is_object($RCMAIL->storage) ? $RCMAIL->storage->get_error_code() : 1; 132 133 $OUTPUT->show_message($error_code < -1 ? 'storageerror' : (!$auth['valid'] ? 'invalidrequest' : 'loginfailed'), 'warning'); 134 134 $RCMAIL->plugins->exec_hook('login_failed', array( 135 135 'code' => $error_code, 'host' => $auth['host'], 'user' => $auth['user'])); … … 140 140 // end session (after optional referer check) 141 141 else if ($RCMAIL->task == 'logout' && isset($_SESSION['user_id']) && (!$RCMAIL->config->get('referer_check') || rcube_check_referer())) { 142 $userdata = array('user' => $_SESSION['username'], 'host' => $_SESSION['imap_host'], 'lang' => $RCMAIL->user->language); 142 $userdata = array( 143 'user' => $_SESSION['username'], 144 'host' => $_SESSION['storage_host'], 145 'lang' => $RCMAIL->user->language, 146 ); 143 147 $OUTPUT->show_message('loggedout'); 144 148 $RCMAIL->logout_actions(); -
installer/rcube_install.php
r3efe96a rc321a955 42 42 'imap_root' => 'imap_ns_personal', 43 43 'pagesize' => 'mail_pagesize', 44 'default_imap_folders' => 'default_folders', 44 45 ); 45 46 … … 180 181 $value = '%p'; 181 182 } 182 else if ($prop == 'default_ imap_folders') {183 else if ($prop == 'default_folders') { 183 184 $value = array(); 184 foreach ($this->config['default_ imap_folders'] as $_folder) {185 foreach ($this->config['default_folders'] as $_folder) { 185 186 switch ($_folder) { 186 187 case 'Drafts': $_folder = $this->config['drafts_mbox']; break; -
program/include/iniset.php
- Property mode changed from 100755 to 100644
-
program/include/main.inc
r4391a780 rc321a955 27 27 */ 28 28 29 require_once 'utf7.inc';30 29 require_once INSTALL_PATH . 'program/include/rcube_shared.inc'; 31 30 … … 184 183 185 184 186 /** 187 * Catch an error and throw an exception. 188 * 189 * @param int Level of the error 190 * @param string Error message 191 */ 192 function rcube_error_handler($errno, $errstr) 193 { 194 throw new ErrorException($errstr, 0, $errno); 195 } 196 197 198 /** 199 * Convert a string from one charset to another. 200 * Uses mbstring and iconv functions if possible 201 * 202 * @param string Input string 203 * @param string Suspected charset of the input string 204 * @param string Target charset to convert to; defaults to RCMAIL_CHARSET 205 * @return string Converted string 206 */ 185 // Deprecated 207 186 function rcube_charset_convert($str, $from, $to=NULL) 208 187 { 209 static $iconv_options = null; 210 static $mbstring_loaded = null; 211 static $mbstring_list = null; 212 static $conv = null; 213 214 $error = false; 215 216 $to = empty($to) ? strtoupper(RCMAIL_CHARSET) : rcube_parse_charset($to); 217 $from = rcube_parse_charset($from); 218 219 if ($from == $to || empty($str) || empty($from)) 220 return $str; 221 222 // convert charset using iconv module 223 if (function_exists('iconv') && $from != 'UTF7-IMAP' && $to != 'UTF7-IMAP') { 224 if ($iconv_options === null) { 225 // ignore characters not available in output charset 226 $iconv_options = '//IGNORE'; 227 if (iconv('', $iconv_options, '') === false) { 228 // iconv implementation does not support options 229 $iconv_options = ''; 230 } 231 } 232 233 // throw an exception if iconv reports an illegal character in input 234 // it means that input string has been truncated 235 set_error_handler('rcube_error_handler', E_NOTICE); 236 try { 237 $_iconv = iconv($from, $to . $iconv_options, $str); 238 } catch (ErrorException $e) { 239 $_iconv = false; 240 } 241 restore_error_handler(); 242 if ($_iconv !== false) { 243 return $_iconv; 244 } 245 } 246 247 if ($mbstring_loaded === null) 248 $mbstring_loaded = extension_loaded('mbstring'); 249 250 // convert charset using mbstring module 251 if ($mbstring_loaded) { 252 $aliases['WINDOWS-1257'] = 'ISO-8859-13'; 253 254 if ($mbstring_list === null) { 255 $mbstring_list = mb_list_encodings(); 256 $mbstring_list = array_map('strtoupper', $mbstring_list); 257 } 258 259 $mb_from = $aliases[$from] ? $aliases[$from] : $from; 260 $mb_to = $aliases[$to] ? $aliases[$to] : $to; 261 262 // return if encoding found, string matches encoding and convert succeeded 263 if (in_array($mb_from, $mbstring_list) && in_array($mb_to, $mbstring_list)) { 264 if (mb_check_encoding($str, $mb_from) && ($out = mb_convert_encoding($str, $mb_to, $mb_from))) 265 return $out; 266 } 267 } 268 269 // convert charset using bundled classes/functions 270 if ($to == 'UTF-8') { 271 if ($from == 'UTF7-IMAP') { 272 if ($_str = utf7_to_utf8($str)) 273 return $_str; 274 } 275 else if ($from == 'UTF-7') { 276 if ($_str = rcube_utf7_to_utf8($str)) 277 return $_str; 278 } 279 else if (($from == 'ISO-8859-1') && function_exists('utf8_encode')) { 280 return utf8_encode($str); 281 } 282 else if (class_exists('utf8')) { 283 if (!$conv) 284 $conv = new utf8($from); 285 else 286 $conv->loadCharset($from); 287 288 if($_str = $conv->strToUtf8($str)) 289 return $_str; 290 } 291 $error = true; 292 } 293 294 // encode string for output 295 if ($from == 'UTF-8') { 296 // @TODO: we need a function for UTF-7 (RFC2152) conversion 297 if ($to == 'UTF7-IMAP' || $to == 'UTF-7') { 298 if ($_str = utf8_to_utf7($str)) 299 return $_str; 300 } 301 else if ($to == 'ISO-8859-1' && function_exists('utf8_decode')) { 302 return utf8_decode($str); 303 } 304 else if (class_exists('utf8')) { 305 if (!$conv) 306 $conv = new utf8($to); 307 else 308 $conv->loadCharset($from); 309 310 if ($_str = $conv->strToUtf8($str)) 311 return $_str; 312 } 313 $error = true; 314 } 315 316 // return UTF-8 or original string 317 return $str; 318 } 319 320 321 /** 322 * Parse and validate charset name string (see #1485758). 323 * Sometimes charset string is malformed, there are also charset aliases 324 * but we need strict names for charset conversion (specially utf8 class) 325 * 326 * @param string Input charset name 327 * @return string The validated charset name 328 */ 329 function rcube_parse_charset($input) 330 { 331 static $charsets = array(); 332 $charset = strtoupper($input); 333 334 if (isset($charsets[$input])) 335 return $charsets[$input]; 336 337 $charset = preg_replace(array( 338 '/^[^0-9A-Z]+/', // e.g. _ISO-8859-JP$SIO 339 '/\$.*$/', // e.g. _ISO-8859-JP$SIO 340 '/UNICODE-1-1-*/', // RFC1641/1642 341 '/^X-/', // X- prefix (e.g. X-ROMAN8 => ROMAN8) 342 ), '', $charset); 343 344 if ($charset == 'BINARY') 345 return $charsets[$input] = null; 346 347 # Aliases: some of them from HTML5 spec. 348 $aliases = array( 349 'USASCII' => 'WINDOWS-1252', 350 'ANSIX31101983' => 'WINDOWS-1252', 351 'ANSIX341968' => 'WINDOWS-1252', 352 'UNKNOWN8BIT' => 'ISO-8859-15', 353 'UNKNOWN' => 'ISO-8859-15', 354 'USERDEFINED' => 'ISO-8859-15', 355 'KSC56011987' => 'EUC-KR', 356 'GB2312' => 'GBK', 357 'GB231280' => 'GBK', 358 'UNICODE' => 'UTF-8', 359 'UTF7IMAP' => 'UTF7-IMAP', 360 'TIS620' => 'WINDOWS-874', 361 'ISO88599' => 'WINDOWS-1254', 362 'ISO885911' => 'WINDOWS-874', 363 'MACROMAN' => 'MACINTOSH', 364 '77' => 'MAC', 365 '128' => 'SHIFT-JIS', 366 '129' => 'CP949', 367 '130' => 'CP1361', 368 '134' => 'GBK', 369 '136' => 'BIG5', 370 '161' => 'WINDOWS-1253', 371 '162' => 'WINDOWS-1254', 372 '163' => 'WINDOWS-1258', 373 '177' => 'WINDOWS-1255', 374 '178' => 'WINDOWS-1256', 375 '186' => 'WINDOWS-1257', 376 '204' => 'WINDOWS-1251', 377 '222' => 'WINDOWS-874', 378 '238' => 'WINDOWS-1250', 379 'MS950' => 'CP950', 380 'WINDOWS949' => 'UHC', 381 ); 382 383 // allow A-Z and 0-9 only 384 $str = preg_replace('/[^A-Z0-9]/', '', $charset); 385 386 if (isset($aliases[$str])) 387 $result = $aliases[$str]; 388 // UTF 389 else if (preg_match('/U[A-Z][A-Z](7|8|16|32)(BE|LE)*/', $str, $m)) 390 $result = 'UTF-' . $m[1] . $m[2]; 391 // ISO-8859 392 else if (preg_match('/ISO8859([0-9]{0,2})/', $str, $m)) { 393 $iso = 'ISO-8859-' . ($m[1] ? $m[1] : 1); 394 // some clients sends windows-1252 text as latin1, 395 // it is safe to use windows-1252 for all latin1 396 $result = $iso == 'ISO-8859-1' ? 'WINDOWS-1252' : $iso; 397 } 398 // handle broken charset names e.g. WINDOWS-1250HTTP-EQUIVCONTENT-TYPE 399 else if (preg_match('/(WIN|WINDOWS)([0-9]+)/', $str, $m)) { 400 $result = 'WINDOWS-' . $m[2]; 401 } 402 // LATIN 403 else if (preg_match('/LATIN(.*)/', $str, $m)) { 404 $aliases = array('2' => 2, '3' => 3, '4' => 4, '5' => 9, '6' => 10, 405 '7' => 13, '8' => 14, '9' => 15, '10' => 16, 406 'ARABIC' => 6, 'CYRILLIC' => 5, 'GREEK' => 7, 'GREEK1' => 7, 'HEBREW' => 8); 407 408 // some clients sends windows-1252 text as latin1, 409 // it is safe to use windows-1252 for all latin1 410 if ($m[1] == 1) { 411 $result = 'WINDOWS-1252'; 412 } 413 // if iconv is not supported we need ISO labels, it's also safe for iconv 414 else if (!empty($aliases[$m[1]])) { 415 $result = 'ISO-8859-'.$aliases[$m[1]]; 416 } 417 // iconv requires convertion of e.g. LATIN-1 to LATIN1 418 else { 419 $result = $str; 420 } 421 } 422 else { 423 $result = $charset; 424 } 425 426 $charsets[$input] = $result; 427 428 return $result; 429 } 430 431 432 /** 433 * Converts string from standard UTF-7 (RFC 2152) to UTF-8. 434 * 435 * @param string Input string 436 * @return string The converted string 437 */ 438 function rcube_utf7_to_utf8($str) 439 { 440 $Index_64 = array( 441 0,0,0,0, 0,0,0,0, 0,0,0,0, 0,0,0,0, 442 0,0,0,0, 0,0,0,0, 0,0,0,0, 0,0,0,0, 443 0,0,0,0, 0,0,0,0, 0,0,0,1, 0,0,0,0, 444 1,1,1,1, 1,1,1,1, 1,1,0,0, 0,0,0,0, 445 0,1,1,1, 1,1,1,1, 1,1,1,1, 1,1,1,1, 446 1,1,1,1, 1,1,1,1, 1,1,1,0, 0,0,0,0, 447 0,1,1,1, 1,1,1,1, 1,1,1,1, 1,1,1,1, 448 1,1,1,1, 1,1,1,1, 1,1,1,0, 0,0,0,0, 449 ); 450 451 $u7len = strlen($str); 452 $str = strval($str); 453 $res = ''; 454 455 for ($i=0; $u7len > 0; $i++, $u7len--) 456 { 457 $u7 = $str[$i]; 458 if ($u7 == '+') 459 { 460 $i++; 461 $u7len--; 462 $ch = ''; 463 464 for (; $u7len > 0; $i++, $u7len--) 465 { 466 $u7 = $str[$i]; 467 468 if (!$Index_64[ord($u7)]) 469 break; 470 471 $ch .= $u7; 472 } 473 474 if ($ch == '') { 475 if ($u7 == '-') 476 $res .= '+'; 477 continue; 478 } 479 480 $res .= rcube_utf16_to_utf8(base64_decode($ch)); 481 } 482 else 483 { 484 $res .= $u7; 485 } 486 } 487 488 return $res; 489 } 490 491 /** 492 * Converts string from UTF-16 to UTF-8 (helper for utf-7 to utf-8 conversion) 493 * 494 * @param string Input string 495 * @return string The converted string 496 */ 497 function rcube_utf16_to_utf8($str) 498 { 499 $len = strlen($str); 500 $dec = ''; 501 502 for ($i = 0; $i < $len; $i += 2) { 503 $c = ord($str[$i]) << 8 | ord($str[$i + 1]); 504 if ($c >= 0x0001 && $c <= 0x007F) { 505 $dec .= chr($c); 506 } else if ($c > 0x07FF) { 507 $dec .= chr(0xE0 | (($c >> 12) & 0x0F)); 508 $dec .= chr(0x80 | (($c >> 6) & 0x3F)); 509 $dec .= chr(0x80 | (($c >> 0) & 0x3F)); 510 } else { 511 $dec .= chr(0xC0 | (($c >> 6) & 0x1F)); 512 $dec .= chr(0x80 | (($c >> 0) & 0x3F)); 513 } 514 } 515 return $dec; 188 return rcube_charset::convert($str, $from, $to); 189 } 190 191 192 // Deprecated 193 function rc_detect_encoding($string, $failover='') 194 { 195 return rcube_charset::detect($string, $failover); 196 } 197 198 199 // Deprecated 200 function rc_utf8_clean($input) 201 { 202 return rcube_charset::clean($input); 203 } 204 205 206 /** 207 * Convert a variable into a javascript object notation 208 * 209 * @param mixed Input value 210 * @return string Serialized JSON string 211 */ 212 function json_serialize($input) 213 { 214 $input = rcube_charset::clean($input); 215 216 // sometimes even using rcube_charset::clean() the input contains invalid UTF-8 sequences 217 // that's why we have @ here 218 return @json_encode($input); 516 219 } 517 220 … … 1194 897 1195 898 // get mailbox list 1196 $mbox_name = $RCMAIL-> imap->get_mailbox_name();899 $mbox_name = $RCMAIL->storage->get_folder(); 1197 900 1198 901 // build the folders tree 1199 902 if (empty($a_mailboxes)) { 1200 903 // get mailbox list 1201 $a_folders = $RCMAIL-> imap->list_mailboxes('', $attrib['folder_name'], $attrib['folder_filter']);1202 $delimiter = $RCMAIL-> imap->get_hierarchy_delimiter();904 $a_folders = $RCMAIL->storage->list_folders_subscribed('', $attrib['folder_name'], $attrib['folder_filter']); 905 $delimiter = $RCMAIL->storage->get_hierarchy_delimiter(); 1203 906 $a_mailboxes = array(); 1204 907 … … 1246 949 $p += array('maxlength' => 100, 'realnames' => false); 1247 950 $a_mailboxes = array(); 1248 1249 if (empty($p['folder_name'])) 951 $storage = $RCMAIL->get_storage(); 952 953 if (empty($p['folder_name'])) { 1250 954 $p['folder_name'] = '*'; 955 } 1251 956 1252 957 if ($p['unsubscribed']) 1253 $list = $ RCMAIL->imap->list_unsubscribed('', $p['folder_name'], $p['folder_filter'], $p['folder_rights']);958 $list = $storage->list_folders('', $p['folder_name'], $p['folder_filter'], $p['folder_rights']); 1254 959 else 1255 $list = $ RCMAIL->imap->list_mailboxes('', $p['folder_name'], $p['folder_filter'], $p['folder_rights']);1256 1257 $delimiter = $ RCMAIL->imap->get_hierarchy_delimiter();960 $list = $storage->list_folders_subscribed('', $p['folder_name'], $p['folder_filter'], $p['folder_rights']); 961 962 $delimiter = $storage->get_hierarchy_delimiter(); 1258 963 1259 964 foreach ($list as $folder) { … … 1286 991 if (!$path) { 1287 992 $n_folder = $folder; 1288 $folder = $RCMAIL-> imap->mod_mailbox($folder);993 $folder = $RCMAIL->storage->mod_folder($folder); 1289 994 1290 995 if ($n_folder != $folder) { … … 1341 1046 $maxlength = intval($attrib['maxlength']); 1342 1047 $realnames = (bool)$attrib['realnames']; 1343 $msgcounts = $RCMAIL-> imap->get_cache('messagecount');1048 $msgcounts = $RCMAIL->storage->get_cache('messagecount'); 1344 1049 1345 1050 $out = ''; … … 1433 1138 1434 1139 // skip folders in which it isn't possible to create subfolders 1435 if (!empty($opts['skip_noinferiors']) && ($attrs = $RCMAIL-> imap->mailbox_attributes($folder['id']))1140 if (!empty($opts['skip_noinferiors']) && ($attrs = $RCMAIL->storage->folder_attributes($folder['id'])) 1436 1141 && in_array('\\Noinferiors', $attrs) 1437 1142 ) { … … 1502 1207 1503 1208 $protect_folders = $RCMAIL->config->get('protect_default_folders'); 1504 $default_folders = (array) $RCMAIL->config->get('default_ imap_folders');1505 $delimiter = $RCMAIL-> imap->get_hierarchy_delimiter();1209 $default_folders = (array) $RCMAIL->config->get('default_folders'); 1210 $delimiter = $RCMAIL->storage->get_hierarchy_delimiter(); 1506 1211 $path = explode($delimiter, $path); 1507 1212 $result = array(); … … 1546 1251 global $RCMAIL; 1547 1252 1548 $quota = $RCMAIL-> imap->get_quota();1253 $quota = $RCMAIL->storage->get_quota(); 1549 1254 $quota = $RCMAIL->plugins->exec_hook('quota', $quota); 1550 1255 … … 1592 1297 global $RCMAIL; 1593 1298 1594 $err_code = $RCMAIL->imap->get_error_code(); 1595 $res_code = $RCMAIL->imap->get_response_code(); 1596 1597 if ($res_code == rcube_imap::NOPERM) { 1299 $err_code = $RCMAIL->storage->get_error_code(); 1300 $res_code = $RCMAIL->storage->get_response_code(); 1301 1302 if ($err_code < 0) { 1303 $RCMAIL->output->show_message('storageerror', 'error'); 1304 } 1305 else if ($res_code == rcube_storage::NOPERM) { 1598 1306 $RCMAIL->output->show_message('errornoperm', 'error'); 1599 1307 } 1600 else if ($res_code == rcube_ imap::READONLY) {1308 else if ($res_code == rcube_storage::READONLY) { 1601 1309 $RCMAIL->output->show_message('errorreadonly', 'error'); 1602 1310 } 1603 else if ($err_code && ($err_str = $RCMAIL-> imap->get_error_str())) {1311 else if ($err_code && ($err_str = $RCMAIL->storage->get_error_str())) { 1604 1312 // try to detect access rights problem and display appropriate message 1605 1313 if (stripos($err_str, 'Permission denied') !== false) … … 1969 1677 $d = preg_replace('/^[^\.]+\./', '', $n); 1970 1678 // %h - IMAP host 1971 $h = $_SESSION[' imap_host'] ? $_SESSION['imap_host'] : $host;1679 $h = $_SESSION['storage_host'] ? $_SESSION['storage_host'] : $host; 1972 1680 // %z - IMAP domain without first part, e.g. %h=imap.domain.tld, %z=domain.tld 1973 1681 $z = preg_replace('/^[^\.]+\./', '', $h); -
program/include/rcmail.php
rfdff340 rc321a955 87 87 88 88 /** 89 * Instance of rcube_ imapclass.90 * 91 * @var rcube_ imap92 */ 93 public $ imap;89 * Instance of rcube_storage class. 90 * 91 * @var rcube_storage 92 */ 93 public $storage; 94 94 95 95 /** … … 172 172 // connect to database 173 173 $this->get_dbh(); 174 175 // set global object for backward compatibility176 $GLOBALS['DB'] = $this->db;177 174 178 175 // start session … … 242 239 if (is_object($user)) { 243 240 $this->user = $user; 244 245 // set global object for backward compatibility246 $GLOBALS['USER'] = $this->user;247 241 248 242 // overwrite config with user preferences … … 425 419 } 426 420 else if ($id && $ldap_config[$id]) { 427 $contacts = new rcube_ldap($ldap_config[$id], $this->config->get('ldap_debug'), $this->config->mail_domain($_SESSION[' imap_host']));421 $contacts = new rcube_ldap($ldap_config[$id], $this->config->get('ldap_debug'), $this->config->mail_domain($_SESSION['storage_host'])); 428 422 } 429 423 else if ($id === '0') { … … 585 579 586 580 /** 587 * Create global IMAP object and connect to server588 * 589 * @ param boolean True if connection should be established590 */ 591 public function imap_init($connect = false)581 * Initialize and get storage object 582 * 583 * @return rcube_storage Storage object 584 */ 585 public function get_storage() 592 586 { 593 587 // already initialized 594 if (is_object($this->imap)) 588 if (!is_object($this->storage)) { 589 $this->storage_init(); 590 } 591 592 return $this->storage; 593 } 594 595 596 /** 597 * Connect to the IMAP server with stored session data. 598 * 599 * @return bool True on success, False on error 600 * @deprecated 601 */ 602 public function imap_connect() 603 { 604 return $this->storage_connect(); 605 } 606 607 608 /** 609 * Initialize IMAP object. 610 * 611 * @deprecated 612 */ 613 public function imap_init() 614 { 615 $this->storage_init(); 616 } 617 618 619 /** 620 * Initialize storage object 621 */ 622 public function storage_init() 623 { 624 // already initialized 625 if (is_object($this->storage)) { 595 626 return; 596 597 $this->imap = new rcube_imap(); 598 $this->imap->skip_deleted = $this->config->get('skip_deleted'); 599 600 // enable caching of imap data 601 $imap_cache = $this->config->get('imap_cache'); 627 } 628 629 $driver = $this->config->get('storage_driver', 'imap'); 630 $driver_class = "rcube_{$driver}"; 631 632 if (!class_exists($driver_class)) { 633 raise_error(array( 634 'code' => 700, 'type' => 'php', 635 'file' => __FILE__, 'line' => __LINE__, 636 'message' => "Storage driver class ($driver) not found!"), 637 true, true); 638 } 639 640 // Initialize storage object 641 $this->storage = new $driver_class; 642 643 // for backward compat. (deprecated, will be removed) 644 $this->imap = $this->storage; 645 646 // enable caching of mail data 647 $storage_cache = $this->config->get("{$driver}_cache"); 602 648 $messages_cache = $this->config->get('messages_cache'); 603 649 // for backward compatybility 604 if ($ imap_cache === null && $messages_cache === null && $this->config->get('enable_caching')) {605 $ imap_cache= 'db';650 if ($storage_cache === null && $messages_cache === null && $this->config->get('enable_caching')) { 651 $storage_cache = 'db'; 606 652 $messages_cache = true; 607 653 } 608 654 609 if ($ imap_cache)610 $this-> imap->set_caching($imap_cache);655 if ($storage_cache) 656 $this->storage->set_caching($storage_cache); 611 657 if ($messages_cache) 612 $this-> imap->set_messages_caching(true);658 $this->storage->set_messages_caching(true); 613 659 614 660 // set pagesize from config … … 617 663 $pagesize = $this->config->get('pagesize', 50); 618 664 } 619 $this-> imap->set_pagesize($pagesize);620 621 // set c onnectionoptions665 $this->storage->set_pagesize($pagesize); 666 667 // set class options 622 668 $options = array( 623 'auth_type' => $this->config->get('imap_auth_type', 'check'), 624 'auth_cid' => $this->config->get('imap_auth_cid'), 625 'auth_pw' => $this->config->get('imap_auth_pw'), 626 'debug' => (bool) $this->config->get('imap_debug', 0), 627 'force_caps' => (bool) $this->config->get('imap_force_caps'), 628 'timeout' => (int) $this->config->get('imap_timeout', 0), 669 'auth_type' => $this->config->get("{$driver}_auth_type", 'check'), 670 'auth_cid' => $this->config->get("{$driver}_auth_cid"), 671 'auth_pw' => $this->config->get("{$driver}_auth_pw"), 672 'debug' => (bool) $this->config->get("{$driver}_debug"), 673 'force_caps' => (bool) $this->config->get("{$driver}_force_caps"), 674 'timeout' => (int) $this->config->get("{$driver}_timeout"), 675 'skip_deleted' => (bool) $this->config->get('skip_deleted'), 676 'driver' => $driver, 629 677 ); 630 678 631 $this->imap->set_options($options); 632 633 // set global object for backward compatibility 634 $GLOBALS['IMAP'] = $this->imap; 635 636 $hook = $this->plugins->exec_hook('imap_init', array('fetch_headers' => $this->imap->fetch_add_headers)); 637 if ($hook['fetch_headers']) 638 $this->imap->fetch_add_headers = $hook['fetch_headers']; 639 640 // support this parameter for backward compatibility but log warning 641 if ($connect) { 642 $this->imap_connect(); 643 raise_error(array( 644 'code' => 800, 'type' => 'imap', 645 'file' => __FILE__, 'line' => __LINE__, 646 'message' => "rcube::imap_init(true) is deprecated, use rcube::imap_connect() instead"), 647 true, false); 648 } 649 } 650 651 652 /** 653 * Connect to IMAP server with stored session data 654 * 655 * @return bool True on success, false on error 656 */ 657 public function imap_connect() 658 { 659 if (!$this->imap) 660 $this->imap_init(); 661 662 if ($_SESSION['imap_host'] && !$this->imap->conn->connected()) { 663 if (!$this->imap->connect($_SESSION['imap_host'], $_SESSION['username'], $this->decrypt($_SESSION['password']), $_SESSION['imap_port'], $_SESSION['imap_ssl'])) { 679 if (!empty($_SESSION['storage_host'])) { 680 $options['host'] = $_SESSION['storage_host']; 681 $options['user'] = $_SESSION['username']; 682 $options['port'] = $_SESSION['storage_port']; 683 $options['ssl'] = $_SESSION['storage_ssl']; 684 $options['password'] = $this->decrypt($_SESSION['password']); 685 } 686 687 $options = $this->plugins->exec_hook("storage_init", $options); 688 689 // for backward compat. (deprecated, to be removed) 690 $options = $this->plugins->exec_hook("imap_init", $options); 691 692 $this->storage->set_options($options); 693 $this->set_storage_prop(); 694 } 695 696 697 /** 698 * Connect to the mail storage server with stored session data 699 * 700 * @return bool True on success, False on error 701 */ 702 public function storage_connect() 703 { 704 $storage = $this->get_storage(); 705 706 if ($_SESSION['storage_host'] && !$storage->is_connected()) { 707 $host = $_SESSION['storage_host']; 708 $user = $_SESSION['username']; 709 $port = $_SESSION['storage_port']; 710 $ssl = $_SESSION['storage_ssl']; 711 $pass = $this->decrypt($_SESSION['password']); 712 713 if (!$storage->connect($host, $user, $pass, $port, $ssl)) { 664 714 if ($this->output) 665 $this->output->show_message($ this->imap->get_error_code() == -1 ? 'imaperror' : 'sessionerror', 'error');715 $this->output->show_message($storage->get_error_code() == -1 ? 'storageerror' : 'sessionerror', 'error'); 666 716 } 667 717 else { 668 $this->set_ imap_prop();669 return $ this->imap->conn;718 $this->set_storage_prop(); 719 return $storage->is_connected(); 670 720 } 671 721 } … … 745 795 746 796 /** 747 * Perfom login to the IMAPserver and to the webmail service.797 * Perfom login to the mail server and to the webmail service. 748 798 * This will also create a new user entry if auto_create_user is configured. 749 799 * 750 * @param string IMAPuser name751 * @param string IMAPpassword752 * @param string IMAPhost800 * @param string Mail storage (IMAP) user name 801 * @param string Mail storage (IMAP) password 802 * @param string Mail storage (IMAP) host 753 803 * 754 804 * @return boolean True on success, False on failure … … 786 836 if ($a_host['host']) { 787 837 $host = $a_host['host']; 788 $ imap_ssl = (isset($a_host['scheme']) && in_array($a_host['scheme'], array('ssl','imaps','tls'))) ? $a_host['scheme'] : null;838 $ssl = (isset($a_host['scheme']) && in_array($a_host['scheme'], array('ssl','imaps','tls'))) ? $a_host['scheme'] : null; 789 839 if (!empty($a_host['port'])) 790 $imap_port = $a_host['port']; 791 else if ($imap_ssl && $imap_ssl != 'tls' && (!$config['default_port'] || $config['default_port'] == 143)) 792 $imap_port = 993; 793 } 794 795 $imap_port = $imap_port ? $imap_port : $config['default_port']; 840 $port = $a_host['port']; 841 else if ($ssl && $ssl != 'tls' && (!$config['default_port'] || $config['default_port'] == 143)) 842 $port = 993; 843 } 844 845 if (!$port) { 846 $port = $config['default_port']; 847 } 796 848 797 849 /* Modify username with domain if required … … 806 858 } 807 859 808 // Convert username to lowercase. If IMAPbackend860 // Convert username to lowercase. If storage backend 809 861 // is case-insensitive we need to store always the same username (#1487113) 810 862 if ($config['login_lc']) { … … 831 883 $username = $user->data['username']; 832 884 833 if (!$this-> imap)834 $this-> imap_init();835 836 // try IMAP login837 if (!($ imap_login = $this->imap->connect($host, $username, $pass, $imap_port, $imap_ssl))) {885 if (!$this->storage) 886 $this->storage_init(); 887 888 // try to log in 889 if (!($login = $this->storage->connect($host, $username, $pass, $port, $ssl))) { 838 890 // try with lowercase 839 891 $username_lc = mb_strtolower($username); … … 843 895 $username_lc = $user->data['username']; 844 896 845 if ($ imap_login = $this->imap->connect($host, $username_lc, $pass, $imap_port, $imap_ssl))897 if ($login = $this->storage->connect($host, $username_lc, $pass, $port, $ssl)) 846 898 $username = $username_lc; 847 899 } 848 900 } 849 901 850 // exit if IMAPlogin failed851 if (!$ imap_login)902 // exit if login failed 903 if (!$login) { 852 904 return false; 905 } 853 906 854 907 // user already registered -> update user's record … … 882 935 // Configure environment 883 936 $this->set_user($user); 884 $this->set_ imap_prop();937 $this->set_storage_prop(); 885 938 $this->session_configure(); 886 939 … … 890 943 // create default folders on first login 891 944 if ($config['create_default_folders'] && (!empty($created) || empty($user->data['last_login']))) { 892 $this-> imap->create_default_folders();945 $this->storage->create_default_folders(); 893 946 } 894 947 895 948 // set session vars 896 $_SESSION['user_id'] = $user->ID;897 $_SESSION['username'] = $user->data['username'];898 $_SESSION[' imap_host'] = $host;899 $_SESSION[' imap_port'] = $imap_port;900 $_SESSION[' imap_ssl'] = $imap_ssl;901 $_SESSION['password'] = $this->encrypt($pass);902 $_SESSION['login_time'] = mktime();949 $_SESSION['user_id'] = $user->ID; 950 $_SESSION['username'] = $user->data['username']; 951 $_SESSION['storage_host'] = $host; 952 $_SESSION['storage_port'] = $port; 953 $_SESSION['storage_ssl'] = $ssl; 954 $_SESSION['password'] = $this->encrypt($pass); 955 $_SESSION['login_time'] = mktime(); 903 956 904 957 if (isset($_REQUEST['_timezone']) && $_REQUEST['_timezone'] != '_default_') … … 908 961 909 962 // force reloading complete list of subscribed mailboxes 910 $this-> imap->clear_cache('mailboxes', true);963 $this->storage->clear_cache('mailboxes', true); 911 964 912 965 return true; … … 918 971 919 972 /** 920 * Set root dir and last stored mailbox973 * Set storage parameters. 921 974 * This must be done AFTER connecting to the server! 922 975 */ 923 public function set_imap_prop() 924 { 925 $this->imap->set_charset($this->config->get('default_charset', RCMAIL_CHARSET)); 926 927 if ($default_folders = $this->config->get('default_imap_folders')) { 928 $this->imap->set_default_mailboxes($default_folders); 976 private function set_storage_prop() 977 { 978 $storage = $this->get_storage(); 979 980 $storage->set_charset($this->config->get('default_charset', RCMAIL_CHARSET)); 981 982 if ($default_folders = $this->config->get('default_folders')) { 983 $storage->set_default_folders($default_folders); 929 984 } 930 985 if (isset($_SESSION['mbox'])) { 931 $ this->imap->set_mailbox($_SESSION['mbox']);986 $storage->set_folder($_SESSION['mbox']); 932 987 } 933 988 if (isset($_SESSION['page'])) { 934 $ this->imap->set_page($_SESSION['page']);989 $storage->set_page($_SESSION['page']); 935 990 } 936 991 } … … 958 1013 list($user, $domain) = explode('@', get_input_value('_user', RCUBE_INPUT_POST)); 959 1014 if (!empty($domain)) { 960 foreach ($default_host as $ imap_host => $mail_domains) {1015 foreach ($default_host as $storage_host => $mail_domains) { 961 1016 if (is_array($mail_domains) && in_array($domain, $mail_domains)) { 962 $host = $ imap_host;1017 $host = $storage_host; 963 1018 break; 964 1019 } … … 1168 1223 return; 1169 1224 1170 $this-> imap_connect();1225 $this->storage_connect(); 1171 1226 } 1172 1227 1173 1228 if ($config['logout_purge'] && !empty($config['trash_mbox'])) { 1174 $this-> imap->clear_mailbox($config['trash_mbox']);1229 $this->storage->clear_folder($config['trash_mbox']); 1175 1230 } 1176 1231 1177 1232 if ($config['logout_expunge']) { 1178 $this-> imap->expunge('INBOX');1233 $this->storage->expunge_folder('INBOX'); 1179 1234 } 1180 1235 … … 1208 1263 } 1209 1264 1210 if (is_object($this-> imap))1211 $this-> imap->close();1265 if (is_object($this->storage)) 1266 $this->storage->close(); 1212 1267 1213 1268 // before closing the database connection, write session data … … 1608 1663 private function fix_namespace_settings($user) 1609 1664 { 1610 $prefix = $this-> imap->get_namespace('prefix');1665 $prefix = $this->storage->get_namespace('prefix'); 1611 1666 $prefix_len = strlen($prefix); 1612 1667 … … 1619 1674 1620 1675 // Build namespace prefix regexp 1621 $ns = $this-> imap->get_namespace();1676 $ns = $this->storage->get_namespace(); 1622 1677 $regexp = array(); 1623 1678 … … 1643 1698 } 1644 1699 1645 if (!empty($prefs['default_ imap_folders'])) {1646 foreach ($prefs['default_ imap_folders'] as $idx => $name) {1700 if (!empty($prefs['default_folders'])) { 1701 foreach ($prefs['default_folders'] as $idx => $name) { 1647 1702 if ($name != 'INBOX' && !preg_match($regexp, $name)) { 1648 $prefs['default_ imap_folders'][$idx] = $prefix.$name;1703 $prefs['default_folders'][$idx] = $prefix.$name; 1649 1704 } 1650 1705 } … … 1696 1751 // save updated preferences and reset imap settings (default folders) 1697 1752 $user->save_prefs($prefs); 1698 $this->set_ imap_prop();1753 $this->set_storage_prop(); 1699 1754 } 1700 1755 -
program/include/rcube_config.php
re86a21b rc321a955 73 73 $this->prop[$folder] = rcube_charset_convert($this->prop[$folder], RCMAIL_CHARSET, 'UTF7-IMAP'); 74 74 75 if (!empty($this->prop['default_ imap_folders']))76 foreach ($this->prop['default_ imap_folders'] as $n => $folder)77 $this->prop['default_ imap_folders'][$n] = rcube_charset_convert($folder, RCMAIL_CHARSET, 'UTF7-IMAP');75 if (!empty($this->prop['default_folders'])) 76 foreach ($this->prop['default_folders'] as $n => $folder) 77 $this->prop['default_folders'][$n] = rcube_charset_convert($folder, RCMAIL_CHARSET, 'UTF7-IMAP'); 78 78 79 79 // set PHP error logging according to config -
program/include/rcube_imap.php
r2081eed rc321a955 6 6 | | 7 7 | This file is part of the Roundcube Webmail client | 8 | Copyright (C) 2005-201 1, The Roundcube Dev Team |9 | Copyright (C) 2011 , Kolab Systems AG|8 | Copyright (C) 2005-2012, The Roundcube Dev Team | 9 | Copyright (C) 2011-2012, Kolab Systems AG | 10 10 | Licensed under the GNU GPL | 11 11 | | 12 12 | PURPOSE: | 13 | IMAP Engine|13 | IMAP Storage Engine | 14 14 | | 15 15 +-----------------------------------------------------------------------+ … … 31 31 * @version 2.0 32 32 */ 33 class rcube_imap 33 class rcube_imap extends rcube_storage 34 34 { 35 public $skip_deleted = false;36 public $page_size = 10;37 public $list_page = 1;38 public $threading = false;39 public $fetch_add_headers = '';40 public $get_all_headers = false;41 42 35 /** 43 36 * Instance of rcube_imap_generic … … 52 45 * @var rcube_imap_cache 53 46 */ 54 pr ivate$mcache;47 protected $mcache; 55 48 56 49 /** … … 59 52 * @var rcube_cache 60 53 */ 61 pr ivate$cache;54 protected $cache; 62 55 63 56 /** … … 66 59 * @var array 67 60 */ 68 private $icache = array(); 69 70 private $mailbox = 'INBOX'; 71 private $delimiter = NULL; 72 private $namespace = NULL; 73 private $sort_field = ''; 74 private $sort_order = 'DESC'; 75 private $default_charset = 'ISO-8859-1'; 76 private $struct_charset = NULL; 77 private $default_folders = array('INBOX'); 78 private $uid_id_map = array(); 79 private $msg_headers = array(); 80 public $search_set = NULL; 81 public $search_string = ''; 82 private $search_charset = ''; 83 private $search_sort_field = ''; 84 private $search_threads = false; 85 private $search_sorted = false; 86 private $options = array('auth_method' => 'check'); 87 private $host, $user, $pass, $port, $ssl; 88 private $caching = false; 89 private $messages_caching = false; 90 91 /** 92 * All (additional) headers used (in any way) by Roundcube 93 * Not listed here: DATE, FROM, TO, CC, REPLY-TO, SUBJECT, CONTENT-TYPE, LIST-POST 94 * (used for messages listing) are hardcoded in rcube_imap_generic::fetchHeaders() 95 * 96 * @var array 97 * @see rcube_imap::fetch_add_headers 98 */ 99 private $all_headers = array( 100 'IN-REPLY-TO', 101 'BCC', 102 'MESSAGE-ID', 103 'CONTENT-TRANSFER-ENCODING', 104 'REFERENCES', 105 'X-DRAFT-INFO', 106 'MAIL-FOLLOWUP-TO', 107 'MAIL-REPLY-TO', 108 'RETURN-PATH', 109 ); 110 111 const UNKNOWN = 0; 112 const NOPERM = 1; 113 const READONLY = 2; 114 const TRYCREATE = 3; 115 const INUSE = 4; 116 const OVERQUOTA = 5; 117 const ALREADYEXISTS = 6; 118 const NONEXISTENT = 7; 119 const CONTACTADMIN = 8; 61 protected $icache = array(); 62 63 protected $list_page = 1; 64 protected $delimiter; 65 protected $namespace; 66 protected $sort_field = ''; 67 protected $sort_order = 'DESC'; 68 protected $struct_charset; 69 protected $uid_id_map = array(); 70 protected $msg_headers = array(); 71 protected $search_set; 72 protected $search_string = ''; 73 protected $search_charset = ''; 74 protected $search_sort_field = ''; 75 protected $search_threads = false; 76 protected $search_sorted = false; 77 protected $options = array('auth_method' => 'check'); 78 protected $caching = false; 79 protected $messages_caching = false; 80 protected $threading = false; 120 81 121 82 … … 123 84 * Object constructor. 124 85 */ 125 function __construct()86 public function __construct() 126 87 { 127 88 $this->conn = new rcube_imap_generic(); … … 129 90 // Set namespace and delimiter from session, 130 91 // so some methods would work before connection 131 if (isset($_SESSION['imap_namespace'])) 92 if (isset($_SESSION['imap_namespace'])) { 132 93 $this->namespace = $_SESSION['imap_namespace']; 133 if (isset($_SESSION['imap_delimiter'])) 94 } 95 if (isset($_SESSION['imap_delimiter'])) { 134 96 $this->delimiter = $_SESSION['imap_delimiter']; 97 } 98 } 99 100 101 /** 102 * Magic getter for backward compat. 103 * 104 * @deprecated. 105 */ 106 public function __get($name) 107 { 108 if (isset($this->{$name})) { 109 return $this->{$name}; 110 } 135 111 } 136 112 … … 144 120 * @param integer $port Port to connect to 145 121 * @param string $use_ssl SSL schema (either ssl or tls) or null if plain connection 122 * 146 123 * @return boolean TRUE on success, FALSE on failure 147 * @access public 148 */ 149 function connect($host, $user, $pass, $port=143, $use_ssl=null) 124 */ 125 public function connect($host, $user, $pass, $port=143, $use_ssl=null) 150 126 { 151 127 // check for OpenSSL support in PHP build 152 if ($use_ssl && extension_loaded('openssl')) 128 if ($use_ssl && extension_loaded('openssl')) { 153 129 $this->options['ssl_mode'] = $use_ssl == 'imaps' ? 'ssl' : $use_ssl; 130 } 154 131 else if ($use_ssl) { 155 132 raise_error(array('code' => 403, 'type' => 'imap', … … 162 139 163 140 if ($this->options['debug']) { 164 $this-> conn->setDebug(true, array($this, 'debug_handler'));141 $this->set_debug(true); 165 142 166 143 $this->options['ident'] = array( … … 179 156 'attempt' => ++$attempt))); 180 157 181 if (!empty($data['pass'])) 158 if (!empty($data['pass'])) { 182 159 $pass = $data['pass']; 160 } 183 161 184 162 $this->conn->connect($data['host'], $data['user'], $pass, $data); 185 163 } while(!$this->conn->connected() && $data['retry']); 186 164 187 $this->host = $data['host']; 188 $this->user = $data['user']; 189 $this->pass = $pass; 190 $this->port = $port; 191 $this->ssl = $use_ssl; 165 $config = array( 166 'host' => $data['host'], 167 'user' => $data['user'], 168 'password' => $pass, 169 'port' => $port, 170 'ssl' => $use_ssl, 171 ); 172 173 $this->options = array_merge($this->options, $config); 174 $this->connect_done = true; 192 175 193 176 if ($this->conn->connected()) { … … 213 196 214 197 /** 215 * Close IMAP connection 198 * Close IMAP connection. 216 199 * Usually done on script shutdown 217 * 218 * @access public 219 */ 220 function close() 200 */ 201 public function close() 221 202 { 222 203 $this->conn->closeConnection(); 223 if ($this->mcache) 204 if ($this->mcache) { 224 205 $this->mcache->close(); 225 } 226 227 228 /** 229 * Close IMAP connection and re-connect 230 * This is used to avoid some strange socket errors when talking to Courier IMAP 231 * 232 * @access public 233 */ 234 function reconnect() 235 { 236 $this->conn->closeConnection(); 237 $connected = $this->connect($this->host, $this->user, $this->pass, $this->port, $this->ssl); 238 239 // issue SELECT command to restore connection status 240 if ($connected && strlen($this->mailbox)) 241 $this->conn->select($this->mailbox); 206 } 207 } 208 209 210 /** 211 * Check connection state, connect if not connected. 212 */ 213 public function check_connection() 214 { 215 // Establish connection if it wasn't done yet 216 if (!$this->connect_done && !empty($this->options['user'])) { 217 return $this->connect( 218 $this->options['host'], 219 $this->options['user'], 220 $this->options['password'], 221 $this->options['port'], 222 $this->options['ssl'] 223 ); 224 } 225 226 return $this->is_connected(); 227 } 228 229 230 /** 231 * Checks IMAP connection. 232 * 233 * @return boolean TRUE on success, FALSE on failure 234 */ 235 public function is_connected() 236 { 237 return $this->conn->connected(); 242 238 } 243 239 … … 248 244 * @return int Error code 249 245 */ 250 function get_error_code()246 public function get_error_code() 251 247 { 252 248 return $this->conn->errornum; … … 255 251 256 252 /** 257 * Returns messageof last error258 * 259 * @return string Error message260 */ 261 function get_error_str()253 * Returns text of last error 254 * 255 * @return string Error string 256 */ 257 public function get_error_str() 262 258 { 263 259 return $this->conn->error; … … 270 266 * @return int Response code 271 267 */ 272 function get_response_code()268 public function get_response_code() 273 269 { 274 270 switch ($this->conn->resultcode) { … … 296 292 297 293 /** 298 * Returns last command response299 *300 * @return string Response301 */302 function get_response_str()303 {304 return $this->conn->result;305 }306 307 308 /**309 * Set options to be used in rcube_imap_generic::connect()310 *311 * @param array $opt Options array312 */313 function set_options($opt)314 {315 $this->options = array_merge($this->options, (array)$opt);316 }317 318 319 /**320 294 * Activate/deactivate debug mode 321 295 * 322 296 * @param boolean $dbg True if IMAP conversation should be logged 323 * @access public 324 */ 325 function set_debug($dbg = true) 297 */ 298 public function set_debug($dbg = true) 326 299 { 327 300 $this->options['debug'] = $dbg; … … 331 304 332 305 /** 333 * Set default message charset 334 * 335 * This will be used for message decoding if a charset specification is not available 336 * 337 * @param string $cs Charset string 338 * @access public 339 */ 340 function set_charset($cs) 341 { 342 $this->default_charset = $cs; 343 } 344 345 346 /** 347 * This list of folders will be listed above all other folders 348 * 349 * @param array $arr Indexed list of folder names 350 * @access public 351 */ 352 function set_default_mailboxes($arr) 353 { 354 if (is_array($arr)) { 355 $this->default_folders = $arr; 356 357 // add inbox if not included 358 if (!in_array('INBOX', $this->default_folders)) 359 array_unshift($this->default_folders, 'INBOX'); 360 } 361 } 362 363 364 /** 365 * Set internal mailbox reference. 366 * 367 * All operations will be perfomed on this mailbox/folder 368 * 369 * @param string $mailbox Mailbox/Folder name 370 * @access public 371 */ 372 function set_mailbox($mailbox) 373 { 374 if ($this->mailbox == $mailbox) 306 * Set internal folder reference. 307 * All operations will be perfomed on this folder. 308 * 309 * @param string $folder Folder name 310 */ 311 public function set_folder($folder) 312 { 313 if ($this->folder == $folder) { 375 314 return; 376 377 $this->mailbox = $mailbox; 378 379 // clear messagecount cache for this mailbox 380 $this->_clear_messagecount($mailbox); 381 } 382 383 384 /** 385 * Set internal list page 386 * 387 * @param number $page Page number to list 388 * @access public 389 */ 390 function set_page($page) 391 { 392 $this->list_page = (int)$page; 393 } 394 395 396 /** 397 * Set internal page size 398 * 399 * @param number $size Number of messages to display on one page 400 * @access public 401 */ 402 function set_pagesize($size) 403 { 404 $this->page_size = (int)$size; 315 } 316 317 $this->folder = $folder; 318 319 // clear messagecount cache for this folder 320 $this->clear_messagecount($folder); 405 321 } 406 322 … … 416 332 * 4 - true if sorted, bool 417 333 */ 418 function set_search_set($set)334 public function set_search_set($set) 419 335 { 420 336 $set = (array)$set; … … 434 350 * @return array Search set 435 351 */ 436 function get_search_set() 437 { 352 public function get_search_set() 353 { 354 if (empty($this->search_set)) { 355 return null; 356 } 357 438 358 return array( 439 359 $this->search_string, … … 447 367 448 368 /** 449 * Returns the currently used mailbox name 450 * 451 * @return string Name of the mailbox/folder 452 * @access public 453 */ 454 function get_mailbox_name() 455 { 456 return $this->mailbox; 457 } 458 459 460 /** 461 * Returns the IMAP server's capability 369 * Returns the IMAP server's capability. 462 370 * 463 371 * @param string $cap Capability name 372 * 464 373 * @return mixed Capability value or TRUE if supported, FALSE if not 465 * @access public 466 */ 467 function get_capability($cap) 468 { 469 return $this->conn->getCapability(strtoupper($cap)); 470 } 471 472 473 /** 474 * Sets threading flag to the best supported THREAD algorithm 475 * 476 * @param boolean $enable TRUE to enable and FALSE 477 * @return string Algorithm or false if THREAD is not supported 478 * @access public 479 */ 480 function set_threading($enable=false) 481 { 482 $this->threading = false; 483 484 if ($enable && ($caps = $this->get_capability('THREAD'))) { 485 if (in_array('REFS', $caps)) 486 $this->threading = 'REFS'; 487 else if (in_array('REFERENCES', $caps)) 488 $this->threading = 'REFERENCES'; 489 else if (in_array('ORDEREDSUBJECT', $caps)) 490 $this->threading = 'ORDEREDSUBJECT'; 491 } 492 493 return $this->threading; 494 } 495 496 497 /** 498 * Checks the PERMANENTFLAGS capability of the current mailbox 374 */ 375 public function get_capability($cap) 376 { 377 $cap = strtoupper($cap); 378 $sess_key = "STORAGE_$cap"; 379 380 if (!isset($_SESSION[$sess_key])) { 381 if (!$this->check_connection()) { 382 return false; 383 } 384 385 $_SESSION[$sess_key] = $this->conn->getCapability($cap); 386 } 387 388 return $_SESSION[$sess_key]; 389 } 390 391 392 /** 393 * Checks the PERMANENTFLAGS capability of the current folder 499 394 * and returns true if the given flag is supported by the IMAP server 500 395 * 501 396 * @param string $flag Permanentflag name 397 * 502 398 * @return boolean True if this flag is supported 503 * @access public 504 */ 505 function check_permflag($flag) 399 */ 400 public function check_permflag($flag) 506 401 { 507 402 $flag = strtoupper($flag); 508 403 $imap_flag = $this->conn->flags[$flag]; 404 405 if ($this->folder !== null) { 406 $this->check_connection(); 407 } 408 // @TODO: cache permanent flags (?) 409 509 410 return (in_array_nocase($imap_flag, $this->conn->data['PERMANENTFLAGS'])); 510 411 } … … 517 418 * @access public 518 419 */ 519 function get_hierarchy_delimiter()420 public function get_hierarchy_delimiter() 520 421 { 521 422 return $this->delimiter; … … 529 430 * 530 431 * @return array Namespace data 531 * @access public 532 */ 533 function get_namespace($name=null) 432 */ 433 public function get_namespace($name = null) 534 434 { 535 435 $ns = $this->namespace; … … 546 446 /** 547 447 * Sets delimiter and namespaces 548 * 549 * @access private 550 */ 551 private function set_env() 448 */ 449 protected function set_env() 552 450 { 553 451 if ($this->delimiter !== null && $this->namespace !== null) { … … 561 459 $imap_delimiter = $config->get('imap_delimiter'); 562 460 563 if (!$this->c onn->connected())461 if (!$this->check_connection()) { 564 462 return; 463 } 565 464 566 465 $ns = $this->conn->getNamespace(); … … 615 514 } 616 515 617 // Find personal namespace prefix for mod_ mailbox()516 // Find personal namespace prefix for mod_folder() 618 517 // Prefix can be removed when there is only one personal namespace 619 518 if (is_array($this->namespace['personal']) && count($this->namespace['personal']) == 1) { … … 627 526 628 527 /** 629 * Get message count for a specific mailbox630 * 631 * @param string $ mailbox Mailbox/folder name528 * Get message count for a specific folder 529 * 530 * @param string $folder Folder name 632 531 * @param string $mode Mode for count [ALL|THREADS|UNSEEN|RECENT] 633 532 * @param boolean $force Force reading from server and update cache 634 533 * @param boolean $status Enables storing folder status info (max UID/count), 635 * required for mailbox_status() 534 * required for folder_status() 535 * 636 536 * @return int Number of messages 637 * @access public 638 */ 639 function messagecount($mailbox='', $mode='ALL', $force=false, $status=true) 640 { 641 if (!strlen($mailbox)) { 642 $mailbox = $this->mailbox; 643 } 644 645 return $this->_messagecount($mailbox, $mode, $force, $status); 646 } 647 648 649 /** 650 * Private method for getting nr of messages 651 * 652 * @param string $mailbox Mailbox name 537 */ 538 public function count($folder='', $mode='ALL', $force=false, $status=true) 539 { 540 if (!strlen($folder)) { 541 $folder = $this->folder; 542 } 543 544 return $this->messagecount($folder, $mode, $force, $status); 545 } 546 547 548 /** 549 * protected method for getting nr of messages 550 * 551 * @param string $folder Folder name 653 552 * @param string $mode Mode for count [ALL|THREADS|UNSEEN|RECENT] 654 553 * @param boolean $force Force reading from server and update cache 655 554 * @param boolean $status Enables storing folder status info (max UID/count), 656 * required for mailbox_status() 555 * required for folder_status() 556 * 657 557 * @return int Number of messages 658 * @access private 659 * @see rcube_imap::messagecount() 660 */ 661 private function _messagecount($mailbox, $mode='ALL', $force=false, $status=true) 558 * @see rcube_imap::count() 559 */ 560 protected function messagecount($folder, $mode='ALL', $force=false, $status=true) 662 561 { 663 562 $mode = strtoupper($mode); 664 563 665 564 // count search set 666 if ($this->search_string && $mailbox == $this->mailbox && ($mode == 'ALL' || $mode == 'THREADS') && !$force) { 667 if ($mode == 'ALL') 668 return $this->search_set->countMessages(); 669 else 565 if ($this->search_string && $folder == $this->folder && ($mode == 'ALL' || $mode == 'THREADS') && !$force) { 566 if ($mode == 'ALL') { 567 return $this->search_set->count_messages(); 568 } 569 else { 670 570 return $this->search_set->count(); 671 } 672 673 $a_mailbox_cache = $this->get_cache('messagecount'); 571 } 572 } 573 574 $a_folder_cache = $this->get_cache('messagecount'); 674 575 675 576 // return cached value 676 if (!$force && is_array($a_mailbox_cache[$mailbox]) && isset($a_mailbox_cache[$mailbox][$mode])) 677 return $a_mailbox_cache[$mailbox][$mode]; 678 679 if (!is_array($a_mailbox_cache[$mailbox])) 680 $a_mailbox_cache[$mailbox] = array(); 577 if (!$force && is_array($a_folder_cache[$folder]) && isset($a_folder_cache[$folder][$mode])) { 578 return $a_folder_cache[$folder][$mode]; 579 } 580 581 if (!is_array($a_folder_cache[$folder])) { 582 $a_folder_cache[$folder] = array(); 583 } 681 584 682 585 if ($mode == 'THREADS') { 683 $res = $this->fetch_threads($ mailbox, $force);586 $res = $this->fetch_threads($folder, $force); 684 587 $count = $res->count(); 685 588 686 589 if ($status) { 687 $msg_count = $res->countMessages(); 688 $this->set_folder_stats($mailbox, 'cnt', $msg_count); 689 $this->set_folder_stats($mailbox, 'maxuid', $msg_count ? $this->id2uid($msg_count, $mailbox) : 0); 690 } 590 $msg_count = $res->count_messages(); 591 $this->set_folder_stats($folder, 'cnt', $msg_count); 592 $this->set_folder_stats($folder, 'maxuid', $msg_count ? $this->id2uid($msg_count, $folder) : 0); 593 } 594 } 595 // Need connection here 596 else if (!$this->check_connection()) { 597 return 0; 691 598 } 692 599 // RECENT count is fetched a bit different 693 600 else if ($mode == 'RECENT') { 694 $count = $this->conn->countRecent($ mailbox);601 $count = $this->conn->countRecent($folder); 695 602 } 696 603 // use SEARCH for message counting 697 else if ( $this->skip_deleted) {604 else if (!empty($this->options['skip_deleted'])) { 698 605 $search_str = "ALL UNDELETED"; 699 606 $keys = array('COUNT'); … … 715 622 // get message count using (E)SEARCH 716 623 // not very performant but more precise (using UNDELETED) 717 $index = $this->conn->search($ mailbox, $search_str, true, $keys);624 $index = $this->conn->search($folder, $search_str, true, $keys); 718 625 $count = $index->count(); 719 626 720 627 if ($mode == 'ALL') { 721 // Cache index data, will be used in message_index_direct()628 // Cache index data, will be used in index_direct() 722 629 $this->icache['undeleted_idx'] = $index; 723 630 724 631 if ($status) { 725 $this->set_folder_stats($ mailbox, 'cnt', $count);726 $this->set_folder_stats($ mailbox, 'maxuid', $index->max());632 $this->set_folder_stats($folder, 'cnt', $count); 633 $this->set_folder_stats($folder, 'maxuid', $index->max()); 727 634 } 728 635 } 729 636 } 730 637 else { 731 if ($mode == 'UNSEEN') 732 $count = $this->conn->countUnseen($mailbox); 638 if ($mode == 'UNSEEN') { 639 $count = $this->conn->countUnseen($folder); 640 } 733 641 else { 734 $count = $this->conn->countMessages($ mailbox);642 $count = $this->conn->countMessages($folder); 735 643 if ($status) { 736 $this->set_folder_stats($ mailbox,'cnt', $count);737 $this->set_folder_stats($ mailbox, 'maxuid', $count ? $this->id2uid($count, $mailbox) : 0);738 } 739 } 740 } 741 742 $a_ mailbox_cache[$mailbox][$mode] = (int)$count;644 $this->set_folder_stats($folder,'cnt', $count); 645 $this->set_folder_stats($folder, 'maxuid', $count ? $this->id2uid($count, $folder) : 0); 646 } 647 } 648 } 649 650 $a_folder_cache[$folder][$mode] = (int)$count; 743 651 744 652 // write back to cache 745 $this->update_cache('messagecount', $a_ mailbox_cache);653 $this->update_cache('messagecount', $a_folder_cache); 746 654 747 655 return (int)$count; … … 751 659 /** 752 660 * Public method for listing headers 753 * convert mailbox name with root dir first 754 * 755 * @param string $mailbox Mailbox/folder name 661 * 662 * @param string $folder Folder name 756 663 * @param int $page Current page to list 757 664 * @param string $sort_field Header field to sort by … … 760 667 * 761 668 * @return array Indexed array with message header objects 762 * @access public 763 */ 764 public function list_headers($mailbox='', $page=NULL, $sort_field=NULL, $sort_order=NULL, $slice=0) 765 { 766 if (!strlen($mailbox)) { 767 $mailbox = $this->mailbox; 768 } 769 770 return $this->_list_headers($mailbox, $page, $sort_field, $sort_order, $slice); 771 } 772 773 774 /** 775 * Private method for listing message headers 776 * 777 * @param string $mailbox Mailbox name 669 */ 670 public function list_messages($folder='', $page=NULL, $sort_field=NULL, $sort_order=NULL, $slice=0) 671 { 672 if (!strlen($folder)) { 673 $folder = $this->folder; 674 } 675 676 return $this->_list_messages($folder, $page, $sort_field, $sort_order, $slice); 677 } 678 679 680 /** 681 * protected method for listing message headers 682 * 683 * @param string $folder Folder name 778 684 * @param int $page Current page to list 779 685 * @param string $sort_field Header field to sort by … … 782 688 * 783 689 * @return array Indexed array with message header objects 784 * @see rcube_imap::list_ headers785 */ 786 pr ivate function _list_headers($mailbox='', $page=NULL, $sort_field=NULL, $sort_order=NULL, $slice=0)787 { 788 if (!strlen($ mailbox)) {690 * @see rcube_imap::list_messages 691 */ 692 protected function _list_messages($folder='', $page=NULL, $sort_field=NULL, $sort_order=NULL, $slice=0) 693 { 694 if (!strlen($folder)) { 789 695 return array(); 790 696 } … … 794 700 795 701 // use saved message set 796 if ($this->search_string && $ mailbox == $this->mailbox) {797 return $this-> _list_header_set($mailbox, $page, $slice);702 if ($this->search_string && $folder == $this->folder) { 703 return $this->list_search_messages($folder, $page, $slice); 798 704 } 799 705 800 706 if ($this->threading) { 801 return $this-> _list_thread_headers($mailbox, $page, $slice);707 return $this->list_thread_messages($folder, $page, $slice); 802 708 } 803 709 804 710 // get UIDs of all messages in the folder, sorted 805 $index = $this-> message_index($mailbox, $this->sort_field, $this->sort_order);806 807 if ($index->is Empty()) {711 $index = $this->index($folder, $this->sort_field, $this->sort_order); 712 713 if ($index->is_empty()) { 808 714 return array(); 809 715 } … … 814 720 $index->slice($from, $to - $from); 815 721 816 if ($slice) 722 if ($slice) { 817 723 $index->slice(-$slice, $slice); 724 } 818 725 819 726 // fetch reqested messages headers 820 727 $a_index = $index->get(); 821 $a_msg_headers = $this->fetch_headers($ mailbox, $a_index);728 $a_msg_headers = $this->fetch_headers($folder, $a_index); 822 729 823 730 return array_values($a_msg_headers); … … 826 733 827 734 /** 828 * Privatemethod for listing message headers using threads829 * 830 * @param string $ mailbox Mailbox/folder name735 * protected method for listing message headers using threads 736 * 737 * @param string $folder Folder name 831 738 * @param int $page Current page to list 832 739 * @param int $slice Number of slice items to extract from result array 833 740 * 834 741 * @return array Indexed array with message header objects 835 * @see rcube_imap::list_ headers836 */ 837 pr ivate function _list_thread_headers($mailbox, $page, $slice=0)742 * @see rcube_imap::list_messages 743 */ 744 protected function list_thread_messages($folder, $page, $slice=0) 838 745 { 839 746 // get all threads (not sorted) 840 if ($mcache = $this->get_mcache_engine()) 841 $threads = $mcache->get_thread($mailbox); 842 else 843 $threads = $this->fetch_threads($mailbox); 844 845 return $this->_fetch_thread_headers($mailbox, $threads, $page, $slice); 846 } 847 747 if ($mcache = $this->get_mcache_engine()) { 748 $threads = $mcache->get_thread($folder); 749 } 750 else { 751 $threads = $this->fetch_threads($folder); 752 } 753 754 return $this->fetch_thread_headers($folder, $threads, $page, $slice); 755 } 848 756 849 757 /** 850 758 * Method for fetching threads data 851 759 * 852 * @param string $ mailboxFolder name853 * @param bool $force Use IMAP server, no cache760 * @param string $folder Folder name 761 * @param bool $force Use IMAP server, no cache 854 762 * 855 763 * @return rcube_imap_thread Thread data object 856 764 */ 857 function fetch_threads($ mailbox, $force = false)765 function fetch_threads($folder, $force = false) 858 766 { 859 767 if (!$force && ($mcache = $this->get_mcache_engine())) { 860 768 // don't store in self's internal cache, cache has it's own internal cache 861 return $mcache->get_thread($ mailbox);769 return $mcache->get_thread($folder); 862 770 } 863 771 864 772 if (empty($this->icache['threads'])) { 773 if (!$this->check_connection()) { 774 return new rcube_result_thread(); 775 } 776 865 777 // get all threads 866 $result = $this->conn->thread($ mailbox, $this->threading,867 $this-> skip_deleted? 'UNDELETED' : '', true);778 $result = $this->conn->thread($folder, $this->threading, 779 $this->options['skip_deleted'] ? 'UNDELETED' : '', true); 868 780 869 781 // add to internal (fast) cache … … 876 788 877 789 /** 878 * Privatemethod for fetching threaded messages headers879 * 880 * @param string $ mailbox Mailboxname790 * protected method for fetching threaded messages headers 791 * 792 * @param string $folder Folder name 881 793 * @param rcube_result_thread $threads Threads data object 882 794 * @param int $page List page number … … 884 796 * 885 797 * @return array Messages headers 886 * @access private 887 */ 888 private function _fetch_thread_headers($mailbox, $threads, $page, $slice=0) 798 */ 799 protected function fetch_thread_headers($folder, $threads, $page, $slice=0) 889 800 { 890 801 // Sort thread structure … … 896 807 $threads->slice($from, $to - $from); 897 808 898 if ($slice) 809 if ($slice) { 899 810 $threads->slice(-$slice, $slice); 811 } 900 812 901 813 // Get UIDs of all messages in all threads … … 903 815 904 816 // fetch reqested headers from server 905 $a_msg_headers = $this->fetch_headers($ mailbox, $a_index);817 $a_msg_headers = $this->fetch_headers($folder, $a_index); 906 818 907 819 unset($a_index); 908 820 909 821 // Set depth, has_children and unread_children fields in headers 910 $this-> _set_thread_flags($a_msg_headers, $threads);822 $this->set_thread_flags($a_msg_headers, $threads); 911 823 912 824 return array_values($a_msg_headers); … … 915 827 916 828 /** 917 * Privatemethod for setting threaded messages flags:829 * protected method for setting threaded messages flags: 918 830 * depth, has_children and unread_children 919 831 * … … 922 834 * 923 835 * @return array Message headers array indexed by message UID 924 * @access private 925 */ 926 private function _set_thread_flags(&$headers, $threads) 836 */ 837 protected function set_thread_flags(&$headers, $threads) 927 838 { 928 839 $parents = array(); 929 840 930 list ($msg_depth, $msg_children) = $threads->get ThreadData();841 list ($msg_depth, $msg_children) = $threads->get_thread_data(); 931 842 932 843 foreach ($headers as $uid => $header) { … … 948 859 949 860 /** 950 * Privatemethod for listing a set of message headers (search results)951 * 952 * @param string $ mailbox Mailbox/folder name861 * protected method for listing a set of message headers (search results) 862 * 863 * @param string $folder Folder name 953 864 * @param int $page Current page to list 954 865 * @param int $slice Number of slice items to extract from result array 955 866 * 956 867 * @return array Indexed array with message header objects 957 * @access private 958 */ 959 private function _list_header_set($mailbox, $page, $slice=0) 960 { 961 if (!strlen($mailbox) || empty($this->search_set) || $this->search_set->isEmpty()) { 868 */ 869 protected function list_search_messages($folder, $page, $slice=0) 870 { 871 if (!strlen($folder) || empty($this->search_set) || $this->search_set->is_empty()) { 962 872 return array(); 963 873 } … … 965 875 // use saved messages from searching 966 876 if ($this->threading) { 967 return $this-> _list_thread_header_set($mailbox, $page, $slice);877 return $this->list_search_thread_messages($folder, $page, $slice); 968 878 } 969 879 … … 978 888 979 889 // return empty array if no messages found 980 if ($index->is Empty())890 if ($index->is_empty()) { 981 891 return array(); 892 } 982 893 983 894 // quickest method (default sorting) … … 995 906 996 907 // return empty array if no messages found 997 if ($index->is Empty())908 if ($index->is_empty()) { 998 909 return array(); 910 } 999 911 } 1000 912 } 1001 913 1002 914 if ($got_index) { 1003 if ($this->sort_order != $index->get Parameters('ORDER')) {915 if ($this->sort_order != $index->get_parameters('ORDER')) { 1004 916 $index->revert(); 1005 917 } … … 1008 920 $index->slice($from, $to-$from); 1009 921 1010 if ($slice) 922 if ($slice) { 1011 923 $index->slice(-$slice, $slice); 924 } 1012 925 1013 926 // fetch headers 1014 927 $a_index = $index->get(); 1015 $a_msg_headers = $this->fetch_headers($ mailbox, $a_index);928 $a_msg_headers = $this->fetch_headers($folder, $a_index); 1016 929 1017 930 return array_values($a_msg_headers); … … 1024 937 if (($cnt > 300 && $cnt > $this->page_size) || !$this->sort_field) { 1025 938 // use memory less expensive (and quick) method for big result set 1026 $index = clone $this-> message_index('', $this->sort_field, $this->sort_order);939 $index = clone $this->index('', $this->sort_field, $this->sort_order); 1027 940 // get messages uids for one page... 1028 941 $index->slice($start_msg, min($cnt-$from, $this->page_size)); 1029 942 1030 if ($slice) 943 if ($slice) { 1031 944 $index->slice(-$slice, $slice); 945 } 1032 946 1033 947 // ...and fetch headers 1034 948 $a_index = $index->get(); 1035 $a_msg_headers = $this->fetch_headers($ mailbox, $a_index);949 $a_msg_headers = $this->fetch_headers($folder, $a_index); 1036 950 1037 951 return array_values($a_msg_headers); … … 1040 954 // for small result set we can fetch all messages headers 1041 955 $a_index = $index->get(); 1042 $a_msg_headers = $this->fetch_headers($ mailbox, $a_index, false);956 $a_msg_headers = $this->fetch_headers($folder, $a_index, false); 1043 957 1044 958 // return empty array if no messages found 1045 if (!is_array($a_msg_headers) || empty($a_msg_headers)) 959 if (!is_array($a_msg_headers) || empty($a_msg_headers)) { 1046 960 return array(); 961 } 962 963 if (!$this->check_connection()) { 964 return array(); 965 } 1047 966 1048 967 // if not already sorted … … 1054 973 $from, min($cnt-$to, $this->page_size)); 1055 974 1056 if ($slice) 975 if ($slice) { 1057 976 $a_msg_headers = array_slice($a_msg_headers, -$slice, $slice); 977 } 1058 978 1059 979 return $a_msg_headers; … … 1063 983 1064 984 /** 1065 * Privatemethod for listing a set of threaded message headers (search results)1066 * 1067 * @param string $ mailbox Mailbox/folder name985 * protected method for listing a set of threaded message headers (search results) 986 * 987 * @param string $folder Folder name 1068 988 * @param int $page Current page to list 1069 989 * @param int $slice Number of slice items to extract from result array 1070 990 * 1071 991 * @return array Indexed array with message header objects 1072 * @access private 1073 * @see rcube_imap::list_header_set() 1074 */ 1075 private function _list_thread_header_set($mailbox, $page, $slice=0) 992 * @see rcube_imap::list_search_messages() 993 */ 994 protected function list_search_thread_messages($folder, $page, $slice=0) 1076 995 { 1077 996 // update search_set if previous data was fetched with disabled threading 1078 997 if (!$this->search_threads) { 1079 if ($this->search_set->is Empty())998 if ($this->search_set->is_empty()) { 1080 999 return array(); 1000 } 1081 1001 $this->search('', $this->search_string, $this->search_charset, $this->sort_field); 1082 1002 } 1083 1003 1084 return $this-> _fetch_thread_headers($mailbox, clone $this->search_set, $page, $slice);1004 return $this->fetch_thread_headers($folder, clone $this->search_set, $page, $slice); 1085 1005 } 1086 1006 … … 1089 1009 * Fetches messages headers (by UID) 1090 1010 * 1091 * @param string $ mailbox Mailboxname1011 * @param string $folder Folder name 1092 1012 * @param array $msgs Message UIDs 1093 1013 * @param bool $sort Enables result sorting by $msgs … … 1095 1015 * 1096 1016 * @return array Messages headers indexed by UID 1097 * @access private 1098 */ 1099 function fetch_headers($mailbox, $msgs, $sort = true, $force = false) 1100 { 1101 if (empty($msgs)) 1017 */ 1018 function fetch_headers($folder, $msgs, $sort = true, $force = false) 1019 { 1020 if (empty($msgs)) { 1102 1021 return array(); 1022 } 1103 1023 1104 1024 if (!$force && ($mcache = $this->get_mcache_engine())) { 1105 $headers = $mcache->get_messages($mailbox, $msgs); 1025 $headers = $mcache->get_messages($folder, $msgs); 1026 } 1027 else if (!$this->check_connection()) { 1028 return array(); 1106 1029 } 1107 1030 else { 1108 1031 // fetch reqested headers from server 1109 1032 $headers = $this->conn->fetchHeaders( 1110 $ mailbox, $msgs, true, false, $this->get_fetch_headers());1111 } 1112 1113 if (empty($headers)) 1033 $folder, $msgs, true, false, $this->get_fetch_headers()); 1034 } 1035 1036 if (empty($headers)) { 1114 1037 return array(); 1038 } 1115 1039 1116 1040 foreach ($headers as $h) { … … 1130 1054 1131 1055 /** 1132 * Returns current status of mailbox1056 * Returns current status of folder 1133 1057 * 1134 1058 * We compare the maximum UID to determine the number of 1135 1059 * new messages because the RECENT flag is not reliable. 1136 1060 * 1137 * @param string $mailbox Mailbox/folder name 1061 * @param string $folder Folder name 1062 * 1138 1063 * @return int Folder status 1139 1064 */ 1140 public function mailbox_status($mailbox= null)1141 { 1142 if (!strlen($ mailbox)) {1143 $ mailbox = $this->mailbox;1144 } 1145 $old = $this->get_folder_stats($ mailbox);1065 public function folder_status($folder = null) 1066 { 1067 if (!strlen($folder)) { 1068 $folder = $this->folder; 1069 } 1070 $old = $this->get_folder_stats($folder); 1146 1071 1147 1072 // refresh message count -> will update 1148 $this-> _messagecount($mailbox, 'ALL', true);1073 $this->messagecount($folder, 'ALL', true); 1149 1074 1150 1075 $result = 0; … … 1154 1079 } 1155 1080 1156 $new = $this->get_folder_stats($ mailbox);1081 $new = $this->get_folder_stats($folder); 1157 1082 1158 1083 // got new messages 1159 if ($new['maxuid'] > $old['maxuid']) 1084 if ($new['maxuid'] > $old['maxuid']) { 1160 1085 $result += 1; 1086 } 1161 1087 // some messages has been deleted 1162 if ($new['cnt'] < $old['cnt']) 1088 if ($new['cnt'] < $old['cnt']) { 1163 1089 $result += 2; 1090 } 1164 1091 1165 1092 // @TODO: optional checking for messages flags changes (?) … … 1174 1101 * @TODO: move to separate DB table (cache?) 1175 1102 * 1176 * @param string $ mailbox Mailboxname1103 * @param string $folder Folder name 1177 1104 * @param string $name Data name 1178 1105 * @param mixed $data Data value 1179 1106 */ 1180 pr ivate function set_folder_stats($mailbox, $name, $data)1181 { 1182 $_SESSION['folders'][$ mailbox][$name] = $data;1107 protected function set_folder_stats($folder, $name, $data) 1108 { 1109 $_SESSION['folders'][$folder][$name] = $data; 1183 1110 } 1184 1111 … … 1187 1114 * Gets folder statistic data 1188 1115 * 1189 * @param string $ mailbox Mailboxname1116 * @param string $folder Folder name 1190 1117 * 1191 1118 * @return array Stats data 1192 1119 */ 1193 private function get_folder_stats($mailbox) 1194 { 1195 if ($_SESSION['folders'][$mailbox]) 1196 return (array) $_SESSION['folders'][$mailbox]; 1197 else 1198 return array(); 1120 protected function get_folder_stats($folder) 1121 { 1122 if ($_SESSION['folders'][$folder]) { 1123 return (array) $_SESSION['folders'][$folder]; 1124 } 1125 1126 return array(); 1199 1127 } 1200 1128 … … 1203 1131 * Return sorted list of message UIDs 1204 1132 * 1205 * @param string $ mailbox Mailboxto get index from1133 * @param string $folder Folder to get index from 1206 1134 * @param string $sort_field Sort column 1207 1135 * @param string $sort_order Sort order [ASC, DESC] … … 1209 1137 * @return rcube_result_index|rcube_result_thread List of messages (UIDs) 1210 1138 */ 1211 public function message_index($mailbox='', $sort_field=NULL, $sort_order=NULL) 1212 { 1213 if ($this->threading) 1214 return $this->thread_index($mailbox, $sort_field, $sort_order); 1139 public function index($folder = '', $sort_field = NULL, $sort_order = NULL) 1140 { 1141 if ($this->threading) { 1142 return $this->thread_index($folder, $sort_field, $sort_order); 1143 } 1215 1144 1216 1145 $this->set_sort_order($sort_field, $sort_order); 1217 1146 1218 if (!strlen($ mailbox)) {1219 $ mailbox = $this->mailbox;1147 if (!strlen($folder)) { 1148 $folder = $this->folder; 1220 1149 } 1221 1150 … … 1223 1152 if ($this->search_string) { 1224 1153 if ($this->search_threads) { 1225 $this->search($ mailbox, $this->search_string, $this->search_charset, $this->sort_field);1154 $this->search($folder, $this->search_string, $this->search_charset, $this->sort_field); 1226 1155 } 1227 1156 … … 1229 1158 if (!$this->sort_field || $this->search_sorted) { 1230 1159 if ($this->sort_field && $this->search_sort_field != $this->sort_field) { 1231 $this->search($ mailbox, $this->search_string, $this->search_charset, $this->sort_field);1160 $this->search($folder, $this->search_string, $this->search_charset, $this->sort_field); 1232 1161 } 1233 1162 $index = $this->search_set; 1234 1163 } 1164 else if (!$this->check_connection()) { 1165 return new rcube_result_index(); 1166 } 1235 1167 else { 1236 $index = $this->conn->index($ mailbox, $this->search_set->get(),1237 $this->sort_field, $this-> skip_deleted, true, true);1238 } 1239 1240 if ($this->sort_order != $index->get Parameters('ORDER')) {1168 $index = $this->conn->index($folder, $this->search_set->get(), 1169 $this->sort_field, $this->options['skip_deleted'], true, true); 1170 } 1171 1172 if ($this->sort_order != $index->get_parameters('ORDER')) { 1241 1173 $index->revert(); 1242 1174 } … … 1247 1179 // check local cache 1248 1180 if ($mcache = $this->get_mcache_engine()) { 1249 $index = $mcache->get_index($ mailbox, $this->sort_field, $this->sort_order);1181 $index = $mcache->get_index($folder, $this->sort_field, $this->sort_order); 1250 1182 } 1251 1183 // fetch from IMAP server 1252 1184 else { 1253 $index = $this-> message_index_direct(1254 $ mailbox, $this->sort_field, $this->sort_order);1185 $index = $this->index_direct( 1186 $folder, $this->sort_field, $this->sort_order); 1255 1187 } 1256 1188 … … 1263 1195 * Doesn't uses cache by default. 1264 1196 * 1265 * @param string $ mailbox Mailboxto get index from1197 * @param string $folder Folder to get index from 1266 1198 * @param string $sort_field Sort column 1267 1199 * @param string $sort_order Sort order [ASC, DESC] … … 1270 1202 * @return rcube_result_index Sorted list of message UIDs 1271 1203 */ 1272 public function message_index_direct($mailbox, $sort_field = null, $sort_order = null, $skip_cache = true)1204 public function index_direct($folder, $sort_field = null, $sort_order = null, $skip_cache = true) 1273 1205 { 1274 1206 if (!$skip_cache && ($mcache = $this->get_mcache_engine())) { 1275 $index = $mcache->get_index($ mailbox, $sort_field, $sort_order);1207 $index = $mcache->get_index($folder, $sort_field, $sort_order); 1276 1208 } 1277 1209 // use message index sort as default sorting 1278 1210 else if (!$sort_field) { 1279 if ($this-> skip_deleted&& !empty($this->icache['undeleted_idx'])1280 && $this->icache['undeleted_idx']->get Parameters('MAILBOX') == $mailbox1211 if ($this->options['skip_deleted'] && !empty($this->icache['undeleted_idx']) 1212 && $this->icache['undeleted_idx']->get_parameters('MAILBOX') == $folder 1281 1213 ) { 1282 1214 $index = $this->icache['undeleted_idx']; 1283 1215 } 1216 else if (!$this->check_connection()) { 1217 return new rcube_result_index(); 1218 } 1284 1219 else { 1285 $index = $this->conn->search($mailbox, 1286 'ALL' .($this->skip_deleted ? ' UNDELETED' : ''), true); 1287 } 1220 $index = $this->conn->search($folder, 1221 'ALL' .($this->options['skip_deleted'] ? ' UNDELETED' : ''), true); 1222 } 1223 } 1224 else if (!$this->check_connection()) { 1225 return new rcube_result_index(); 1288 1226 } 1289 1227 // fetch complete message index 1290 1228 else { 1291 1229 if ($this->get_capability('SORT')) { 1292 $index = $this->conn->sort($ mailbox, $sort_field,1293 $this-> skip_deleted? 'UNDELETED' : '', true);1294 } 1295 1296 if (empty($index) || $index->is Error()) {1297 $index = $this->conn->index($ mailbox, "1:*", $sort_field,1298 $this-> skip_deleted, false, true);1299 } 1300 } 1301 1302 if ($sort_order != $index->get Parameters('ORDER')) {1230 $index = $this->conn->sort($folder, $sort_field, 1231 $this->options['skip_deleted'] ? 'UNDELETED' : '', true); 1232 } 1233 1234 if (empty($index) || $index->is_error()) { 1235 $index = $this->conn->index($folder, "1:*", $sort_field, 1236 $this->options['skip_deleted'], false, true); 1237 } 1238 } 1239 1240 if ($sort_order != $index->get_parameters('ORDER')) { 1303 1241 $index->revert(); 1304 1242 } … … 1311 1249 * Return index of threaded message UIDs 1312 1250 * 1313 * @param string $ mailbox Mailboxto get index from1251 * @param string $folder Folder to get index from 1314 1252 * @param string $sort_field Sort column 1315 1253 * @param string $sort_order Sort order [ASC, DESC] … … 1317 1255 * @return rcube_result_thread Message UIDs 1318 1256 */ 1319 function thread_index($mailbox='', $sort_field=NULL, $sort_order=NULL)1320 { 1321 if (!strlen($ mailbox)) {1322 $ mailbox = $this->mailbox;1257 public function thread_index($folder='', $sort_field=NULL, $sort_order=NULL) 1258 { 1259 if (!strlen($folder)) { 1260 $folder = $this->folder; 1323 1261 } 1324 1262 1325 1263 // we have a saved search result, get index from there 1326 if ($this->search_string && $this->search_threads && $ mailbox == $this->mailbox) {1264 if ($this->search_string && $this->search_threads && $folder == $this->folder) { 1327 1265 $threads = $this->search_set; 1328 1266 } 1329 1267 else { 1330 1268 // get all threads (default sort order) 1331 $threads = $this->fetch_threads($ mailbox);1269 $threads = $this->fetch_threads($folder); 1332 1270 } 1333 1271 … … 1344 1282 * @param rcube_result_thread $threads Threads result set 1345 1283 */ 1346 pr ivatefunction sort_threads($threads)1347 { 1348 if ($threads->is Empty()) {1284 protected function sort_threads($threads) 1285 { 1286 if ($threads->is_empty()) { 1349 1287 return; 1350 1288 } … … 1355 1293 1356 1294 if ($this->sort_field && ($this->sort_field != 'date' || $this->get_capability('THREAD') != 'REFS')) { 1357 $index = $this-> message_index_direct($this->mailbox, $this->sort_field, $this->sort_order, false);1358 1359 if (!$index->is Empty()) {1295 $index = $this->index_direct($this->folder, $this->sort_field, $this->sort_order, false); 1296 1297 if (!$index->is_empty()) { 1360 1298 $threads->sort($index); 1361 1299 } 1362 1300 } 1363 1301 else { 1364 if ($this->sort_order != $threads->get Parameters('ORDER')) {1302 if ($this->sort_order != $threads->get_parameters('ORDER')) { 1365 1303 $threads->revert(); 1366 1304 } … … 1372 1310 * Invoke search request to IMAP server 1373 1311 * 1374 * @param string $ mailbox Mailboxname to search in1312 * @param string $folder Folder name to search in 1375 1313 * @param string $str Search criteria 1376 1314 * @param string $charset Search charset 1377 1315 * @param string $sort_field Header field to sort by 1378 * @access public1316 * 1379 1317 * @todo: Search criteria should be provided in non-IMAP format, eg. array 1380 1318 */ 1381 function search($mailbox='', $str='ALL', $charset=NULL, $sort_field=NULL)1382 { 1383 if (!$str) 1319 public function search($folder='', $str='ALL', $charset=NULL, $sort_field=NULL) 1320 { 1321 if (!$str) { 1384 1322 $str = 'ALL'; 1323 } 1324 1325 if (!strlen($folder)) { 1326 $folder = $this->folder; 1327 } 1328 1329 $results = $this->search_index($folder, $str, $charset, $sort_field); 1330 1331 $this->set_search_set(array($str, $results, $charset, $sort_field, 1332 $this->threading || $this->search_sorted ? true : false)); 1333 } 1334 1335 1336 /** 1337 * Direct (real and simple) SEARCH request (without result sorting and caching). 1338 * 1339 * @param string $mailbox Mailbox name to search in 1340 * @param string $str Search string 1341 * 1342 * @return rcube_result_index Search result (UIDs) 1343 */ 1344 public function search_once($mailbox = null, $str = 'ALL') 1345 { 1346 if (!$str) { 1347 return 'ALL'; 1348 } 1385 1349 1386 1350 if (!strlen($mailbox)) { … … 1388 1352 } 1389 1353 1390 $results = $this->_search_index($mailbox, $str, $charset, $sort_field); 1391 1392 $this->set_search_set(array($str, $results, $charset, $sort_field, 1393 $this->threading || $this->search_sorted ? true : false)); 1394 } 1395 1396 1397 /** 1398 * Private search method 1399 * 1400 * @param string $mailbox Mailbox name 1354 if (!$this->check_connection()) { 1355 return new rcube_result_index(); 1356 } 1357 1358 $index = $this->conn->search($mailbox, $str, true); 1359 1360 return $index; 1361 } 1362 1363 1364 /** 1365 * protected search method 1366 * 1367 * @param string $folder Folder name 1401 1368 * @param string $criteria Search criteria 1402 1369 * @param string $charset Charset … … 1406 1373 * @see rcube_imap::search() 1407 1374 */ 1408 pr ivate function _search_index($mailbox, $criteria='ALL', $charset=NULL, $sort_field=NULL)1375 protected function search_index($folder, $criteria='ALL', $charset=NULL, $sort_field=NULL) 1409 1376 { 1410 1377 $orig_criteria = $criteria; 1411 1378 1412 if ($this->skip_deleted && !preg_match('/UNDELETED/', $criteria)) 1379 if (!$this->check_connection()) { 1380 if ($this->threading) { 1381 return new rcube_result_thread(); 1382 } 1383 else { 1384 return new rcube_result_index(); 1385 } 1386 } 1387 1388 if ($this->options['skip_deleted'] && !preg_match('/UNDELETED/', $criteria)) { 1413 1389 $criteria = 'UNDELETED '.$criteria; 1390 } 1414 1391 1415 1392 if ($this->threading) { 1416 $threads = $this->conn->thread($ mailbox, $this->threading, $criteria, true, $charset);1393 $threads = $this->conn->thread($folder, $this->threading, $criteria, true, $charset); 1417 1394 1418 1395 // Error, try with US-ASCII (RFC5256: SORT/THREAD must support US-ASCII and UTF-8, 1419 1396 // but I've seen that Courier doesn't support UTF-8) 1420 if ($threads->is Error() && $charset && $charset != 'US-ASCII')1421 $threads = $this->conn->thread($ mailbox, $this->threading,1397 if ($threads->is_error() && $charset && $charset != 'US-ASCII') { 1398 $threads = $this->conn->thread($folder, $this->threading, 1422 1399 $this->convert_criteria($criteria, $charset), true, 'US-ASCII'); 1400 } 1423 1401 1424 1402 return $threads; … … 1427 1405 if ($sort_field && $this->get_capability('SORT')) { 1428 1406 $charset = $charset ? $charset : $this->default_charset; 1429 $messages = $this->conn->sort($ mailbox, $sort_field, $criteria, true, $charset);1407 $messages = $this->conn->sort($folder, $sort_field, $criteria, true, $charset); 1430 1408 1431 1409 // Error, try with US-ASCII (RFC5256: SORT/THREAD must support US-ASCII and UTF-8, 1432 1410 // but I've seen Courier with disabled UTF-8 support) 1433 if ($messages->is Error() && $charset && $charset != 'US-ASCII')1434 $messages = $this->conn->sort($ mailbox, $sort_field,1411 if ($messages->is_error() && $charset && $charset != 'US-ASCII') { 1412 $messages = $this->conn->sort($folder, $sort_field, 1435 1413 $this->convert_criteria($criteria, $charset), true, 'US-ASCII'); 1436 1437 if (!$messages->isError()) { 1414 } 1415 1416 if (!$messages->is_error()) { 1438 1417 $this->search_sorted = true; 1439 1418 return $messages; … … 1441 1420 } 1442 1421 1443 $messages = $this->conn->search($ mailbox,1422 $messages = $this->conn->search($folder, 1444 1423 ($charset ? "CHARSET $charset " : '') . $criteria, true); 1445 1424 1446 1425 // Error, try with US-ASCII (some servers may support only US-ASCII) 1447 if ($messages->is Error() && $charset && $charset != 'US-ASCII')1448 $messages = $this->conn->search($ mailbox,1426 if ($messages->is_error() && $charset && $charset != 'US-ASCII') { 1427 $messages = $this->conn->search($folder, 1449 1428 $this->convert_criteria($criteria, $charset), true); 1429 } 1450 1430 1451 1431 $this->search_sorted = false; 1452 1432 1453 1433 return $messages; 1454 }1455 1456 1457 /**1458 * Direct (real and simple) SEARCH request to IMAP server,1459 * without result sorting and caching1460 *1461 * @param string $mailbox Mailbox name to search in1462 * @param string $str Search string1463 * @param boolean $ret_uid True if UIDs should be returned1464 *1465 * @return rcube_result_index Search result (UIDs)1466 */1467 function search_once($mailbox='', $str='ALL')1468 {1469 if (!$str)1470 return 'ALL';1471 1472 if (!strlen($mailbox)) {1473 $mailbox = $this->mailbox;1474 }1475 1476 $index = $this->conn->search($mailbox, $str, true);1477 1478 return $index;1479 1434 } 1480 1435 … … 1486 1441 * @param string $charset Original charset 1487 1442 * @param string $dest_charset Destination charset (default US-ASCII) 1443 * 1488 1444 * @return string Search string 1489 * @access private 1490 */ 1491 private function convert_criteria($str, $charset, $dest_charset='US-ASCII') 1445 */ 1446 protected function convert_criteria($str, $charset, $dest_charset='US-ASCII') 1492 1447 { 1493 1448 // convert strings to US_ASCII … … 1498 1453 $string = substr($str, $string_offset - 1, $m[0]); 1499 1454 $string = rcube_charset_convert($string, $charset, $dest_charset); 1500 if ($string === false) 1455 if ($string === false) { 1501 1456 continue; 1457 } 1502 1458 $res .= substr($str, $last, $m[1] - $last - 1) . rcube_imap_generic::escape($string); 1503 1459 $last = $m[0] + $string_offset - 1; 1504 1460 } 1505 if ($last < strlen($str)) 1461 if ($last < strlen($str)) { 1506 1462 $res .= substr($str, $last, strlen($str)-$last); 1507 } 1508 else // strings for conversion not found 1463 } 1464 } 1465 // strings for conversion not found 1466 else { 1509 1467 $res = $str; 1468 } 1510 1469 1511 1470 return $res; … … 1518 1477 * @return array Current search set 1519 1478 */ 1520 function refresh_search()1479 public function refresh_search() 1521 1480 { 1522 1481 if (!empty($this->search_string)) { … … 1531 1490 * Return message headers object of a specific message 1532 1491 * 1533 * @param int $id Message sequence ID orUID1534 * @param string $ mailbox Mailboxto read from1492 * @param int $id Message UID 1493 * @param string $folder Folder to read from 1535 1494 * @param bool $force True to skip cache 1536 1495 * 1537 1496 * @return rcube_mail_header Message headers 1538 1497 */ 1539 function get_headers($uid, $mailbox= null, $force = false)1540 { 1541 if (!strlen($ mailbox)) {1542 $ mailbox = $this->mailbox;1498 public function get_message_headers($uid, $folder = null, $force = false) 1499 { 1500 if (!strlen($folder)) { 1501 $folder = $this->folder; 1543 1502 } 1544 1503 1545 1504 // get cached headers 1546 1505 if (!$force && $uid && ($mcache = $this->get_mcache_engine())) { 1547 $headers = $mcache->get_message($mailbox, $uid); 1506 $headers = $mcache->get_message($folder, $uid); 1507 } 1508 else if (!$this->check_connection()) { 1509 $headers = false; 1548 1510 } 1549 1511 else { 1550 1512 $headers = $this->conn->fetchHeader( 1551 $ mailbox, $uid, true, true, $this->get_fetch_headers());1513 $folder, $uid, true, true, $this->get_fetch_headers()); 1552 1514 } 1553 1515 … … 1561 1523 * 1562 1524 * @param int $uid Message UID to fetch 1563 * @param string $ mailbox Mailboxto read from1525 * @param string $folder Folder to read from 1564 1526 * 1565 1527 * @return object rcube_mail_header Message data 1566 1528 */ 1567 function get_message($uid, $mailbox= null)1568 { 1569 if (!strlen($ mailbox)) {1570 $ mailbox = $this->mailbox;1529 public function get_message($uid, $folder = null) 1530 { 1531 if (!strlen($folder)) { 1532 $folder = $this->folder; 1571 1533 } 1572 1534 … … 1578 1540 } 1579 1541 1580 $headers = $this->get_ headers($uid, $mailbox);1542 $headers = $this->get_message_headers($uid, $folder); 1581 1543 1582 1544 // message doesn't exist? 1583 if (empty($headers)) 1545 if (empty($headers)) { 1584 1546 return null; 1547 } 1585 1548 1586 1549 // structure might be cached 1587 if (!empty($headers->structure)) 1550 if (!empty($headers->structure)) { 1588 1551 return $headers; 1589 1590 $this->_msg_uid = $uid; 1552 } 1553 1554 $this->msg_uid = $uid; 1555 1556 if (!$this->check_connection()) { 1557 return $headers; 1558 } 1591 1559 1592 1560 if (empty($headers->bodystructure)) { 1593 $headers->bodystructure = $this->conn->getStructure($ mailbox, $uid, true);1561 $headers->bodystructure = $this->conn->getStructure($folder, $uid, true); 1594 1562 } 1595 1563 1596 1564 $structure = $headers->bodystructure; 1597 1565 1598 if (empty($structure)) 1566 if (empty($structure)) { 1599 1567 return $headers; 1568 } 1600 1569 1601 1570 // set message charset from message headers 1602 if ($headers->charset) 1571 if ($headers->charset) { 1603 1572 $this->struct_charset = $headers->charset; 1604 else 1605 $this->struct_charset = $this->_structure_charset($structure); 1573 } 1574 else { 1575 $this->struct_charset = $this->structure_charset($structure); 1576 } 1606 1577 1607 1578 $headers->ctype = strtolower($headers->ctype); … … 1619 1590 $structure[1] = $m[2]; 1620 1591 } 1621 else 1592 else { 1622 1593 return $headers; 1623 } 1624 1625 $struct = $this->_structure_part($structure, 0, '', $headers); 1594 } 1595 } 1596 1597 $struct = $this->structure_part($structure, 0, '', $headers); 1626 1598 1627 1599 // don't trust given content-type … … 1644 1616 * @param int $count 1645 1617 * @param string $parent 1646 * @access private 1647 */ 1648 private function _structure_part($part, $count=0, $parent='', $mime_headers=null) 1618 */ 1619 protected function structure_part($part, $count=0, $parent='', $mime_headers=null) 1649 1620 { 1650 1621 $struct = new rcube_message_part; … … 1679 1650 // build parts list for headers pre-fetching 1680 1651 for ($i=0; $i<count($part); $i++) { 1681 if (!is_array($part[$i])) 1652 if (!is_array($part[$i])) { 1682 1653 break; 1654 } 1683 1655 // fetch message headers if message/rfc822 1684 1656 // or named part (could contain Content-Location header) … … 1698 1670 // headers for parts on all levels 1699 1671 if ($mime_part_headers) { 1700 $mime_part_headers = $this->conn->fetchMIMEHeaders($this-> mailbox,1701 $this-> _msg_uid, $mime_part_headers);1672 $mime_part_headers = $this->conn->fetchMIMEHeaders($this->folder, 1673 $this->msg_uid, $mime_part_headers); 1702 1674 } 1703 1675 1704 1676 $struct->parts = array(); 1705 1677 for ($i=0, $count=0; $i<count($part); $i++) { 1706 if (!is_array($part[$i])) 1678 if (!is_array($part[$i])) { 1707 1679 break; 1680 } 1708 1681 $tmp_part_id = $struct->mime_id ? $struct->mime_id.'.'.($i+1) : $i+1; 1709 $struct->parts[] = $this-> _structure_part($part[$i], ++$count, $struct->mime_id,1682 $struct->parts[] = $this->structure_part($part[$i], ++$count, $struct->mime_id, 1710 1683 $mime_part_headers[$tmp_part_id]); 1711 1684 } … … 1743 1716 if (is_array($part[2])) { 1744 1717 $struct->ctype_parameters = array(); 1745 for ($i=0; $i<count($part[2]); $i+=2) 1718 for ($i=0; $i<count($part[2]); $i+=2) { 1746 1719 $struct->ctype_parameters[strtolower($part[2][$i])] = $part[2][$i+1]; 1747 1748 if (isset($struct->ctype_parameters['charset'])) 1720 } 1721 1722 if (isset($struct->ctype_parameters['charset'])) { 1749 1723 $struct->charset = $struct->ctype_parameters['charset']; 1724 } 1750 1725 } 1751 1726 … … 1762 1737 1763 1738 // get part size 1764 if (!empty($part[6])) 1739 if (!empty($part[6])) { 1765 1740 $struct->size = intval($part[6]); 1741 } 1766 1742 1767 1743 // read part disposition 1768 1744 $di = 8; 1769 if ($struct->ctype_primary == 'text') $di += 1; 1770 else if ($struct->mimetype == 'message/rfc822') $di += 3; 1745 if ($struct->ctype_primary == 'text') { 1746 $di += 1; 1747 } 1748 else if ($struct->mimetype == 'message/rfc822') { 1749 $di += 3; 1750 } 1771 1751 1772 1752 if (is_array($part[$di]) && count($part[$di]) == 2) { 1773 1753 $struct->disposition = strtolower($part[$di][0]); 1774 1754 1775 if (is_array($part[$di][1])) 1776 for ($n=0; $n<count($part[$di][1]); $n+=2) 1755 if (is_array($part[$di][1])) { 1756 for ($n=0; $n<count($part[$di][1]); $n+=2) { 1777 1757 $struct->d_parameters[strtolower($part[$di][1][$n])] = $part[$di][1][$n+1]; 1758 } 1759 } 1778 1760 } 1779 1761 … … 1782 1764 $struct->parts = array(); 1783 1765 for ($i=0, $count=0; $i<count($part[8]); $i++) { 1784 if (!is_array($part[8][$i])) 1766 if (!is_array($part[8][$i])) { 1785 1767 break; 1786 $struct->parts[] = $this->_structure_part($part[8][$i], ++$count, $struct->mime_id); 1768 } 1769 $struct->parts[] = $this->structure_part($part[8][$i], ++$count, $struct->mime_id); 1787 1770 } 1788 1771 } … … 1793 1776 $struct->headers['content-id'] = $part[3]; 1794 1777 1795 if (empty($struct->disposition)) 1778 if (empty($struct->disposition)) { 1796 1779 $struct->disposition = 'inline'; 1780 } 1797 1781 } 1798 1782 … … 1801 1785 if (empty($mime_headers)) { 1802 1786 $mime_headers = $this->conn->fetchPartHeader( 1803 $this-> mailbox, $this->_msg_uid, true, $struct->mime_id);1804 } 1805 1806 if (is_string($mime_headers)) 1787 $this->folder, $this->msg_uid, true, $struct->mime_id); 1788 } 1789 1790 if (is_string($mime_headers)) { 1807 1791 $struct->headers = rcube_mime::parse_headers($mime_headers) + $struct->headers; 1808 else if (is_object($mime_headers)) 1792 } 1793 else if (is_object($mime_headers)) { 1809 1794 $struct->headers = get_object_vars($mime_headers) + $struct->headers; 1795 } 1810 1796 1811 1797 // get real content-type of message/rfc822 1812 1798 if ($struct->mimetype == 'message/rfc822') { 1813 1799 // single-part 1814 if (!is_array($part[8][0])) 1800 if (!is_array($part[8][0])) { 1815 1801 $struct->real_mimetype = strtolower($part[8][0] . '/' . $part[8][1]); 1802 } 1816 1803 // multi-part 1817 1804 else { 1818 for ($n=0; $n<count($part[8]); $n++) 1819 if (!is_array($part[8][$n])) 1805 for ($n=0; $n<count($part[8]); $n++) { 1806 if (!is_array($part[8][$n])) { 1820 1807 break; 1808 } 1809 } 1821 1810 $struct->real_mimetype = 'multipart/' . strtolower($part[8][$n]); 1822 1811 } … … 1824 1813 1825 1814 if ($struct->ctype_primary == 'message' && empty($struct->parts)) { 1826 if (is_array($part[8]) && $di != 8) 1827 $struct->parts[] = $this->_structure_part($part[8], ++$count, $struct->mime_id); 1815 if (is_array($part[8]) && $di != 8) { 1816 $struct->parts[] = $this->structure_part($part[8], ++$count, $struct->mime_id); 1817 } 1828 1818 } 1829 1819 } 1830 1820 1831 1821 // normalize filename property 1832 $this-> _set_part_filename($struct, $mime_headers);1822 $this->set_part_filename($struct, $mime_headers); 1833 1823 1834 1824 return $struct; … … 1841 1831 * @param rcube_message_part $part Part object 1842 1832 * @param string $headers Part's raw headers 1843 * @access private 1844 */ 1845 private function _set_part_filename(&$part, $headers=null) 1846 { 1847 if (!empty($part->d_parameters['filename'])) 1833 */ 1834 protected function set_part_filename(&$part, $headers=null) 1835 { 1836 if (!empty($part->d_parameters['filename'])) { 1848 1837 $filename_mime = $part->d_parameters['filename']; 1849 else if (!empty($part->d_parameters['filename*'])) 1838 } 1839 else if (!empty($part->d_parameters['filename*'])) { 1850 1840 $filename_encoded = $part->d_parameters['filename*']; 1851 else if (!empty($part->ctype_parameters['name*'])) 1841 } 1842 else if (!empty($part->ctype_parameters['name*'])) { 1852 1843 $filename_encoded = $part->ctype_parameters['name*']; 1844 } 1853 1845 // RFC2231 value continuations 1854 1846 // TODO: this should be rewrited to support RFC2231 4.1 combinations … … 1864 1856 if (!$headers) { 1865 1857 $headers = $this->conn->fetchPartHeader( 1866 $this-> mailbox, $this->_msg_uid, true, $part->mime_id);1858 $this->folder, $this->msg_uid, true, $part->mime_id); 1867 1859 } 1868 1860 $filename_mime = ''; … … 1883 1875 if (!$headers) { 1884 1876 $headers = $this->conn->fetchPartHeader( 1885 $this-> mailbox, $this->_msg_uid, true, $part->mime_id);1877 $this->folder, $this->msg_uid, true, $part->mime_id); 1886 1878 } 1887 1879 $filename_encoded = ''; … … 1902 1894 if (!$headers) { 1903 1895 $headers = $this->conn->fetchPartHeader( 1904 $this-> mailbox, $this->_msg_uid, true, $part->mime_id);1896 $this->folder, $this->msg_uid, true, $part->mime_id); 1905 1897 } 1906 1898 $filename_mime = ''; … … 1921 1913 if (!$headers) { 1922 1914 $headers = $this->conn->fetchPartHeader( 1923 $this-> mailbox, $this->_msg_uid, true, $part->mime_id);1915 $this->folder, $this->msg_uid, true, $part->mime_id); 1924 1916 } 1925 1917 $filename_encoded = ''; … … 1932 1924 } 1933 1925 // read 'name' after rfc2231 parameters as it may contains truncated filename (from Thunderbird) 1934 else if (!empty($part->ctype_parameters['name'])) 1926 else if (!empty($part->ctype_parameters['name'])) { 1935 1927 $filename_mime = $part->ctype_parameters['name']; 1928 } 1936 1929 // Content-Disposition 1937 else if (!empty($part->headers['content-description'])) 1930 else if (!empty($part->headers['content-description'])) { 1938 1931 $filename_mime = $part->headers['content-description']; 1939 else 1932 } 1933 else { 1940 1934 return; 1935 } 1941 1936 1942 1937 // decode filename 1943 1938 if (!empty($filename_mime)) { 1944 if (!empty($part->charset)) 1939 if (!empty($part->charset)) { 1945 1940 $charset = $part->charset; 1946 else if (!empty($this->struct_charset)) 1941 } 1942 else if (!empty($this->struct_charset)) { 1947 1943 $charset = $this->struct_charset; 1948 else 1944 } 1945 else { 1949 1946 $charset = rc_detect_encoding($filename_mime, $this->default_charset); 1947 } 1950 1948 1951 1949 $part->filename = rcube_mime::decode_mime_string($filename_mime, $charset); … … 1967 1965 * 1968 1966 * @param array $structure Message structure 1967 * 1969 1968 * @return string Charset name 1970 * @access private 1971 */ 1972 private function _structure_charset($structure) 1969 */ 1970 protected function structure_charset($structure) 1973 1971 { 1974 1972 while (is_array($structure)) { 1975 if (is_array($structure[2]) && $structure[2][0] == 'charset') 1973 if (is_array($structure[2]) && $structure[2][0] == 'charset') { 1976 1974 return $structure[2][1]; 1975 } 1977 1976 $structure = $structure[0]; 1978 1977 } … … 1992 1991 * @return string Message/part body if not printed 1993 1992 */ 1994 function get_message_part($uid, $part=1, $o_part=NULL, $print=NULL, $fp=NULL, $skip_charset_conv=false) 1995 { 1993 public function get_message_part($uid, $part=1, $o_part=NULL, $print=NULL, $fp=NULL, $skip_charset_conv=false) 1994 { 1995 if (!$this->check_connection()) { 1996 return null; 1997 } 1998 1996 1999 // get part data if not provided 1997 2000 if (!is_object($o_part)) { 1998 $structure = $this->conn->getStructure($this-> mailbox, $uid, true);2001 $structure = $this->conn->getStructure($this->folder, $uid, true); 1999 2002 $part_data = rcube_imap_generic::getStructurePartData($structure, $part); 2000 2003 … … 2007 2010 2008 2011 if ($o_part && $o_part->size) { 2009 $body = $this->conn->handlePartBody($this-> mailbox, $uid, true,2012 $body = $this->conn->handlePartBody($this->folder, $uid, true, 2010 2013 $part ? $part : 'TEXT', $o_part->encoding, $print, $fp); 2011 2014 } … … 2025 2028 if (!$o_part->charset || strtoupper($o_part->charset) == 'US-ASCII') { 2026 2029 // try to extract charset information from HTML meta tag (#1488125) 2027 if ($o_part->ctype_secondary == 'html' && preg_match('/<meta[^>]+charset=([a-z0-9-_]+)/i', $body, $m)) 2030 if ($o_part->ctype_secondary == 'html' && preg_match('/<meta[^>]+charset=([a-z0-9-_]+)/i', $body, $m)) { 2028 2031 $o_part->charset = strtoupper($m[1]); 2029 else 2032 } 2033 else { 2030 2034 $o_part->charset = $this->default_charset; 2035 } 2031 2036 } 2032 2037 $body = rcube_charset_convert($body, $o_part->charset); … … 2035 2040 2036 2041 return $body; 2037 }2038 2039 2040 /**2041 * Fetch message body of a specific message from the server2042 *2043 * @param int $uid Message UID2044 * @return string $part Message/part body2045 * @see rcube_imap::get_message_part()2046 */2047 function get_body($uid, $part=1)2048 {2049 $headers = $this->get_headers($uid);2050 return rcube_charset_convert($this->get_message_part($uid, $part, NULL),2051 $headers->charset ? $headers->charset : $this->default_charset);2052 2042 } 2053 2043 … … 2061 2051 * @return string Message source string 2062 2052 */ 2063 function get_raw_body($uid, $fp=null) 2064 { 2065 return $this->conn->handlePartBody($this->mailbox, $uid, 2053 public function get_raw_body($uid, $fp=null) 2054 { 2055 if (!$this->check_connection()) { 2056 return null; 2057 } 2058 2059 return $this->conn->handlePartBody($this->folder, $uid, 2066 2060 true, null, null, false, $fp); 2067 2061 } … … 2072 2066 * 2073 2067 * @param int $uid Message UID 2068 * 2074 2069 * @return string Message headers string 2075 2070 */ 2076 function get_raw_headers($uid) 2077 { 2078 return $this->conn->fetchPartHeader($this->mailbox, $uid, true); 2071 public function get_raw_headers($uid) 2072 { 2073 if (!$this->check_connection()) { 2074 return null; 2075 } 2076 2077 return $this->conn->fetchPartHeader($this->folder, $uid, true); 2079 2078 } 2080 2079 … … 2082 2081 /** 2083 2082 * Sends the whole message source to stdout 2084 * 2085 * @param int $uid Message UID 2086 */ 2087 function print_raw_body($uid) 2088 { 2089 $this->conn->handlePartBody($this->mailbox, $uid, true, NULL, NULL, true); 2083 */ 2084 public function print_raw_body($uid) 2085 { 2086 if (!$this->check_connection()) { 2087 return; 2088 } 2089 2090 $this->conn->handlePartBody($this->folder, $uid, true, NULL, NULL, true); 2090 2091 } 2091 2092 … … 2096 2097 * @param mixed $uids Message UIDs as array or comma-separated string, or '*' 2097 2098 * @param string $flag Flag to set: SEEN, UNDELETED, DELETED, RECENT, ANSWERED, DRAFT, MDNSENT 2098 * @param string $ mailboxFolder name2099 * @param string $folder Folder name 2099 2100 * @param boolean $skip_cache True to skip message cache clean up 2100 2101 * 2101 2102 * @return boolean Operation status 2102 2103 */ 2103 function set_flag($uids, $flag, $mailbox=null, $skip_cache=false) 2104 { 2105 if (!strlen($mailbox)) { 2106 $mailbox = $this->mailbox; 2104 public function set_flag($uids, $flag, $folder=null, $skip_cache=false) 2105 { 2106 if (!strlen($folder)) { 2107 $folder = $this->folder; 2108 } 2109 2110 if (!$this->check_connection()) { 2111 return false; 2107 2112 } 2108 2113 2109 2114 $flag = strtoupper($flag); 2110 list($uids, $all_mode) = $this->_parse_uids($uids, $mailbox); 2111 2112 if (strpos($flag, 'UN') === 0) 2113 $result = $this->conn->unflag($mailbox, $uids, substr($flag, 2)); 2114 else 2115 $result = $this->conn->flag($mailbox, $uids, $flag); 2115 list($uids, $all_mode) = $this->parse_uids($uids); 2116 2117 if (strpos($flag, 'UN') === 0) { 2118 $result = $this->conn->unflag($folder, $uids, substr($flag, 2)); 2119 } 2120 else { 2121 $result = $this->conn->flag($folder, $uids, $flag); 2122 } 2116 2123 2117 2124 if ($result) { … … 2121 2128 $status = strpos($flag, 'UN') !== 0; 2122 2129 $mflag = preg_replace('/^UN/', '', $flag); 2123 $mcache->change_flag($ mailbox, $all_mode ? null : explode(',', $uids),2130 $mcache->change_flag($folder, $all_mode ? null : explode(',', $uids), 2124 2131 $mflag, $status); 2125 2132 } … … 2127 2134 // clear cached counters 2128 2135 if ($flag == 'SEEN' || $flag == 'UNSEEN') { 2129 $this-> _clear_messagecount($mailbox, 'SEEN');2130 $this-> _clear_messagecount($mailbox, 'UNSEEN');2136 $this->clear_messagecount($folder, 'SEEN'); 2137 $this->clear_messagecount($folder, 'UNSEEN'); 2131 2138 } 2132 2139 else if ($flag == 'DELETED') { 2133 $this-> _clear_messagecount($mailbox, 'DELETED');2140 $this->clear_messagecount($folder, 'DELETED'); 2134 2141 } 2135 2142 } … … 2140 2147 2141 2148 /** 2142 * Remove message flag for one or several messages 2143 * 2144 * @param mixed $uids Message UIDs as array or comma-separated string, or '*' 2145 * @param string $flag Flag to unset: SEEN, DELETED, RECENT, ANSWERED, DRAFT, MDNSENT 2146 * @param string $mailbox Folder name 2147 * 2148 * @return int Number of flagged messages, -1 on failure 2149 * @see set_flag 2150 */ 2151 function unset_flag($uids, $flag, $mailbox=null) 2152 { 2153 return $this->set_flag($uids, 'UN'.$flag, $mailbox); 2154 } 2155 2156 2157 /** 2158 * Append a mail message (source) to a specific mailbox 2159 * 2160 * @param string $mailbox Target mailbox 2149 * Append a mail message (source) to a specific folder 2150 * 2151 * @param string $folder Target folder 2161 2152 * @param string $message The message source string or filename 2162 2153 * @param string $headers Headers string if $message contains only the body … … 2165 2156 * @return int|bool Appended message UID or True on success, False on error 2166 2157 */ 2167 function save_message($mailbox, &$message, $headers='', $is_file=false) 2168 { 2169 if (!strlen($mailbox)) { 2170 $mailbox = $this->mailbox; 2171 } 2172 2173 // make sure mailbox exists 2174 if ($this->mailbox_exists($mailbox)) { 2175 if ($is_file) 2176 $saved = $this->conn->appendFromFile($mailbox, $message, $headers); 2177 else 2178 $saved = $this->conn->append($mailbox, $message); 2158 public function save_message($folder, &$message, $headers='', $is_file=false) 2159 { 2160 if (!strlen($folder)) { 2161 $folder = $this->folder; 2162 } 2163 2164 // make sure folder exists 2165 if ($this->folder_exists($folder)) { 2166 if ($is_file) { 2167 $saved = $this->conn->appendFromFile($folder, $message, $headers); 2168 } 2169 else { 2170 $saved = $this->conn->append($folder, $message); 2171 } 2179 2172 } 2180 2173 2181 2174 if ($saved) { 2182 // increase messagecount of the target mailbox2183 $this-> _set_messagecount($mailbox, 'ALL', 1);2175 // increase messagecount of the target folder 2176 $this->set_messagecount($folder, 'ALL', 1); 2184 2177 } 2185 2178 … … 2189 2182 2190 2183 /** 2191 * Move a message from one mailboxto another2184 * Move a message from one folder to another 2192 2185 * 2193 2186 * @param mixed $uids Message UIDs as array or comma-separated string, or '*' 2194 * @param string $to_mbox Target mailbox 2195 * @param string $from_mbox Source mailbox 2187 * @param string $to_mbox Target folder 2188 * @param string $from_mbox Source folder 2189 * 2196 2190 * @return boolean True on success, False on error 2197 2191 */ 2198 function move_message($uids, $to_mbox, $from_mbox='')2192 public function move_message($uids, $to_mbox, $from_mbox='') 2199 2193 { 2200 2194 if (!strlen($from_mbox)) { 2201 $from_mbox = $this-> mailbox;2195 $from_mbox = $this->folder; 2202 2196 } 2203 2197 … … 2206 2200 } 2207 2201 2208 list($uids, $all_mode) = $this-> _parse_uids($uids, $from_mbox);2202 list($uids, $all_mode) = $this->parse_uids($uids); 2209 2203 2210 2204 // exit if no message uids are specified 2211 if (empty($uids)) 2205 if (empty($uids)) { 2212 2206 return false; 2213 2214 // make sure mailbox exists 2215 if ($to_mbox != 'INBOX' && !$this->mailbox_exists($to_mbox)) { 2207 } 2208 2209 if (!$this->check_connection()) { 2210 return false; 2211 } 2212 2213 // make sure folder exists 2214 if ($to_mbox != 'INBOX' && !$this->folder_exists($to_mbox)) { 2216 2215 if (in_array($to_mbox, $this->default_folders)) { 2217 if (!$this->create_ mailbox($to_mbox, true)) {2216 if (!$this->create_folder($to_mbox, true)) { 2218 2217 return false; 2219 2218 } … … 2237 2236 2238 2237 // send expunge command in order to have the moved message 2239 // really deleted from the source mailbox2238 // really deleted from the source folder 2240 2239 if ($moved) { 2241 $this-> _expunge($from_mbox, false, $uids);2242 $this-> _clear_messagecount($from_mbox);2243 $this-> _clear_messagecount($to_mbox);2240 $this->expunge_message($uids, $from_mbox, false); 2241 $this->clear_messagecount($from_mbox); 2242 $this->clear_messagecount($to_mbox); 2244 2243 } 2245 2244 // moving failed … … 2253 2252 2254 2253 // remove message ids from search set 2255 if ($this->search_set && $from_mbox == $this-> mailbox) {2254 if ($this->search_set && $from_mbox == $this->folder) { 2256 2255 // threads are too complicated to just remove messages from set 2257 if ($this->search_threads || $all_mode) 2256 if ($this->search_threads || $all_mode) { 2258 2257 $this->refresh_search(); 2259 else 2258 } 2259 else { 2260 2260 $this->search_set->filter(explode(',', $uids)); 2261 } 2261 2262 } 2262 2263 … … 2271 2272 2272 2273 /** 2273 * Copy a message from one mailboxto another2274 * Copy a message from one folder to another 2274 2275 * 2275 2276 * @param mixed $uids Message UIDs as array or comma-separated string, or '*' 2276 * @param string $to_mbox Target mailbox 2277 * @param string $from_mbox Source mailbox 2277 * @param string $to_mbox Target folder 2278 * @param string $from_mbox Source folder 2279 * 2278 2280 * @return boolean True on success, False on error 2279 2281 */ 2280 function copy_message($uids, $to_mbox, $from_mbox='')2282 public function copy_message($uids, $to_mbox, $from_mbox='') 2281 2283 { 2282 2284 if (!strlen($from_mbox)) { 2283 $from_mbox = $this-> mailbox;2284 } 2285 2286 list($uids, $all_mode) = $this-> _parse_uids($uids, $from_mbox);2285 $from_mbox = $this->folder; 2286 } 2287 2288 list($uids, $all_mode) = $this->parse_uids($uids); 2287 2289 2288 2290 // exit if no message uids are specified … … 2291 2293 } 2292 2294 2293 // make sure mailbox exists 2294 if ($to_mbox != 'INBOX' && !$this->mailbox_exists($to_mbox)) { 2295 if (!$this->check_connection()) { 2296 return false; 2297 } 2298 2299 // make sure folder exists 2300 if ($to_mbox != 'INBOX' && !$this->folder_exists($to_mbox)) { 2295 2301 if (in_array($to_mbox, $this->default_folders)) { 2296 if (!$this->create_ mailbox($to_mbox, true)) {2302 if (!$this->create_folder($to_mbox, true)) { 2297 2303 return false; 2298 2304 } … … 2307 2313 2308 2314 if ($copied) { 2309 $this-> _clear_messagecount($to_mbox);2315 $this->clear_messagecount($to_mbox); 2310 2316 } 2311 2317 … … 2315 2321 2316 2322 /** 2317 * Mark messages as deleted and expunge mailbox2323 * Mark messages as deleted and expunge them 2318 2324 * 2319 2325 * @param mixed $uids Message UIDs as array or comma-separated string, or '*' 2320 * @param string $ mailbox Source mailbox2326 * @param string $folder Source folder 2321 2327 * 2322 2328 * @return boolean True on success, False on error 2323 2329 */ 2324 function delete_message($uids, $mailbox='')2325 { 2326 if (!strlen($ mailbox)) {2327 $ mailbox = $this->mailbox;2328 } 2329 2330 list($uids, $all_mode) = $this-> _parse_uids($uids, $mailbox);2330 public function delete_message($uids, $folder='') 2331 { 2332 if (!strlen($folder)) { 2333 $folder = $this->folder; 2334 } 2335 2336 list($uids, $all_mode) = $this->parse_uids($uids); 2331 2337 2332 2338 // exit if no message uids are specified 2333 if (empty($uids)) 2339 if (empty($uids)) { 2334 2340 return false; 2335 2336 $deleted = $this->conn->flag($mailbox, $uids, 'DELETED'); 2341 } 2342 2343 if (!$this->check_connection()) { 2344 return false; 2345 } 2346 2347 $deleted = $this->conn->flag($folder, $uids, 'DELETED'); 2337 2348 2338 2349 if ($deleted) { 2339 2350 // send expunge command in order to have the deleted message 2340 // really deleted from the mailbox2341 $this-> _expunge($mailbox, false, $uids);2342 $this-> _clear_messagecount($mailbox);2343 unset($this->uid_id_map[$ mailbox]);2351 // really deleted from the folder 2352 $this->expunge_message($uids, $folder, false); 2353 $this->clear_messagecount($folder); 2354 unset($this->uid_id_map[$folder]); 2344 2355 2345 2356 // unset threads internal cache … … 2347 2358 2348 2359 // remove message ids from search set 2349 if ($this->search_set && $ mailbox == $this->mailbox) {2360 if ($this->search_set && $folder == $this->folder) { 2350 2361 // threads are too complicated to just remove messages from set 2351 if ($this->search_threads || $all_mode) 2362 if ($this->search_threads || $all_mode) { 2352 2363 $this->refresh_search(); 2353 else 2364 } 2365 else { 2354 2366 $this->search_set->filter(explode(',', $uids)); 2367 } 2355 2368 } 2356 2369 2357 2370 // remove cached messages 2358 $this->clear_message_cache($ mailbox, $all_mode ? null : explode(',', $uids));2371 $this->clear_message_cache($folder, $all_mode ? null : explode(',', $uids)); 2359 2372 } 2360 2373 … … 2364 2377 2365 2378 /** 2366 * Clear all messages in a specific mailbox2367 *2368 * @param string $mailbox Mailbox name2369 *2370 * @return int Above 0 on success2371 */2372 function clear_mailbox($mailbox=null)2373 {2374 if (!strlen($mailbox)) {2375 $mailbox = $this->mailbox;2376 }2377 2378 // SELECT will set messages count for clearFolder()2379 if ($this->conn->select($mailbox)) {2380 $cleared = $this->conn->clearFolder($mailbox);2381 }2382 2383 // make sure the cache is cleared as well2384 if ($cleared) {2385 $this->clear_message_cache($mailbox);2386 $a_mailbox_cache = $this->get_cache('messagecount');2387 unset($a_mailbox_cache[$mailbox]);2388 $this->update_cache('messagecount', $a_mailbox_cache);2389 }2390 2391 return $cleared;2392 }2393 2394 2395 /**2396 2379 * Send IMAP expunge command and clear cache 2397 2380 * 2398 * @param string $mailbox Mailbox name 2381 * @param mixed $uids Message UIDs as array or comma-separated string, or '*' 2382 * @param string $folder Folder name 2399 2383 * @param boolean $clear_cache False if cache should not be cleared 2400 2384 * 2401 * @return boolean True on success 2402 */ 2403 function expunge($mailbox='', $clear_cache=true) 2404 { 2405 if (!strlen($mailbox)) { 2406 $mailbox = $this->mailbox; 2407 } 2408 2409 return $this->_expunge($mailbox, $clear_cache); 2410 } 2411 2412 2413 /** 2414 * Send IMAP expunge command and clear cache 2415 * 2416 * @param string $mailbox Mailbox name 2417 * @param boolean $clear_cache False if cache should not be cleared 2418 * @param mixed $uids Message UIDs as array or comma-separated string, or '*' 2419 * @return boolean True on success 2420 * @access private 2421 * @see rcube_imap::expunge() 2422 */ 2423 private function _expunge($mailbox, $clear_cache=true, $uids=NULL) 2424 { 2425 if ($uids && $this->get_capability('UIDPLUS')) 2426 list($uids, $all_mode) = $this->_parse_uids($uids, $mailbox); 2427 else 2385 * @return boolean True on success, False on failure 2386 */ 2387 public function expunge_message($uids, $folder = null, $clear_cache = true) 2388 { 2389 if ($uids && $this->get_capability('UIDPLUS')) { 2390 list($uids, $all_mode) = $this->parse_uids($uids); 2391 } 2392 else { 2428 2393 $uids = null; 2429 2430 // force mailbox selection and check if mailbox is writeable 2394 } 2395 2396 if (!strlen($folder)) { 2397 $folder = $this->folder; 2398 } 2399 2400 if (!$this->check_connection()) { 2401 return false; 2402 } 2403 2404 // force folder selection and check if folder is writeable 2431 2405 // to prevent a situation when CLOSE is executed on closed 2432 // or EXPUNGE on read-only mailbox2433 $result = $this->conn->select($ mailbox);2406 // or EXPUNGE on read-only folder 2407 $result = $this->conn->select($folder); 2434 2408 if (!$result) { 2435 2409 return false; 2436 2410 } 2411 2437 2412 if (!$this->conn->data['READ-WRITE']) { 2438 $this->conn->setError(rcube_imap_generic::ERROR_READONLY, " Mailboxis read-only");2413 $this->conn->setError(rcube_imap_generic::ERROR_READONLY, "Folder is read-only"); 2439 2414 return false; 2440 2415 } 2441 2416 2442 2417 // CLOSE(+SELECT) should be faster than EXPUNGE 2443 if (empty($uids) || $all_mode) 2418 if (empty($uids) || $all_mode) { 2444 2419 $result = $this->conn->close(); 2445 else 2446 $result = $this->conn->expunge($mailbox, $uids); 2420 } 2421 else { 2422 $result = $this->conn->expunge($folder, $uids); 2423 } 2447 2424 2448 2425 if ($result && $clear_cache) { 2449 $this->clear_message_cache($ mailbox, $all_mode ? null : explode(',', $uids));2450 $this-> _clear_messagecount($mailbox);2426 $this->clear_message_cache($folder, $all_mode ? null : explode(',', $uids)); 2427 $this->clear_messagecount($folder); 2451 2428 } 2452 2429 2453 2430 return $result; 2454 }2455 2456 2457 /**2458 * Parse message UIDs input2459 *2460 * @param mixed $uids UIDs array or comma-separated list or '*' or '1:*'2461 * @param string $mailbox Mailbox name2462 * @return array Two elements array with UIDs converted to list and ALL flag2463 * @access private2464 */2465 private function _parse_uids($uids, $mailbox)2466 {2467 if ($uids === '*' || $uids === '1:*') {2468 if (empty($this->search_set)) {2469 $uids = '1:*';2470 $all = true;2471 }2472 // get UIDs from current search set2473 else {2474 $uids = join(',', $this->search_set->get());2475 }2476 }2477 else {2478 if (is_array($uids))2479 $uids = join(',', $uids);2480 2481 if (preg_match('/[^0-9,]/', $uids))2482 $uids = '';2483 }2484 2485 return array($uids, (bool) $all);2486 2431 } 2487 2432 … … 2492 2437 2493 2438 /** 2494 * Public method for listing subscribed folders 2439 * Public method for listing subscribed folders. 2495 2440 * 2496 2441 * @param string $root Optional root folder … … 2501 2446 * 2502 2447 * @return array List of folders 2503 * @access public 2504 */ 2505 function list_mailboxes($root='', $name='*', $filter=null, $rights=null, $skip_sort=false) 2448 */ 2449 public function list_folders_subscribed($root='', $name='*', $filter=null, $rights=null, $skip_sort=false) 2506 2450 { 2507 2451 $cache_key = $root.':'.$name; … … 2518 2462 } 2519 2463 2520 $a_mboxes = $this->_list_ mailboxes($root, $name, $filter, $rights);2464 $a_mboxes = $this->_list_folders_subscribed($root, $name, $filter, $rights); 2521 2465 2522 2466 if (!is_array($a_mboxes)) { … … 2534 2478 } 2535 2479 2536 // sort mailboxes (always sort for cache)2480 // sort folders (always sort for cache) 2537 2481 if (!$skip_sort || $this->cache) { 2538 $a_mboxes = $this-> _sort_mailbox_list($a_mboxes);2539 } 2540 2541 // write mailboxlist to cache2482 $a_mboxes = $this->sort_folder_list($a_mboxes); 2483 } 2484 2485 // write folders list to cache 2542 2486 $this->update_cache($cache_key, $a_mboxes); 2543 2487 … … 2547 2491 2548 2492 /** 2549 * Private method for mailboxlisting (LSUB)2493 * protected method for folders listing (LSUB) 2550 2494 * 2551 2495 * @param string $root Optional root folder … … 2555 2499 * 2556 2500 * @return array List of subscribed folders 2557 * @see rcube_imap::list_mailboxes() 2558 * @access private 2559 */ 2560 private function _list_mailboxes($root='', $name='*', $filter=null, $rights=null) 2501 * @see rcube_imap::list_folders_subscribed() 2502 */ 2503 protected function _list_folders_subscribed($root='', $name='*', $filter=null, $rights=null) 2561 2504 { 2562 2505 $a_defaults = $a_out = array(); 2563 2506 2564 // Give plugins a chance to provide a list of mailboxes2565 $data = rcmail::get_instance()->plugins->exec_hook(' mailboxes_list',2507 // Give plugins a chance to provide a list of folders 2508 $data = rcmail::get_instance()->plugins->exec_hook('folders_list', 2566 2509 array('root' => $root, 'name' => $name, 'filter' => $filter, 'mode' => 'LSUB')); 2567 2510 … … 2569 2512 $a_folders = $data['folders']; 2570 2513 } 2571 else if (!$this->c onn->connected()) {2514 else if (!$this->check_connection()) { 2572 2515 return null; 2573 2516 } … … 2577 2520 // #1486225: Some dovecot versions returns wrong result using LIST-EXTENDED 2578 2521 if (!$config->get('imap_force_lsub') && $this->get_capability('LIST-EXTENDED')) { 2579 // This will also set mailboxoptions, LSUB doesn't do that2522 // This will also set folder options, LSUB doesn't do that 2580 2523 $a_folders = $this->conn->listMailboxes($root, $name, 2581 2524 NULL, array('SUBSCRIBED')); … … 2604 2547 ) { 2605 2548 // Some servers returns \Noselect for existing folders 2606 if (!$this-> mailbox_exists($folder)) {2549 if (!$this->folder_exists($folder)) { 2607 2550 $this->conn->unsubscribe($folder); 2608 2551 unset($a_folders[$idx]); … … 2623 2566 2624 2567 /** 2625 * Get a list of all folders available on the IMAPserver2568 * Get a list of all folders available on the server 2626 2569 * 2627 2570 * @param string $root IMAP root dir … … 2633 2576 * @return array Indexed array with folder names 2634 2577 */ 2635 function list_unsubscribed($root='', $name='*', $filter=null, $rights=null, $skip_sort=false)2578 public function list_folders($root='', $name='*', $filter=null, $rights=null, $skip_sort=false) 2636 2579 { 2637 2580 $cache_key = $root.':'.$name; … … 2648 2591 } 2649 2592 2650 // Give plugins a chance to provide a list of mailboxes2651 $data = rcmail::get_instance()->plugins->exec_hook(' mailboxes_list',2593 // Give plugins a chance to provide a list of folders 2594 $data = rcmail::get_instance()->plugins->exec_hook('folders_list', 2652 2595 array('root' => $root, 'name' => $name, 'filter' => $filter, 'mode' => 'LIST')); 2653 2596 … … 2657 2600 else { 2658 2601 // retrieve list of folders from IMAP server 2659 $a_mboxes = $this->_list_ unsubscribed($root, $name);2602 $a_mboxes = $this->_list_folders($root, $name); 2660 2603 } 2661 2604 … … 2670 2613 2671 2614 // cache folder attributes 2672 if ($root == '' && $name == '*' && empty($filter) ) {2615 if ($root == '' && $name == '*' && empty($filter) && !empty($this->conn->data)) { 2673 2616 $this->update_cache('mailboxes.attributes', $this->conn->data['LIST']); 2674 2617 } … … 2681 2624 // filter folders and sort them 2682 2625 if (!$skip_sort) { 2683 $a_mboxes = $this-> _sort_mailbox_list($a_mboxes);2684 } 2685 2686 // write mailboxlist to cache2626 $a_mboxes = $this->sort_folder_list($a_mboxes); 2627 } 2628 2629 // write folders list to cache 2687 2630 $this->update_cache($cache_key, $a_mboxes); 2688 2631 … … 2692 2635 2693 2636 /** 2694 * Private method for mailboxlisting (LIST)2637 * protected method for folders listing (LIST) 2695 2638 * 2696 2639 * @param string $root Optional root folder … … 2698 2641 * 2699 2642 * @return array List of folders 2700 * @see rcube_imap::list_unsubscribed() 2701 */ 2702 private function _list_unsubscribed($root='', $name='*') 2703 { 2643 * @see rcube_imap::list_folders() 2644 */ 2645 protected function _list_folders($root='', $name='*') 2646 { 2647 if (!$this->check_connection()) { 2648 return null; 2649 } 2650 2704 2651 $result = $this->conn->listMailboxes($root, $name); 2705 2652 … … 2758 2705 * Filter the given list of folders according to access rights 2759 2706 */ 2760 pr ivatefunction filter_rights($a_folders, $rights)2707 protected function filter_rights($a_folders, $rights) 2761 2708 { 2762 2709 $regex = '/('.$rights.')/'; 2763 2710 foreach ($a_folders as $idx => $folder) { 2764 2711 $myrights = join('', (array)$this->my_rights($folder)); 2765 if ($myrights !== null && !preg_match($regex, $myrights)) 2712 if ($myrights !== null && !preg_match($regex, $myrights)) { 2766 2713 unset($a_folders[$idx]); 2714 } 2767 2715 } 2768 2716 … … 2777 2725 * @return mixed Quota info or False if not supported 2778 2726 */ 2779 function get_quota()2780 { 2781 if ($this->get_capability('QUOTA')) 2727 public function get_quota() 2728 { 2729 if ($this->get_capability('QUOTA')) { 2782 2730 return $this->conn->getQuota(); 2731 } 2783 2732 2784 2733 return false; … … 2787 2736 2788 2737 /** 2789 * Get mailbox size (size of all messages in a mailbox) 2790 * 2791 * @param string $mailbox Mailbox name 2792 * 2793 * @return int Mailbox size in bytes, False on error 2794 */ 2795 function get_mailbox_size($mailbox) 2796 { 2738 * Get folder size (size of all messages in a folder) 2739 * 2740 * @param string $folder Folder name 2741 * 2742 * @return int Folder size in bytes, False on error 2743 */ 2744 public function folder_size($folder) 2745 { 2746 if (!$this->check_connection()) { 2747 return 0; 2748 } 2749 2797 2750 // @TODO: could we try to use QUOTA here? 2798 $result = $this->conn->fetchHeaderIndex($ mailbox, '1:*', 'SIZE', false);2799 2800 if (is_array($result)) 2751 $result = $this->conn->fetchHeaderIndex($folder, '1:*', 'SIZE', false); 2752 2753 if (is_array($result)) { 2801 2754 $result = array_sum($result); 2755 } 2802 2756 2803 2757 return $result; … … 2806 2760 2807 2761 /** 2808 * Subscribe to a specific mailbox(es) 2809 * 2810 * @param array $a_mboxes Mailbox name(s) 2762 * Subscribe to a specific folder(s) 2763 * 2764 * @param array $folders Folder name(s) 2765 * 2811 2766 * @return boolean True on success 2812 2767 */ 2813 function subscribe($a_mboxes) 2814 { 2815 if (!is_array($a_mboxes)) 2816 $a_mboxes = array($a_mboxes); 2817 2768 public function subscribe($folders) 2769 { 2818 2770 // let this common function do the main work 2819 return $this->_change_subscription($a_mboxes, 'subscribe'); 2820 } 2821 2822 2823 /** 2824 * Unsubscribe mailboxes 2825 * 2826 * @param array $a_mboxes Mailbox name(s) 2771 return $this->change_subscription($folders, 'subscribe'); 2772 } 2773 2774 2775 /** 2776 * Unsubscribe folder(s) 2777 * 2778 * @param array $a_mboxes Folder name(s) 2779 * 2827 2780 * @return boolean True on success 2828 2781 */ 2829 function unsubscribe($a_mboxes) 2830 { 2831 if (!is_array($a_mboxes)) 2832 $a_mboxes = array($a_mboxes); 2833 2782 public function unsubscribe($folders) 2783 { 2834 2784 // let this common function do the main work 2835 return $this-> _change_subscription($a_mboxes, 'unsubscribe');2836 } 2837 2838 2839 /** 2840 * Create a new mailboxon the server and register it in local cache2841 * 2842 * @param string $ mailbox New mailboxname2843 * @param boolean $subscribe True if the new mailboxshould be subscribed2785 return $this->change_subscription($folders, 'unsubscribe'); 2786 } 2787 2788 2789 /** 2790 * Create a new folder on the server and register it in local cache 2791 * 2792 * @param string $folder New folder name 2793 * @param boolean $subscribe True if the new folder should be subscribed 2844 2794 * 2845 2795 * @return boolean True on success 2846 2796 */ 2847 function create_mailbox($mailbox, $subscribe=false) 2848 { 2849 $result = $this->conn->createFolder($mailbox); 2797 public function create_folder($folder, $subscribe=false) 2798 { 2799 if (!$this->check_connection()) { 2800 return false; 2801 } 2802 2803 $result = $this->conn->createFolder($folder); 2850 2804 2851 2805 // try to subscribe it … … 2854 2808 $this->clear_cache('mailboxes', true); 2855 2809 2856 if ($subscribe) 2857 $this->subscribe($mailbox); 2810 if ($subscribe) { 2811 $this->subscribe($folder); 2812 } 2858 2813 } 2859 2814 … … 2863 2818 2864 2819 /** 2865 * Set a new name to an existing mailbox2866 * 2867 * @param string $ mailbox Mailboxto rename2868 * @param string $new_name New mailboxname2820 * Set a new name to an existing folder 2821 * 2822 * @param string $folder Folder to rename 2823 * @param string $new_name New folder name 2869 2824 * 2870 2825 * @return boolean True on success 2871 2826 */ 2872 function rename_mailbox($mailbox, $new_name)2827 public function rename_folder($folder, $new_name) 2873 2828 { 2874 2829 if (!strlen($new_name)) { … … 2876 2831 } 2877 2832 2833 if (!$this->check_connection()) { 2834 return false; 2835 } 2836 2878 2837 $delm = $this->get_hierarchy_delimiter(); 2879 2838 2880 2839 // get list of subscribed folders 2881 if ((strpos($ mailbox, '%') === false) && (strpos($mailbox, '*') === false)) {2882 $a_subscribed = $this->_list_ mailboxes('', $mailbox. $delm . '*');2883 $subscribed = $this-> mailbox_exists($mailbox, true);2840 if ((strpos($folder, '%') === false) && (strpos($folder, '*') === false)) { 2841 $a_subscribed = $this->_list_folders_subscribed('', $folder . $delm . '*'); 2842 $subscribed = $this->folder_exists($folder, true); 2884 2843 } 2885 2844 else { 2886 $a_subscribed = $this->_list_ mailboxes();2887 $subscribed = in_array($ mailbox, $a_subscribed);2888 } 2889 2890 $result = $this->conn->renameFolder($ mailbox, $new_name);2845 $a_subscribed = $this->_list_folders_subscribed(); 2846 $subscribed = in_array($folder, $a_subscribed); 2847 } 2848 2849 $result = $this->conn->renameFolder($folder, $new_name); 2891 2850 2892 2851 if ($result) { 2893 2852 // unsubscribe the old folder, subscribe the new one 2894 2853 if ($subscribed) { 2895 $this->conn->unsubscribe($ mailbox);2854 $this->conn->unsubscribe($folder); 2896 2855 $this->conn->subscribe($new_name); 2897 2856 } 2898 2857 2899 // check if mailboxchildren are subscribed2858 // check if folder children are subscribed 2900 2859 foreach ($a_subscribed as $c_subscribed) { 2901 if (strpos($c_subscribed, $ mailbox.$delm) === 0) {2860 if (strpos($c_subscribed, $folder.$delm) === 0) { 2902 2861 $this->conn->unsubscribe($c_subscribed); 2903 $this->conn->subscribe(preg_replace('/^'.preg_quote($ mailbox, '/').'/',2862 $this->conn->subscribe(preg_replace('/^'.preg_quote($folder, '/').'/', 2904 2863 $new_name, $c_subscribed)); 2905 2864 … … 2910 2869 2911 2870 // clear cache 2912 $this->clear_message_cache($ mailbox);2871 $this->clear_message_cache($folder); 2913 2872 $this->clear_cache('mailboxes', true); 2914 2873 } … … 2919 2878 2920 2879 /** 2921 * Remove mailboxfrom server2922 * 2923 * @param string $ mailbox Mailboxname2880 * Remove folder from server 2881 * 2882 * @param string $folder Folder name 2924 2883 * 2925 2884 * @return boolean True on success 2926 2885 */ 2927 function delete_ mailbox($mailbox)2886 function delete_folder($folder) 2928 2887 { 2929 2888 $delm = $this->get_hierarchy_delimiter(); 2930 2889 2890 if (!$this->check_connection()) { 2891 return false; 2892 } 2893 2931 2894 // get list of folders 2932 if ((strpos($mailbox, '%') === false) && (strpos($mailbox, '*') === false)) 2933 $sub_mboxes = $this->list_unsubscribed('', $mailbox . $delm . '*'); 2934 else 2895 if ((strpos($folder, '%') === false) && (strpos($folder, '*') === false)) { 2896 $sub_mboxes = $this->list_unsubscribed('', $folder . $delm . '*'); 2897 } 2898 else { 2935 2899 $sub_mboxes = $this->list_unsubscribed(); 2900 } 2936 2901 2937 2902 // send delete command to server 2938 $result = $this->conn->deleteFolder($ mailbox);2903 $result = $this->conn->deleteFolder($folder); 2939 2904 2940 2905 if ($result) { 2941 // unsubscribe mailbox2942 $this->conn->unsubscribe($ mailbox);2906 // unsubscribe folder 2907 $this->conn->unsubscribe($folder); 2943 2908 2944 2909 foreach ($sub_mboxes as $c_mbox) { 2945 if (strpos($c_mbox, $ mailbox.$delm) === 0) {2910 if (strpos($c_mbox, $folder.$delm) === 0) { 2946 2911 $this->conn->unsubscribe($c_mbox); 2947 2912 if ($this->conn->deleteFolder($c_mbox)) { … … 2951 2916 } 2952 2917 2953 // clear mailbox-related cache2954 $this->clear_message_cache($ mailbox);2918 // clear folder-related cache 2919 $this->clear_message_cache($folder); 2955 2920 $this->clear_cache('mailboxes', true); 2956 2921 } … … 2963 2928 * Create all folders specified as default 2964 2929 */ 2965 function create_default_folders()2930 public function create_default_folders() 2966 2931 { 2967 2932 // create default folders if they do not exist 2968 2933 foreach ($this->default_folders as $folder) { 2969 if (!$this->mailbox_exists($folder)) 2970 $this->create_mailbox($folder, true); 2971 else if (!$this->mailbox_exists($folder, true)) 2934 if (!$this->folder_exists($folder)) { 2935 $this->create_folder($folder, true); 2936 } 2937 else if (!$this->folder_exists($folder, true)) { 2972 2938 $this->subscribe($folder); 2939 } 2973 2940 } 2974 2941 } … … 2978 2945 * Checks if folder exists and is subscribed 2979 2946 * 2980 * @param string $ mailboxFolder name2947 * @param string $folder Folder name 2981 2948 * @param boolean $subscription Enable subscription checking 2982 2949 * 2983 2950 * @return boolean TRUE or FALSE 2984 2951 */ 2985 function mailbox_exists($mailbox, $subscription=false)2986 { 2987 if ($ mailbox== 'INBOX') {2952 public function folder_exists($folder, $subscription=false) 2953 { 2954 if ($folder == 'INBOX') { 2988 2955 return true; 2989 2956 } … … 2991 2958 $key = $subscription ? 'subscribed' : 'existing'; 2992 2959 2993 if (is_array($this->icache[$key]) && in_array($ mailbox, $this->icache[$key]))2960 if (is_array($this->icache[$key]) && in_array($folder, $this->icache[$key])) { 2994 2961 return true; 2962 } 2963 2964 if (!$this->check_connection()) { 2965 return false; 2966 } 2995 2967 2996 2968 if ($subscription) { 2997 $a_folders = $this->conn->listSubscribed('', $ mailbox);2969 $a_folders = $this->conn->listSubscribed('', $folder); 2998 2970 } 2999 2971 else { 3000 $a_folders = $this->conn->listMailboxes('', $ mailbox);3001 } 3002 3003 if (is_array($a_folders) && in_array($ mailbox, $a_folders)) {3004 $this->icache[$key][] = $ mailbox;2972 $a_folders = $this->conn->listMailboxes('', $folder); 2973 } 2974 2975 if (is_array($a_folders) && in_array($folder, $a_folders)) { 2976 $this->icache[$key][] = $folder; 3005 2977 return true; 3006 2978 } … … 3013 2985 * Returns the namespace where the folder is in 3014 2986 * 3015 * @param string $ mailboxFolder name2987 * @param string $folder Folder name 3016 2988 * 3017 2989 * @return string One of 'personal', 'other' or 'shared' 3018 * @access public 3019 */ 3020 function mailbox_namespace($mailbox) 3021 { 3022 if ($mailbox == 'INBOX') { 2990 */ 2991 public function folder_namespace($folder) 2992 { 2993 if ($folder == 'INBOX') { 3023 2994 return 'personal'; 3024 2995 } … … 3028 2999 foreach ($namespace as $ns) { 3029 3000 if ($len = strlen($ns[0])) { 3030 if (($len > 1 && $ mailbox== substr($ns[0], 0, -1))3031 || strpos($ mailbox, $ns[0]) === 03001 if (($len > 1 && $folder == substr($ns[0], 0, -1)) 3002 || strpos($folder, $ns[0]) === 0 3032 3003 ) { 3033 3004 return $type; … … 3048 3019 * of the folders tree. 3049 3020 * 3050 * @param string $ mailboxFolder name3021 * @param string $folder Folder name 3051 3022 * @param string $mode Mode name (out/in) 3052 3023 * 3053 3024 * @return string Folder name 3054 3025 */ 3055 function mod_mailbox($mailbox, $mode = 'out')3056 { 3057 if (!strlen($ mailbox)) {3058 return $ mailbox;3026 public function mod_folder($folder, $mode = 'out') 3027 { 3028 if (!strlen($folder)) { 3029 return $folder; 3059 3030 } 3060 3031 … … 3063 3034 3064 3035 if (!$prefix_len) { 3065 return $ mailbox;3036 return $folder; 3066 3037 } 3067 3038 3068 3039 // remove prefix for output 3069 3040 if ($mode == 'out') { 3070 if (substr($ mailbox, 0, $prefix_len) === $prefix) {3071 return substr($ mailbox, $prefix_len);3041 if (substr($folder, 0, $prefix_len) === $prefix) { 3042 return substr($folder, $prefix_len); 3072 3043 } 3073 3044 } 3074 3045 // add prefix for input (e.g. folder creation) 3075 3046 else { 3076 return $prefix . $ mailbox;3077 } 3078 3079 return $ mailbox;3047 return $prefix . $folder; 3048 } 3049 3050 return $folder; 3080 3051 } 3081 3052 … … 3084 3055 * Gets folder attributes from LIST response, e.g. \Noselect, \Noinferiors 3085 3056 * 3086 * @param string $ mailboxFolder name3057 * @param string $folder Folder name 3087 3058 * @param bool $force Set to True if attributes should be refreshed 3088 3059 * 3089 3060 * @return array Options list 3090 3061 */ 3091 function mailbox_attributes($mailbox, $force=false)3062 public function folder_attributes($folder, $force=false) 3092 3063 { 3093 3064 // get attributes directly from LIST command 3094 if (!empty($this->conn->data['LIST']) && is_array($this->conn->data['LIST'][$ mailbox])) {3095 $opts = $this->conn->data['LIST'][$ mailbox];3065 if (!empty($this->conn->data['LIST']) && is_array($this->conn->data['LIST'][$folder])) { 3066 $opts = $this->conn->data['LIST'][$folder]; 3096 3067 } 3097 3068 // get cached folder attributes 3098 3069 else if (!$force) { 3099 3070 $opts = $this->get_cache('mailboxes.attributes'); 3100 $opts = $opts[$ mailbox];3071 $opts = $opts[$folder]; 3101 3072 } 3102 3073 3103 3074 if (!is_array($opts)) { 3104 $this->conn->listMailboxes('', $mailbox); 3105 $opts = $this->conn->data['LIST'][$mailbox]; 3075 if (!$this->check_connection()) { 3076 return array(); 3077 } 3078 3079 $this->conn->listMailboxes('', $folder); 3080 $opts = $this->conn->data['LIST'][$folder]; 3106 3081 } 3107 3082 … … 3111 3086 3112 3087 /** 3113 * Gets connection (and current mailbox) data: UIDVALIDITY, EXISTS, RECENT,3088 * Gets connection (and current folder) data: UIDVALIDITY, EXISTS, RECENT, 3114 3089 * PERMANENTFLAGS, UIDNEXT, UNSEEN 3115 3090 * 3116 * @param string $ mailboxFolder name3091 * @param string $folder Folder name 3117 3092 * 3118 3093 * @return array Data 3119 3094 */ 3120 function mailbox_data($mailbox) 3121 { 3122 if (!strlen($mailbox)) 3123 $mailbox = $this->mailbox !== null ? $this->mailbox : 'INBOX'; 3124 3125 if ($this->conn->selected != $mailbox) { 3126 if ($this->conn->select($mailbox)) 3127 $this->mailbox = $mailbox; 3128 else 3095 public function folder_data($folder) 3096 { 3097 if (!strlen($folder)) { 3098 $folder = $this->folder !== null ? $this->folder : 'INBOX'; 3099 } 3100 3101 if ($this->conn->selected != $folder) { 3102 if (!$this->check_connection()) { 3103 return array(); 3104 } 3105 3106 if ($this->conn->select($folder)) { 3107 $this->folder = $folder; 3108 } 3109 else { 3129 3110 return null; 3111 } 3130 3112 } 3131 3113 … … 3134 3116 // add (E)SEARCH result for ALL UNDELETED query 3135 3117 if (!empty($this->icache['undeleted_idx']) 3136 && $this->icache['undeleted_idx']->get Parameters('MAILBOX') == $mailbox3118 && $this->icache['undeleted_idx']->get_parameters('MAILBOX') == $folder 3137 3119 ) { 3138 3120 $data['UNDELETED'] = $this->icache['undeleted_idx']; … … 3146 3128 * Returns extended information about the folder 3147 3129 * 3148 * @param string $ mailboxFolder name3130 * @param string $folder Folder name 3149 3131 * 3150 3132 * @return array Data 3151 3133 */ 3152 function mailbox_info($mailbox)3153 { 3154 if ($this->icache['options'] && $this->icache['options']['name'] == $ mailbox) {3134 public function folder_info($folder) 3135 { 3136 if ($this->icache['options'] && $this->icache['options']['name'] == $folder) { 3155 3137 return $this->icache['options']; 3156 3138 } … … 3162 3144 // check if the folder is a namespace prefix 3163 3145 if (!empty($namespace)) { 3164 $mbox = $ mailbox. $this->delimiter;3146 $mbox = $folder . $this->delimiter; 3165 3147 foreach ($namespace as $ns) { 3166 3148 if (!empty($ns)) { … … 3176 3158 // check if the folder is other user virtual-root 3177 3159 if (!$options['is_root'] && !empty($namespace) && !empty($namespace['other'])) { 3178 $parts = explode($this->delimiter, $ mailbox);3160 $parts = explode($this->delimiter, $folder); 3179 3161 if (count($parts) == 2) { 3180 3162 $mbox = $parts[0] . $this->delimiter; … … 3188 3170 } 3189 3171 3190 $options['name'] = $ mailbox;3191 $options['attributes'] = $this-> mailbox_attributes($mailbox, true);3192 $options['namespace'] = $this-> mailbox_namespace($mailbox);3193 $options['rights'] = $acl && !$options['is_root'] ? (array)$this->my_rights($ mailbox) : array();3194 $options['special'] = in_array($ mailbox, $this->default_folders);3172 $options['name'] = $folder; 3173 $options['attributes'] = $this->folder_attributes($folder, true); 3174 $options['namespace'] = $this->folder_namespace($folder); 3175 $options['rights'] = $acl && !$options['is_root'] ? (array)$this->my_rights($folder) : array(); 3176 $options['special'] = in_array($folder, $this->default_folders); 3195 3177 3196 3178 // Set 'noselect' and 'norename' flags … … 3227 3209 * Synchronizes messages cache. 3228 3210 * 3229 * @param string $ mailboxFolder name3230 */ 3231 public function mailbox_sync($mailbox)3211 * @param string $folder Folder name 3212 */ 3213 public function folder_sync($folder) 3232 3214 { 3233 3215 if ($mcache = $this->get_mcache_engine()) { 3234 $mcache->synchronize($ mailbox);3216 $mcache->synchronize($folder); 3235 3217 } 3236 3218 } … … 3242 3224 * @return string Space-separated list of header names 3243 3225 */ 3244 private function get_fetch_headers() 3245 { 3246 $headers = explode(' ', $this->fetch_add_headers); 3247 $headers = array_map('strtoupper', $headers); 3248 3249 if ($this->messages_caching || $this->get_all_headers) 3226 protected function get_fetch_headers() 3227 { 3228 if (!empty($this->options['fetch_headers'])) { 3229 $headers = explode(' ', $this->options['fetch_headers']); 3230 $headers = array_map('strtoupper', $headers); 3231 } 3232 else { 3233 $headers = array(); 3234 } 3235 3236 if ($this->messages_caching || $this->options['all_headers']) { 3250 3237 $headers = array_merge($headers, $this->all_headers); 3238 } 3251 3239 3252 3240 return implode(' ', array_unique($headers)); … … 3259 3247 3260 3248 /** 3261 * Changes the ACL on the specified mailbox(SETACL)3262 * 3263 * @param string $ mailbox Mailboxname3249 * Changes the ACL on the specified folder (SETACL) 3250 * 3251 * @param string $folder Folder name 3264 3252 * @param string $user User name 3265 3253 * @param string $acl ACL string 3266 3254 * 3267 3255 * @return boolean True on success, False on failure 3268 *3269 * @access public3270 3256 * @since 0.5-beta 3271 3257 */ 3272 function set_acl($mailbox, $user, $acl) 3273 { 3274 if ($this->get_capability('ACL')) 3275 return $this->conn->setACL($mailbox, $user, $acl); 3276 3277 return false; 3258 public function set_acl($folder, $user, $acl) 3259 { 3260 if (!$this->get_capability('ACL')) { 3261 return false; 3262 } 3263 3264 if (!$this->check_connection()) { 3265 return false; 3266 } 3267 3268 return $this->conn->setACL($folder, $user, $acl); 3278 3269 } 3279 3270 … … 3282 3273 * Removes any <identifier,rights> pair for the 3283 3274 * specified user from the ACL for the specified 3284 * mailbox(DELETEACL)3285 * 3286 * @param string $ mailbox Mailboxname3275 * folder (DELETEACL) 3276 * 3277 * @param string $folder Folder name 3287 3278 * @param string $user User name 3288 3279 * 3289 3280 * @return boolean True on success, False on failure 3290 *3291 * @access public3292 3281 * @since 0.5-beta 3293 3282 */ 3294 function delete_acl($mailbox, $user) 3295 { 3296 if ($this->get_capability('ACL')) 3297 return $this->conn->deleteACL($mailbox, $user); 3298 3299 return false; 3300 } 3301 3302 3303 /** 3304 * Returns the access control list for mailbox (GETACL) 3305 * 3306 * @param string $mailbox Mailbox name 3283 public function delete_acl($folder, $user) 3284 { 3285 if (!$this->get_capability('ACL')) { 3286 return false; 3287 } 3288 3289 if (!$this->check_connection()) { 3290 return false; 3291 } 3292 3293 return $this->conn->deleteACL($folder, $user); 3294 } 3295 3296 3297 /** 3298 * Returns the access control list for folder (GETACL) 3299 * 3300 * @param string $folder Folder name 3307 3301 * 3308 3302 * @return array User-rights array on success, NULL on error 3309 * @access public3310 3303 * @since 0.5-beta 3311 3304 */ 3312 function get_acl($mailbox) 3313 { 3314 if ($this->get_capability('ACL')) 3315 return $this->conn->getACL($mailbox); 3316 3317 return NULL; 3305 public function get_acl($folder) 3306 { 3307 if (!$this->get_capability('ACL')) { 3308 return null; 3309 } 3310 3311 if (!$this->check_connection()) { 3312 return null; 3313 } 3314 3315 return $this->conn->getACL($folder); 3318 3316 } 3319 3317 … … 3321 3319 /** 3322 3320 * Returns information about what rights can be granted to the 3323 * user (identifier) in the ACL for the mailbox(LISTRIGHTS)3324 * 3325 * @param string $ mailbox Mailboxname3321 * user (identifier) in the ACL for the folder (LISTRIGHTS) 3322 * 3323 * @param string $folder Folder name 3326 3324 * @param string $user User name 3327 3325 * 3328 3326 * @return array List of user rights 3329 * @access public3330 3327 * @since 0.5-beta 3331 3328 */ 3332 function list_rights($mailbox, $user) 3333 { 3334 if ($this->get_capability('ACL')) 3335 return $this->conn->listRights($mailbox, $user); 3336 3337 return NULL; 3329 public function list_rights($folder, $user) 3330 { 3331 if (!$this->get_capability('ACL')) { 3332 return null; 3333 } 3334 3335 if (!$this->check_connection()) { 3336 return null; 3337 } 3338 3339 return $this->conn->listRights($folder, $user); 3338 3340 } 3339 3341 … … 3341 3343 /** 3342 3344 * Returns the set of rights that the current user has to 3343 * mailbox(MYRIGHTS)3344 * 3345 * @param string $ mailbox Mailboxname3345 * folder (MYRIGHTS) 3346 * 3347 * @param string $folder Folder name 3346 3348 * 3347 3349 * @return array MYRIGHTS response on success, NULL on error 3348 * @access public3349 3350 * @since 0.5-beta 3350 3351 */ 3351 function my_rights($mailbox) 3352 { 3353 if ($this->get_capability('ACL')) 3354 return $this->conn->myRights($mailbox); 3355 3356 return NULL; 3352 public function my_rights($folder) 3353 { 3354 if (!$this->get_capability('ACL')) { 3355 return null; 3356 } 3357 3358 if (!$this->check_connection()) { 3359 return null; 3360 } 3361 3362 return $this->conn->myRights($folder); 3357 3363 } 3358 3364 … … 3361 3367 * Sets IMAP metadata/annotations (SETMETADATA/SETANNOTATION) 3362 3368 * 3363 * @param string $ mailbox Mailboxname (empty for server metadata)3369 * @param string $folder Folder name (empty for server metadata) 3364 3370 * @param array $entries Entry-value array (use NULL value as NIL) 3365 3371 * 3366 3372 * @return boolean True on success, False on failure 3367 * @access public3368 3373 * @since 0.5-beta 3369 3374 */ 3370 function set_metadata($mailbox, $entries) 3371 { 3375 public function set_metadata($folder, $entries) 3376 { 3377 if (!$this->check_connection()) { 3378 return false; 3379 } 3380 3372 3381 if ($this->get_capability('METADATA') || 3373 (!strlen($ mailbox) && $this->get_capability('METADATA-SERVER'))3382 (!strlen($folder) && $this->get_capability('METADATA-SERVER')) 3374 3383 ) { 3375 return $this->conn->setMetadata($ mailbox, $entries);3384 return $this->conn->setMetadata($folder, $entries); 3376 3385 } 3377 3386 else if ($this->get_capability('ANNOTATEMORE') || $this->get_capability('ANNOTATEMORE2')) { … … 3380 3389 $entries[$entry] = array($ent, $attr, $value); 3381 3390 } 3382 return $this->conn->setAnnotation($ mailbox, $entries);3391 return $this->conn->setAnnotation($folder, $entries); 3383 3392 } 3384 3393 … … 3390 3399 * Unsets IMAP metadata/annotations (SETMETADATA/SETANNOTATION) 3391 3400 * 3392 * @param string $ mailbox Mailboxname (empty for server metadata)3401 * @param string $folder Folder name (empty for server metadata) 3393 3402 * @param array $entries Entry names array 3394 3403 * 3395 3404 * @return boolean True on success, False on failure 3396 *3397 * @access public3398 3405 * @since 0.5-beta 3399 3406 */ 3400 function delete_metadata($mailbox, $entries) 3401 { 3407 public function delete_metadata($folder, $entries) 3408 { 3409 if (!$this->check_connection()) { 3410 return false; 3411 } 3412 3402 3413 if ($this->get_capability('METADATA') || 3403 (!strlen($ mailbox) && $this->get_capability('METADATA-SERVER'))3414 (!strlen($folder) && $this->get_capability('METADATA-SERVER')) 3404 3415 ) { 3405 return $this->conn->deleteMetadata($ mailbox, $entries);3416 return $this->conn->deleteMetadata($folder, $entries); 3406 3417 } 3407 3418 else if ($this->get_capability('ANNOTATEMORE') || $this->get_capability('ANNOTATEMORE2')) { … … 3410 3421 $entries[$idx] = array($ent, $attr, NULL); 3411 3422 } 3412 return $this->conn->setAnnotation($ mailbox, $entries);3423 return $this->conn->setAnnotation($folder, $entries); 3413 3424 } 3414 3425 … … 3420 3431 * Returns IMAP metadata/annotations (GETMETADATA/GETANNOTATION) 3421 3432 * 3422 * @param string $ mailbox Mailboxname (empty for server metadata)3433 * @param string $folder Folder name (empty for server metadata) 3423 3434 * @param array $entries Entries 3424 3435 * @param array $options Command options (with MAXSIZE and DEPTH keys) 3425 3436 * 3426 3437 * @return array Metadata entry-value hash array on success, NULL on error 3427 *3428 * @access public3429 3438 * @since 0.5-beta 3430 3439 */ 3431 function get_metadata($mailbox, $entries, $options=array()) 3432 { 3433 if ($this->get_capability('METADATA') || 3434 (!strlen($mailbox) && $this->get_capability('METADATA-SERVER')) 3440 public function get_metadata($folder, $entries, $options=array()) 3441 { 3442 if (!$this->check_connection()) { 3443 return null; 3444 } 3445 3446 if ($this->get_capability('METADATA') || 3447 (!strlen($folder) && $this->get_capability('METADATA-SERVER')) 3435 3448 ) { 3436 return $this->conn->getMetadata($ mailbox, $entries, $options);3449 return $this->conn->getMetadata($folder, $entries, $options); 3437 3450 } 3438 3451 else if ($this->get_capability('ANNOTATEMORE') || $this->get_capability('ANNOTATEMORE2')) { … … 3447 3460 3448 3461 // @TODO: Honor MAXSIZE and DEPTH options 3449 foreach ($queries as $attrib => $entry) 3450 if ($result = $this->conn->getAnnotation($ mailbox, $entry, $attrib))3462 foreach ($queries as $attrib => $entry) { 3463 if ($result = $this->conn->getAnnotation($folder, $entry, $attrib)) { 3451 3464 $res = array_merge_recursive($res, $result); 3465 } 3466 } 3452 3467 3453 3468 return $res; 3454 3469 } 3455 3470 3456 return NULL;3471 return null; 3457 3472 } 3458 3473 … … 3466 3481 * @return array Entry-attribute list, NULL if not supported (?) 3467 3482 */ 3468 pr ivatefunction md2annotate($entry)3483 protected function md2annotate($entry) 3469 3484 { 3470 3485 if (substr($entry, 0, 7) == '/shared') { 3471 3486 return array(substr($entry, 7), 'value.shared'); 3472 3487 } 3473 else if (substr($entry, 0, 8) == '/pr ivate') {3488 else if (substr($entry, 0, 8) == '/protected') { 3474 3489 return array(substr($entry, 8), 'value.priv'); 3475 3490 } 3476 3491 3477 3492 // @TODO: log error 3478 return NULL;3493 return null; 3479 3494 } 3480 3495 … … 3488 3503 * 3489 3504 * @param string $type Cache type (@see rcmail::get_cache) 3490 * @access public 3491 */ 3492 function set_caching($type) 3505 */ 3506 public function set_caching($type) 3493 3507 { 3494 3508 if ($type) { … … 3496 3510 } 3497 3511 else { 3498 if ($this->cache) 3512 if ($this->cache) { 3499 3513 $this->cache->close(); 3514 } 3500 3515 $this->cache = null; 3501 3516 $this->caching = false; … … 3506 3521 * Getter for IMAP cache object 3507 3522 */ 3508 pr ivatefunction get_cache_engine()3523 protected function get_cache_engine() 3509 3524 { 3510 3525 if ($this->caching && !$this->cache) { … … 3520 3535 * 3521 3536 * @param string $key Cache key 3537 * 3522 3538 * @return mixed 3523 * @access public 3524 */ 3525 function get_cache($key) 3539 */ 3540 public function get_cache($key) 3526 3541 { 3527 3542 if ($cache = $this->get_cache_engine()) { … … 3535 3550 * @param string $key Cache key 3536 3551 * @param mixed $data Data 3537 * @access public 3538 */ 3539 function update_cache($key, $data) 3552 */ 3553 protected function update_cache($key, $data) 3540 3554 { 3541 3555 if ($cache = $this->get_cache_engine()) { … … 3550 3564 * @param boolean $prefix_mode Enable it to clear all keys starting 3551 3565 * with prefix specified in $key 3552 * @access public 3553 */ 3554 function clear_cache($key=null, $prefix_mode=false) 3566 */ 3567 public function clear_cache($key = null, $prefix_mode = false) 3555 3568 { 3556 3569 if ($cache = $this->get_cache_engine()) { … … 3569 3582 * @param boolean $set Flag 3570 3583 */ 3571 function set_messages_caching($set)3584 public function set_messages_caching($set) 3572 3585 { 3573 3586 if ($set) { … … 3575 3588 } 3576 3589 else { 3577 if ($this->mcache) 3590 if ($this->mcache) { 3578 3591 $this->mcache->close(); 3592 } 3579 3593 $this->mcache = null; 3580 3594 $this->messages_caching = false; … … 3586 3600 * Getter for messages cache object 3587 3601 */ 3588 pr ivatefunction get_mcache_engine()3602 protected function get_mcache_engine() 3589 3603 { 3590 3604 if ($this->messages_caching && !$this->mcache) { … … 3592 3606 if ($dbh = $rcmail->get_dbh()) { 3593 3607 $this->mcache = new rcube_imap_cache( 3594 $dbh, $this, $rcmail->user->ID, $this-> skip_deleted);3608 $dbh, $this, $rcmail->user->ID, $this->options['skip_deleted']); 3595 3609 } 3596 3610 } … … 3603 3617 * Clears the messages cache. 3604 3618 * 3605 * @param string $ mailboxFolder name3619 * @param string $folder Folder name 3606 3620 * @param array $uids Optional message UIDs to remove from cache 3607 3621 */ 3608 function clear_message_cache($mailbox= null, $uids = null)3622 protected function clear_message_cache($folder = null, $uids = null) 3609 3623 { 3610 3624 if ($mcache = $this->get_mcache_engine()) { 3611 $mcache->clear($ mailbox, $uids);3625 $mcache->clear($folder, $uids); 3612 3626 } 3613 3627 } … … 3615 3629 3616 3630 /* -------------------------------- 3617 * pr ivatemethods3631 * protected methods 3618 3632 * --------------------------------*/ 3619 3633 … … 3623 3637 * @param string $sort_field Sort column 3624 3638 * @param string $sort_order Sort order 3625 * @access private 3626 */ 3627 private function set_sort_order($sort_field, $sort_order) 3628 { 3629 if ($sort_field != null) 3639 */ 3640 protected function set_sort_order($sort_field, $sort_order) 3641 { 3642 if ($sort_field != null) { 3630 3643 $this->sort_field = asciiwords($sort_field); 3631 if ($sort_order != null) 3644 } 3645 if ($sort_order != null) { 3632 3646 $this->sort_order = strtoupper($sort_order) == 'DESC' ? 'DESC' : 'ASC'; 3633 }3634 3635 3636 /** 3637 * Sort mailboxes first by default folders and then in alphabethical order3638 * 3639 * @param array $a_folders Mailboxes list3640 * @ access private3641 */ 3642 pr ivate function _sort_mailbox_list($a_folders)3647 } 3648 } 3649 3650 3651 /** 3652 * Sort folders first by default folders and then in alphabethical order 3653 * 3654 * @param array $a_folders Folders list 3655 */ 3656 protected function sort_folder_list($a_folders) 3643 3657 { 3644 3658 $a_out = $a_defaults = $folders = array(); … … 3648 3662 // find default folders and skip folders starting with '.' 3649 3663 foreach ($a_folders as $i => $folder) { 3650 if ($folder[0] == '.') 3664 if ($folder[0] == '.') { 3651 3665 continue; 3652 3653 if (($p = array_search($folder, $this->default_folders)) !== false && !$a_defaults[$p]) 3666 } 3667 3668 if (($p = array_search($folder, $this->default_folders)) !== false && !$a_defaults[$p]) { 3654 3669 $a_defaults[$p] = $folder; 3655 else 3670 } 3671 else { 3656 3672 $folders[$folder] = rcube_charset_convert($folder, 'UTF7-IMAP'); 3673 } 3657 3674 } 3658 3675 … … 3670 3687 $a_out[] = (string) $folder; 3671 3688 unset($folders[$key]); 3672 $this-> _rsort($folder, $delimiter, $folders, $a_out);3689 $this->rsort($folder, $delimiter, $folders, $a_out); 3673 3690 } 3674 3691 … … 3678 3695 3679 3696 /** 3680 * @access private3681 */ 3682 pr ivate function _rsort($folder, $delimiter, &$list, &$out)3697 * Recursive method for sorting folders 3698 */ 3699 protected function rsort($folder, $delimiter, &$list, &$out) 3683 3700 { 3684 3701 while (list($key, $name) = each($list)) { … … 3687 3704 $out[] = (string) $name; 3688 3705 unset($list[$key]); 3689 $this-> _rsort($name, $delimiter, $list, $out);3706 $this->rsort($name, $delimiter, $list, $out); 3690 3707 } 3691 3708 } … … 3698 3715 * 3699 3716 * @param int $id Message (sequence) ID 3700 * @param string $ mailbox Mailboxname3717 * @param string $folder Folder name 3701 3718 * 3702 3719 * @return int Message UID 3703 3720 */ 3704 public function id2uid($id, $ mailbox= null)3705 { 3706 if (!strlen($ mailbox)) {3707 $ mailbox = $this->mailbox;3708 } 3709 3710 if ($uid = array_search($id, (array)$this->uid_id_map[$ mailbox])) {3721 public function id2uid($id, $folder = null) 3722 { 3723 if (!strlen($folder)) { 3724 $folder = $this->folder; 3725 } 3726 3727 if ($uid = array_search($id, (array)$this->uid_id_map[$folder])) { 3711 3728 return $uid; 3712 3729 } 3713 3730 3714 $uid = $this->conn->ID2UID($mailbox, $id); 3715 3716 $this->uid_id_map[$mailbox][$uid] = $id; 3731 if (!$this->check_connection()) { 3732 return null; 3733 } 3734 3735 $uid = $this->conn->ID2UID($folder, $id); 3736 3737 $this->uid_id_map[$folder][$uid] = $id; 3717 3738 3718 3739 return $uid; … … 3721 3742 3722 3743 /** 3723 * Subscribe/unsubscribe a list of mailboxes and update local cache 3724 * @access private 3725 */ 3726 private function _change_subscription($a_mboxes, $mode) 3744 * Subscribe/unsubscribe a list of folders and update local cache 3745 */ 3746 protected function change_subscription($folders, $mode) 3727 3747 { 3728 3748 $updated = false; 3729 3749 3730 if (is_array($a_mboxes)) 3731 foreach ($a_mboxes as $i => $mailbox) { 3732 $a_mboxes[$i] = $mailbox; 3733 3734 if ($mode == 'subscribe') 3735 $updated = $this->conn->subscribe($mailbox); 3736 else if ($mode == 'unsubscribe') 3737 $updated = $this->conn->unsubscribe($mailbox); 3738 } 3739 3740 // clear cached mailbox list(s) 3750 if (!empty($folders)) { 3751 if (!$this->check_connection()) { 3752 return false; 3753 } 3754 3755 foreach ((array)$folders as $i => $folder) { 3756 $folders[$i] = $folder; 3757 3758 if ($mode == 'subscribe') { 3759 $updated = $this->conn->subscribe($folder); 3760 } 3761 else if ($mode == 'unsubscribe') { 3762 $updated = $this->conn->unsubscribe($folder); 3763 } 3764 } 3765 } 3766 3767 // clear cached folders list(s) 3741 3768 if ($updated) { 3742 3769 $this->clear_cache('mailboxes', true); … … 3748 3775 3749 3776 /** 3750 * Increde/decrese messagecount for a specific mailbox 3751 * @access private 3752 */ 3753 private function _set_messagecount($mailbox, $mode, $increment) 3754 { 3777 * Increde/decrese messagecount for a specific folder 3778 */ 3779 protected function set_messagecount($folder, $mode, $increment) 3780 { 3781 if (!is_numeric($increment)) { 3782 return false; 3783 } 3784 3755 3785 $mode = strtoupper($mode); 3756 $a_ mailbox_cache = $this->get_cache('messagecount');3757 3758 if (!is_array($a_ mailbox_cache[$mailbox]) || !isset($a_mailbox_cache[$mailbox][$mode]) || !is_numeric($increment))3786 $a_folder_cache = $this->get_cache('messagecount'); 3787
