diff --git a/CHANGELOG b/CHANGELOG index d1958b1b3..da091e7d9 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -1,6 +1,7 @@ CHANGELOG Roundcube Webmail =========================== +- Enigma: Added option to attach public keys to sent mail (#5152) - Enigma: Handle messages with text before an encrypted block (#5149) - Enigma: Handle encrypted/signed content inside message/rfc822 attachments - Enigma: Fix missing html/plain switch on multipart/signed messages (#1490649) @@ -30,6 +31,7 @@ CHANGELOG Roundcube Webmail - Protect download urls against CSRF using unique request tokens (#1490642) - newmail_notifier: Refactor desktop notifications - Fix so contactlist_fields option can be set via config file +- Fix so SPECIAL-USE assignments are forced only until user sets special folders (#4782) RELEASE 1.2-beta ---------------- diff --git a/plugins/acl/acl.php b/plugins/acl/acl.php index 8058656f6..6a0468154 100644 --- a/plugins/acl/acl.php +++ b/plugins/acl/acl.php @@ -563,7 +563,7 @@ class acl extends rcube_plugin $this->mbox = trim(rcube_utils::get_input_value('_mbox', rcube_utils::INPUT_GPC, true)); // UTF7-IMAP $advanced = trim(rcube_utils::get_input_value('_mode', rcube_utils::INPUT_GPC)); - $advanced = $advanced == 'advanced' ? true : false; + $advanced = $advanced == 'advanced'; // Save state in user preferences $this->rc->user->save_prefs(array('acl_advanced_mode' => $advanced)); diff --git a/plugins/emoticons/emoticons.php b/plugins/emoticons/emoticons.php index d5f0e9a16..5de5f91e9 100644 --- a/plugins/emoticons/emoticons.php +++ b/plugins/emoticons/emoticons.php @@ -175,10 +175,10 @@ class emoticons extends rcube_plugin $dont_override = $rcube->config->get('dont_override', array()); if ($args['section'] == 'mailview' && !in_array('emoticons_display', $dont_override)) { - $args['prefs']['emoticons_display'] = rcube_utils::get_input_value('_emoticons_display', rcube_utils::INPUT_POST) ? true : false; + $args['prefs']['emoticons_display'] = !empty(rcube_utils::get_input_value('_emoticons_display', rcube_utils::INPUT_POST)); } else if ($args['section'] == 'compose' && !in_array('emoticons_compose', $dont_override)) { - $args['prefs']['emoticons_compose'] = rcube_utils::get_input_value('_emoticons_compose', rcube_utils::INPUT_POST) ? true : false; + $args['prefs']['emoticons_compose'] = !empty(rcube_utils::get_input_value('_emoticons_compose', rcube_utils::INPUT_POST)); } return $args; diff --git a/plugins/enigma/README b/plugins/enigma/README index ac20b790a..d9fc3799b 100644 --- a/plugins/enigma/README +++ b/plugins/enigma/README @@ -18,6 +18,7 @@ Implemented features: + PGP: key generation (client- or server-side) + Handling of PGP keys attached to incoming messages + User preferences to disable plugin features ++ Attaching public keys to email TODO: @@ -33,7 +34,6 @@ TODO: - Generate revocation certs - Search filter to see invalid/expired keys - Key server(s) support (search, import, upload, refresh) -- Attaching public keys to email - Mark keys as trusted/untrasted, display appropriate message in verify/decrypt status - Change attachment icon on messages list for encrypted messages (like vcard_attachment plugin does) - Support for multi-server installations (store keys in sql database?) diff --git a/plugins/enigma/composer.json b/plugins/enigma/composer.json index 3245ee7b3..4cfc44d54 100644 --- a/plugins/enigma/composer.json +++ b/plugins/enigma/composer.json @@ -3,7 +3,7 @@ "type": "roundcube-plugin", "description": "PGP Encryption for Roundcube", "license": "GPLv3+", - "version": "0.4", + "version": "0.5", "authors": [ { "name": "Aleksander Machniak", @@ -23,7 +23,7 @@ ], "require": { "php": ">=5.3.0", - "roundcube/plugin-installer": ">=0.1.3", - "pear-pear.php.net/crypt_gpg": "*" + "roundcube/plugin-installer": "~0.1.6", + "pear-pear.php.net/crypt_gpg": "~1.4.0" } } diff --git a/plugins/enigma/config.inc.php.dist b/plugins/enigma/config.inc.php.dist index 17e3265b6..2cce5ee95 100644 --- a/plugins/enigma/config.inc.php.dist +++ b/plugins/enigma/config.inc.php.dist @@ -28,6 +28,9 @@ $config['enigma_sign_all'] = false; // Enable encrypting all messages by default $config['enigma_encrypt_all'] = false; +// Enable attaching a public key to all messages by default +$config['enigma_attach_pubkey'] = false; + // Default for how long to store private key passwords (in minutes). // When set to 0 passwords will be stored for the whole session. $config['enigma_password_time'] = 5; diff --git a/plugins/enigma/enigma.php b/plugins/enigma/enigma.php index 8e8ded2a1..2ebe2cc66 100644 --- a/plugins/enigma/enigma.php +++ b/plugins/enigma/enigma.php @@ -339,6 +339,25 @@ class enigma extends rcube_plugin ); } + if (!isset($no_override['enigma_attach_pubkey'])) { + if (!$p['current']) { + $p['blocks']['main']['content'] = true; + return $p; + } + + $field_id = 'rcmfd_enigma_attach_pubkey'; + $input = new html_checkbox(array( + 'name' => '_enigma_attach_pubkey', + 'id' => $field_id, + 'value' => 1, + )); + + $p['blocks']['main']['options']['enigma_attach_pubkey'] = array( + 'title' => html::label($field_id, $this->gettext('attachpubkeydefault')), + 'content' => $input->show($this->rc->config->get('enigma_attach_pubkey') ? 1 : 0), + ); + } + if (!isset($no_override['enigma_password_time'])) { if (!$p['current']) { $p['blocks']['main']['content'] = true; @@ -380,6 +399,7 @@ class enigma extends rcube_plugin 'enigma_encryption' => (bool) rcube_utils::get_input_value('_enigma_encryption', rcube_utils::INPUT_POST), 'enigma_sign_all' => (bool) rcube_utils::get_input_value('_enigma_sign_all', rcube_utils::INPUT_POST), 'enigma_encrypt_all' => (bool) rcube_utils::get_input_value('_enigma_encrypt_all', rcube_utils::INPUT_POST), + 'enigma_attach_pubkey' => (bool) rcube_utils::get_input_value('_enigma_attach_pubkey', rcube_utils::INPUT_POST), 'enigma_password_time' => intval(rcube_utils::get_input_value('_enigma_password_time', rcube_utils::INPUT_POST)), ); } diff --git a/plugins/enigma/lib/enigma_engine.php b/plugins/enigma/lib/enigma_engine.php index 96f792d90..c97093329 100644 --- a/plugins/enigma/lib/enigma_engine.php +++ b/plugins/enigma/lib/enigma_engine.php @@ -312,6 +312,33 @@ class enigma_engine } } + /** + * Handler for attaching public key to a message + * + * @param Mail_mime Original message + * + * @return bool True on success, False on failure + */ + function attach_public_key(&$message) + { + $headers = $message->headers(); + $from = rcube_mime::decode_address_list($headers['From'], 1, false, null, true); + $from = $from[1]; + + // find my key + if ($from && ($key = $this->find_key($from))) { + $pubkey_armor = $this->export_key($key->id); + + if (!$pubkey_armor instanceof enigma_error) { + $pubkey_name = '0x' . enigma_key::format_id($key->id) . '.asc'; + $message->addAttachment($pubkey_armor, 'application/pgp-keys', $pubkey_name, false, '7bit'); + return true; + } + } + + return false; + } + /** * Handler for message_part_structure hook. * Called for every part of the message. diff --git a/plugins/enigma/lib/enigma_ui.php b/plugins/enigma/lib/enigma_ui.php index 6ae69daff..37c1d414a 100644 --- a/plugins/enigma/lib/enigma_ui.php +++ b/plugins/enigma/lib/enigma_ui.php @@ -730,6 +730,11 @@ class enigma_ui $menu->add(null, $chbox->show($this->rc->config->get('enigma_encrypt_all') ? 1 : 0, array('name' => '_enigma_encrypt', 'id' => 'enigmaencryptopt'))); + $menu->add(null, html::label(array('for' => 'enigmaattachpubkeyopt'), + rcube::Q($this->enigma->gettext('attachpubkeymsg')))); + $menu->add(null, $chbox->show($this->rc->config->get('enigma_attach_pubkey') ? 1 : 0, + array('name' => '_enigma_attachpubkey', 'id' => 'enigmaattachpubkeyopt'))); + $menu = html::div(array('id' => 'enigmamenu', 'class' => 'popupmenu'), $menu->show()); // Options menu contents @@ -929,12 +934,17 @@ class enigma_ui } /** - * Handle message_ready hook (encryption/signing) + * Handle message_ready hook (encryption/signing/attach public key) */ function message_ready($p) { $savedraft = !empty($_POST['_draft']) && empty($_GET['_saveonly']); + if (!$savedraft && rcube_utils::get_input_value('_enigma_attachpubkey', rcube_utils::INPUT_POST)) { + $this->enigma->load_engine(); + $this->enigma->engine->attach_public_key($p['message']); + } + if (!$savedraft && rcube_utils::get_input_value('_enigma_sign', rcube_utils::INPUT_POST)) { $this->enigma->load_engine(); $status = $this->enigma->engine->sign_message($p['message']); @@ -971,7 +981,7 @@ class enigma_ui return $p; } - /** + /** * Handler for message_compose_body hook * Display error when the message cannot be encrypted * and provide a way to try again with a password. diff --git a/plugins/enigma/localization/en_US.inc b/plugins/enigma/localization/en_US.inc index 0e4d2b43d..5224ca556 100644 --- a/plugins/enigma/localization/en_US.inc +++ b/plugins/enigma/localization/en_US.inc @@ -53,6 +53,7 @@ $labels['supportsignatures'] = 'Enable message signatures verification'; $labels['supportdecryption'] = 'Enable message decryption'; $labels['signdefault'] = 'Sign all messages by default'; $labels['encryptdefault'] = 'Encrypt all messages by default'; +$labels['attachpubkeydefault'] = 'Attach my public PGP key by default'; $labels['passwordtime'] = 'Keep private key passwords for'; $labels['nminutes'] = '$m minute(s)'; $labels['wholesession'] = 'the whole session'; @@ -82,6 +83,7 @@ $labels['signmsg'] = 'Digitally sign this message'; $labels['enterkeypasstitle'] = 'Enter key passphrase'; $labels['enterkeypass'] = 'A passphrase is needed to unlock the secret key ($keyid) for user: $user.'; $labels['arialabelkeyexportoptions'] = 'Keys export options'; +$labels['attachpubkeymsg'] = 'Attach my public key'; $messages = array(); $messages['sigvalid'] = 'Verified signature from $sender.'; diff --git a/plugins/managesieve/lib/Roundcube/rcube_sieve_engine.php b/plugins/managesieve/lib/Roundcube/rcube_sieve_engine.php index 3fb168443..50f4c08d8 100644 --- a/plugins/managesieve/lib/Roundcube/rcube_sieve_engine.php +++ b/plugins/managesieve/lib/Roundcube/rcube_sieve_engine.php @@ -334,7 +334,7 @@ class rcube_sieve_engine else if ($action == 'act' && !$error) { if (isset($this->script[$fid])) { $rule = $this->script[$fid]; - $disabled = $rule['disabled'] ? true : false; + $disabled = !empty($rule['disabled']); $rule['disabled'] = !$disabled; $result = $this->sieve->script->update_rule($fid, $rule); diff --git a/plugins/newmail_notifier/newmail_notifier.php b/plugins/newmail_notifier/newmail_notifier.php index ca7953329..63a2cf884 100644 --- a/plugins/newmail_notifier/newmail_notifier.php +++ b/plugins/newmail_notifier/newmail_notifier.php @@ -159,7 +159,7 @@ class newmail_notifier extends rcube_plugin foreach (array('basic', 'desktop', 'sound') as $type) { $key = 'newmail_notifier_' . $type; if (!in_array($key, $dont_override)) { - $args['prefs'][$key] = rcube_utils::get_input_value('_'.$key, rcube_utils::INPUT_POST) ? true : false; + $args['prefs'][$key] = !empty(rcube_utils::get_input_value('_' . $key, rcube_utils::INPUT_POST)); } } diff --git a/program/lib/Roundcube/rcube_contacts.php b/program/lib/Roundcube/rcube_contacts.php index 5ac575983..c9c01e46a 100644 --- a/program/lib/Roundcube/rcube_contacts.php +++ b/program/lib/Roundcube/rcube_contacts.php @@ -707,7 +707,7 @@ class rcube_contacts extends rcube_addressbook $this->result = null; // clear current result (from get_record()) } - return $updated ? true : false; + return !empty($updated); } /** diff --git a/program/lib/Roundcube/rcube_imap.php b/program/lib/Roundcube/rcube_imap.php index 5f532a50c..52ca22ccf 100644 --- a/program/lib/Roundcube/rcube_imap.php +++ b/program/lib/Roundcube/rcube_imap.php @@ -3304,6 +3304,12 @@ class rcube_imap extends rcube_storage public function get_special_folders($forced = false) { $result = parent::get_special_folders(); + $rcube = rcube::get_instance(); + + // Lock SPECIAL-USE after user preferences change (#4782) + if ($rcube->config->get('lock_special_folders')) { + return $result; + } if (isset($this->icache['special-use'])) { return array_merge($result, $this->icache['special-use']); @@ -4278,7 +4284,7 @@ class rcube_imap extends rcube_storage $this->clear_cache('mailboxes', true); } - return $updated == count($folders) ? true : false; + return $updated == count($folders); } /** diff --git a/program/lib/Roundcube/rcube_imap_generic.php b/program/lib/Roundcube/rcube_imap_generic.php index 810dcce5f..764604d6a 100644 --- a/program/lib/Roundcube/rcube_imap_generic.php +++ b/program/lib/Roundcube/rcube_imap_generic.php @@ -1063,7 +1063,7 @@ class rcube_imap_generic */ public function connected() { - return ($this->fp && $this->logged) ? true : false; + return $this->fp && $this->logged; } /** diff --git a/program/lib/Roundcube/rcube_result_index.php b/program/lib/Roundcube/rcube_result_index.php index 5ea390b2b..2f73c5e58 100644 --- a/program/lib/Roundcube/rcube_result_index.php +++ b/program/lib/Roundcube/rcube_result_index.php @@ -134,7 +134,7 @@ class rcube_result_index */ public function is_error() { - return $this->raw_data === null ? true : false; + return $this->raw_data === null; } /** @@ -144,7 +144,7 @@ class rcube_result_index */ public function is_empty() { - return empty($this->raw_data) ? true : false; + return empty($this->raw_data); } /** diff --git a/program/lib/Roundcube/rcube_result_thread.php b/program/lib/Roundcube/rcube_result_thread.php index 5388eb109..c508a6625 100644 --- a/program/lib/Roundcube/rcube_result_thread.php +++ b/program/lib/Roundcube/rcube_result_thread.php @@ -89,7 +89,7 @@ class rcube_result_thread */ public function is_error() { - return $this->raw_data === null ? true : false; + return $this->raw_data === null; } /** @@ -99,7 +99,7 @@ class rcube_result_thread */ public function is_empty() { - return empty($this->raw_data) ? true : false; + return empty($this->raw_data); } /** diff --git a/program/steps/mail/show.inc b/program/steps/mail/show.inc index 59ae13493..4183535f6 100644 --- a/program/steps/mail/show.inc +++ b/program/steps/mail/show.inc @@ -19,7 +19,7 @@ +-----------------------------------------------------------------------+ */ -$PRINT_MODE = $RCMAIL->action == 'print' ? TRUE : FALSE; +$PRINT_MODE = $RCMAIL->action == 'print'; // Read browser capabilities and store them in session if ($caps = rcube_utils::get_input_value('_caps', rcube_utils::INPUT_GET)) { diff --git a/program/steps/settings/save_prefs.inc b/program/steps/settings/save_prefs.inc index 4657454b9..a314aaf2b 100644 --- a/program/steps/settings/save_prefs.inc +++ b/program/steps/settings/save_prefs.inc @@ -5,7 +5,7 @@ | program/steps/settings/save_prefs.inc | | | | This file is part of the Roundcube Webmail client | - | Copyright (C) 2005-2013, The Roundcube Dev Team | + | Copyright (C) 2005-2016, The Roundcube Dev Team | | | | Licensed under the GNU General Public License version 3 or | | any later version with exceptions for skins & plugins. | @@ -16,6 +16,7 @@ | | +-----------------------------------------------------------------------+ | Author: Thomas Bruederli | + | Author: Aleksander Machniak | +-----------------------------------------------------------------------+ */ @@ -30,9 +31,9 @@ case 'general': 'timezone' => isset($_POST['_timezone']) ? rcube_utils::get_input_value('_timezone', rcube_utils::INPUT_POST) : $CONFIG['timezone'], 'date_format' => isset($_POST['_date_format']) ? rcube_utils::get_input_value('_date_format', rcube_utils::INPUT_POST) : $CONFIG['date_format'], 'time_format' => isset($_POST['_time_format']) ? rcube_utils::get_input_value('_time_format', rcube_utils::INPUT_POST) : ($CONFIG['time_format'] ? $CONFIG['time_format'] : 'H:i'), - 'prettydate' => isset($_POST['_pretty_date']) ? true : false, + 'prettydate' => isset($_POST['_pretty_date']), 'refresh_interval' => isset($_POST['_refresh_interval']) ? intval($_POST['_refresh_interval'])*60 : $CONFIG['refresh_interval'], - 'standard_windows' => isset($_POST['_standard_windows']) ? true : false, + 'standard_windows' => isset($_POST['_standard_windows']), 'skin' => isset($_POST['_skin']) ? rcube_utils::get_input_value('_skin', rcube_utils::INPUT_POST) : $CONFIG['skin'], ); @@ -46,11 +47,11 @@ case 'general': case 'mailbox': $a_user_prefs = array( - 'preview_pane' => isset($_POST['_preview_pane']) ? true : false, + 'preview_pane' => isset($_POST['_preview_pane']), 'preview_pane_mark_read' => isset($_POST['_preview_pane_mark_read']) ? intval($_POST['_preview_pane_mark_read']) : $CONFIG['preview_pane_mark_read'], 'autoexpand_threads' => isset($_POST['_autoexpand_threads']) ? intval($_POST['_autoexpand_threads']) : 0, 'mdn_requests' => isset($_POST['_mdn_requests']) ? intval($_POST['_mdn_requests']) : 0, - 'check_all_folders' => isset($_POST['_check_all_folders']) ? true : false, + 'check_all_folders' => isset($_POST['_check_all_folders']), 'mail_pagesize' => is_numeric($_POST['_mail_pagesize']) ? max(2, intval($_POST['_mail_pagesize'])) : $CONFIG['mail_pagesize'], ); @@ -59,11 +60,11 @@ case 'mailbox': case 'mailview': $a_user_prefs = array( 'message_extwin' => intval($_POST['_message_extwin']), - 'message_show_email' => isset($_POST['_message_show_email']) ? true : false, - 'prefer_html' => isset($_POST['_prefer_html']) ? true : false, - 'inline_images' => isset($_POST['_inline_images']) ? true : false, + 'message_show_email' => isset($_POST['_message_show_email']), + 'prefer_html' => isset($_POST['_prefer_html']), + 'inline_images' => isset($_POST['_inline_images']), 'show_images' => isset($_POST['_show_images']) ? intval($_POST['_show_images']) : 0, - 'display_next' => isset($_POST['_display_next']) ? true : false, + 'display_next' => isset($_POST['_display_next']), 'default_charset' => rcube_utils::get_input_value('_default_charset', rcube_utils::INPUT_POST), ); @@ -75,19 +76,19 @@ case 'compose': 'htmleditor' => intval($_POST['_htmleditor']), 'draft_autosave' => isset($_POST['_draft_autosave']) ? intval($_POST['_draft_autosave']) : 0, 'mime_param_folding' => isset($_POST['_mime_param_folding']) ? intval($_POST['_mime_param_folding']) : 0, - 'force_7bit' => isset($_POST['_force_7bit']) ? true : false, - 'mdn_default' => isset($_POST['_mdn_default']) ? true : false, - 'dsn_default' => isset($_POST['_dsn_default']) ? true : false, - 'reply_same_folder' => isset($_POST['_reply_same_folder']) ? true : false, - 'spellcheck_before_send' => isset($_POST['_spellcheck_before_send']) ? true : false, - 'spellcheck_ignore_syms' => isset($_POST['_spellcheck_ignore_syms']) ? true : false, - 'spellcheck_ignore_nums' => isset($_POST['_spellcheck_ignore_nums']) ? true : false, - 'spellcheck_ignore_caps' => isset($_POST['_spellcheck_ignore_caps']) ? true : false, + 'force_7bit' => isset($_POST['_force_7bit']), + 'mdn_default' => isset($_POST['_mdn_default']), + 'dsn_default' => isset($_POST['_dsn_default']), + 'reply_same_folder' => isset($_POST['_reply_same_folder']), + 'spellcheck_before_send' => isset($_POST['_spellcheck_before_send']), + 'spellcheck_ignore_syms' => isset($_POST['_spellcheck_ignore_syms']), + 'spellcheck_ignore_nums' => isset($_POST['_spellcheck_ignore_nums']), + 'spellcheck_ignore_caps' => isset($_POST['_spellcheck_ignore_caps']), 'show_sig' => isset($_POST['_show_sig']) ? intval($_POST['_show_sig']) : 1, 'reply_mode' => isset($_POST['_reply_mode']) ? intval($_POST['_reply_mode']) : 0, - 'sig_below' => isset($_POST['_sig_below']) ? true : false, + 'sig_below' => isset($_POST['_sig_below']), 'strip_existing_sig' => isset($_POST['_strip_existing_sig']), - 'sig_separator' => isset($_POST['_sig_separator']) ? true : false, + 'sig_separator' => isset($_POST['_sig_separator']), 'default_font' => rcube_utils::get_input_value('_default_font', rcube_utils::INPUT_POST), 'default_font_size' => rcube_utils::get_input_value('_default_font_size', rcube_utils::INPUT_POST), 'reply_all_mode' => intval($_POST['_reply_all_mode']), @@ -100,7 +101,7 @@ case 'compose': case 'addressbook': $a_user_prefs = array( 'default_addressbook' => rcube_utils::get_input_value('_default_addressbook', rcube_utils::INPUT_POST, true), - 'autocomplete_single' => isset($_POST['_autocomplete_single']) ? true : false, + 'autocomplete_single' => isset($_POST['_autocomplete_single']), 'addressbook_sort_col' => rcube_utils::get_input_value('_addressbook_sort_col', rcube_utils::INPUT_POST), 'addressbook_name_listing' => intval(rcube_utils::get_input_value('_addressbook_name_listing', rcube_utils::INPUT_POST)), 'addressbook_pagesize' => is_numeric($_POST['_addressbook_pagesize']) ? max(2, intval($_POST['_addressbook_pagesize'])) : $CONFIG['addressbook_pagesize'], @@ -110,20 +111,22 @@ case 'addressbook': case 'server': $a_user_prefs = array( - 'read_when_deleted' => isset($_POST['_read_when_deleted']) ? true : false, - 'skip_deleted' => isset($_POST['_skip_deleted']) ? true : false, - 'flag_for_deletion' => isset($_POST['_flag_for_deletion']) ? true : false, - 'delete_always' => isset($_POST['_delete_always']) ? true : false, - 'delete_junk' => isset($_POST['_delete_junk']) ? true : false, - 'logout_purge' => isset($_POST['_logout_purge']) ? true : false, - 'logout_expunge' => isset($_POST['_logout_expunge']) ? true : false, + 'read_when_deleted' => isset($_POST['_read_when_deleted']), + 'skip_deleted' => isset($_POST['_skip_deleted']), + 'flag_for_deletion' => isset($_POST['_flag_for_deletion']), + 'delete_always' => isset($_POST['_delete_always']), + 'delete_junk' => isset($_POST['_delete_junk']), + 'logout_purge' => isset($_POST['_logout_purge']), + 'logout_expunge' => isset($_POST['_logout_expunge']), ); break; case 'folders': $a_user_prefs = array( - 'show_real_foldernames' => isset($_POST['_show_real_foldernames']) ? true : false, + 'show_real_foldernames' => isset($_POST['_show_real_foldernames']), + // stop using SPECIAL-USE (#4782) + 'lock_special_folders' => !in_array('lock_special_folders', (array) $CONFIG['dont_override']), ); foreach (rcube_storage::$folder_types as $type) {