[Svn] r3921 - in trunk/plugins: . enigma enigma/home enigma/lib enigma/lib/Crypt enigma/lib/Crypt/GPG enigma/localization enigma/skins enigma/skins/default enigma/skins/default/templates

trac at roundcube.net trac at roundcube.net
Mon Aug 30 11:12:57 CEST 2010


Author: alec
Date: 2010-08-30 04:12:57 -0500 (Mon, 30 Aug 2010)
New Revision: 3921

Added:
   trunk/plugins/enigma/
   trunk/plugins/enigma/README
   trunk/plugins/enigma/config.inc.php
   trunk/plugins/enigma/enigma.js
   trunk/plugins/enigma/enigma.php
   trunk/plugins/enigma/home/
   trunk/plugins/enigma/home/.htaccess
   trunk/plugins/enigma/lib/
   trunk/plugins/enigma/lib/Crypt/
   trunk/plugins/enigma/lib/Crypt/GPG.php
   trunk/plugins/enigma/lib/Crypt/GPG/
   trunk/plugins/enigma/lib/Crypt/GPG/DecryptStatusHandler.php
   trunk/plugins/enigma/lib/Crypt/GPG/Engine.php
   trunk/plugins/enigma/lib/Crypt/GPG/Exceptions.php
   trunk/plugins/enigma/lib/Crypt/GPG/Key.php
   trunk/plugins/enigma/lib/Crypt/GPG/Signature.php
   trunk/plugins/enigma/lib/Crypt/GPG/SubKey.php
   trunk/plugins/enigma/lib/Crypt/GPG/UserId.php
   trunk/plugins/enigma/lib/Crypt/GPG/VerifyStatusHandler.php
   trunk/plugins/enigma/lib/enigma_driver.php
   trunk/plugins/enigma/lib/enigma_driver_gnupg.php
   trunk/plugins/enigma/lib/enigma_engine.php
   trunk/plugins/enigma/lib/enigma_error.php
   trunk/plugins/enigma/lib/enigma_key.php
   trunk/plugins/enigma/lib/enigma_signature.php
   trunk/plugins/enigma/lib/enigma_subkey.php
   trunk/plugins/enigma/lib/enigma_ui.php
   trunk/plugins/enigma/lib/enigma_userid.php
   trunk/plugins/enigma/localization/
   trunk/plugins/enigma/localization/en_US.inc
   trunk/plugins/enigma/skins/
   trunk/plugins/enigma/skins/default/
   trunk/plugins/enigma/skins/default/enigma.css
   trunk/plugins/enigma/skins/default/enigma.png
   trunk/plugins/enigma/skins/default/enigma_error.png
   trunk/plugins/enigma/skins/default/key.png
   trunk/plugins/enigma/skins/default/key_add.png
   trunk/plugins/enigma/skins/default/keys_toolbar.png
   trunk/plugins/enigma/skins/default/templates/
   trunk/plugins/enigma/skins/default/templates/keyimport.html
   trunk/plugins/enigma/skins/default/templates/keyinfo.html
   trunk/plugins/enigma/skins/default/templates/keys.html
Log:
- Enigma plugin: initial commit


Added: trunk/plugins/enigma/README
===================================================================
--- trunk/plugins/enigma/README	                        (rev 0)
+++ trunk/plugins/enigma/README	2010-08-30 09:12:57 UTC (rev 3921)
@@ -0,0 +1,33 @@
+------------------------------------------------------------------
+THIS IS NOT EVEN AN "ALPHA" STATE. USE ONLY FOR DEVELOPMENT!!!!!!!
+------------------------------------------------------------------
+
+Enigma Plugin Status:
+
+* DONE:
+
+- PGP signed messages verification
+- Handling of PGP keys files attached to incoming messages
+- PGP encrypted messages decryption (started)
+- PGP keys management UI (started)
+
+* TODO (must have):
+
+- Parsing of decrypted messages into array (see rcube_mime_struct) and then into rcube_message_part structure
+  (create core class rcube_mime_parser or take over PEAR::Mail_mimeDecode package and improve it)
+- Sending encrypted/signed messages (probably some changes in core will be needed)
+- Per-Identity settings (including keys/certs) (+ split Identities details page into tabs)
+- Handling big messages with temp files (including changes in Roundcube core)
+- Performance improvements (some caching, code review)
+- better (and more) icons
+
+* TODO (later):
+
+- Keys generation
+- Certs generation
+- Keys/Certs info in Contacts details page (+ split Contact details page into tabs)
+- Key server support
+- S/MIME signed messages verification
+- S/MIME encrypted messages decryption
+- Handling of S/MIME certs files attached to incoming messages
+- SSL (S/MIME) Certs management

Added: trunk/plugins/enigma/config.inc.php
===================================================================
--- trunk/plugins/enigma/config.inc.php	                        (rev 0)
+++ trunk/plugins/enigma/config.inc.php	2010-08-30 09:12:57 UTC (rev 3921)
@@ -0,0 +1,14 @@
+<?php
+
+// Enigma Plugin options
+// --------------------
+
+// A driver to use for PGP. Default: "gnupg".
+$rcmail_config['enigma_pgp_driver'] = 'gnupg';
+
+// A driver to use for S/MIME. Default: "phpssl".
+$rcmail_config['enigma_smime_driver'] = 'phpssl';
+
+// Keys directory for all users. Default 'enigma/home'.
+// Must be writeable by PHP process
+$rcmail_config['enigma_pgp_homedir'] = null;

Added: trunk/plugins/enigma/enigma.js
===================================================================
--- trunk/plugins/enigma/enigma.js	                        (rev 0)
+++ trunk/plugins/enigma/enigma.js	2010-08-30 09:12:57 UTC (rev 3921)
@@ -0,0 +1,134 @@
+/* Enigma Plugin */
+
+if (window.rcmail)
+{
+    rcmail.addEventListener('init', function(evt)
+    {
+        if (rcmail.env.task == 'settings') {
+            rcmail.register_command('plugin.enigma', function() { rcmail.goto_url('plugin.enigma') }, true);
+            rcmail.register_command('plugin.enigma-key-import', function() { rcmail.enigma_key_import() }, true);
+            rcmail.register_command('plugin.enigma-key-export', function() { rcmail.enigma_key_export() }, true);
+
+            if (rcmail.gui_objects.keyslist)
+            {
+                var p = rcmail;
+                rcmail.keys_list = new rcube_list_widget(rcmail.gui_objects.keyslist,
+                    {multiselect:false, draggable:false, keyboard:false});
+                rcmail.keys_list.addEventListener('select', function(o){ p.enigma_key_select(o); });
+                rcmail.keys_list.init();
+                rcmail.keys_list.focus();
+            }
+
+            if (rcmail.env.action == 'edit-prefs') {
+                rcmail.enable_command('search', 'reset-search', true);
+                rcmail.addEventListener('beforesearch', 'enigma_search', rcmail);
+                rcmail.addEventListener('beforereset-search', 'enigma_search_reset', rcmail);
+            }
+            else if (rcmail.env.action == 'plugin.enigma') {
+                rcmail.register_command('plugin.enigma-import', function() { rcmail.enigma_import() }, true);
+                rcmail.register_command('plugin.enigma-export', function() { rcmail.enigma_export() }, true);
+            }
+        }
+    });
+}
+
+/*********************************************************/
+/*********       Enigma Settings  methods        *********/
+/*********************************************************/
+
+// Display key(s) import form
+rcube_webmail.prototype.enigma_key_import = function()
+{
+    this.enigma_loadframe(null, '&_a=keyimport');
+};
+
+// Submit key(s) form
+rcube_webmail.prototype.enigma_import = function()
+{
+    var form, file;
+    if (form = this.gui_objects.importform) {
+        file = document.getElementById('rcmimportfile');
+        if (file && !file.value) {
+            alert(this.get_label('selectimportfile'));
+            return;
+        }
+        form.submit();
+        this.set_busy(true, 'importwait');
+        this.lock_form(form, true);
+   }
+};
+
+// list row selection handler
+rcube_webmail.prototype.enigma_key_select = function(list)
+{
+    var id;
+    if (id = list.get_single_selection())
+        this.enigma_loadframe(id);
+};
+
+// load key frame
+rcube_webmail.prototype.enigma_loadframe = function(id, url)
+{
+    var frm, win;
+    if (this.env.contentframe && window.frames && (frm = window.frames[this.env.contentframe])) {
+        if (!id && !url && (win = window.frames[this.env.contentframe])) {
+            if (win.location && win.location.href.indexOf(this.env.blankpage)<0)
+                win.location.href = this.env.blankpage;
+            return;
+        }
+        this.set_busy(true);
+        if (!url)
+            url = '&_a=keyinfo&_id='+id;
+        frm.location.href = this.env.comm_path+'&_action=plugin.enigma&_framed=1' + url;
+    }
+};
+
+rcube_webmail.prototype.enigma_search = function(props)
+{
+    if (!props && this.gui_objects.qsearchbox)
+        props = this.gui_objects.qsearchbox.value;
+
+    if (props) {
+//        if (this.gui_objects.search_filter)
+  //          addurl += '&_filter=' + this.gui_objects.search_filter.value;
+        this.env.current_page = 1;
+        this.set_busy(true, 'searching');
+        this.enigma_loadframe();
+
+        // reload page (for keys list refresh)
+        this.http_post('plugin.enigma',
+            {'_a': 'keysearch', '_q': urlencode(props)},
+            true);
+    }
+
+    // skip default 'search' command action
+    return false;
+}
+
+rcube_webmail.prototype.enigma_search_reset = function(props)
+{
+    var s = this.env.search_request;
+    this.reset_qsearch();
+
+    if (s) {
+        this.enigma_loadframe();
+        // reload page (for keys list refresh)
+    }
+
+    // skip default 'reset-search' command action
+    return false;
+}
+
+/*********************************************************/
+/*********        Enigma Message methods         *********/
+/*********************************************************/
+
+// Import attached keys/certs file
+rcube_webmail.prototype.enigma_import_attachment = function(mime_id)
+{
+    this.set_busy(true, 'loading');
+    this.http_post('plugin.enigmaimport', '_uid='+this.env.uid+'&_mbox='
+        +urlencode(this.env.mailbox)+'&_part='+urlencode(mime_id), true);
+
+    return false;
+};

Added: trunk/plugins/enigma/enigma.php
===================================================================
--- trunk/plugins/enigma/enigma.php	                        (rev 0)
+++ trunk/plugins/enigma/enigma.php	2010-08-30 09:12:57 UTC (rev 3921)
@@ -0,0 +1,472 @@
+<?php
+/*
+ +-------------------------------------------------------------------------+
+ | Enigma Plugin for Roundcube                                             |
+ | Version 0.1                                                             |
+ |                                                                         |
+ | This program is free software; you can redistribute it and/or modify    |
+ | it under the terms of the GNU General Public License version 2          |
+ | as published by the Free Software Foundation.                           |
+ |                                                                         |
+ | This program is distributed in the hope that it will be useful,         |
+ | but WITHOUT ANY WARRANTY; without even the implied warranty of          |
+ | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the           |
+ | GNU General Public License for more details.                            |
+ |                                                                         |
+ | You should have received a copy of the GNU General Public License along |
+ | with this program; if not, write to the Free Software Foundation, Inc., |
+ | 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.             |
+ |                                                                         |
+ +-------------------------------------------------------------------------+
+ | Author: Aleksander Machniak <alec at alec.pl>                              |
+ +-------------------------------------------------------------------------+
+*/
+
+/*
+    This class contains only hooks and action handlers.
+    Most plugin logic is placed in enigma_engine and enigma_ui classes.
+*/
+
+class enigma extends rcube_plugin
+{
+    public $task = 'mail|settings';
+    public $rc;
+    public $engine;
+
+    private $env_loaded;
+    private $message;
+    private $keys_parts = array();
+    private $keys_bodies = array();
+
+
+    /**
+     * Plugin initialization.
+     */
+    function init()
+    {
+        $rcmail = rcmail::get_instance();
+        $this->rc = $rcmail;
+
+        if ($this->rc->task == 'mail') {
+            // message parse/display hooks
+            $this->add_hook('message_part_structure', array($this, 'parse_structure'));
+            $this->add_hook('message_body_prefix', array($this, 'status_message'));
+
+            // message sending hooks
+            //$this->add_hook('outgoing_message_body', array($this, 'msg_encode'));
+            //$this->add_hook('outgoing_message_body', array($this, 'msg_sign'));
+
+            if ($rcmail->action == 'show' || $rcmail->action == 'preview') {
+                $this->add_hook('message_load', array($this, 'message_load'));
+                $this->add_hook('template_object_messagebody', array($this, 'message_output'));
+            }
+
+            $this->register_action('plugin.enigmaimport', array($this, 'import_file'));
+        }
+        else if ($this->rc->task == 'settings') {
+            // add hooks for Enigma settings
+            $this->add_hook('preferences_sections_list', array($this, 'preferences_section'));
+            $this->add_hook('preferences_list', array($this, 'preferences_list'));
+            $this->add_hook('preferences_save', array($this, 'preferences_save'));
+
+            // register handler for keys/certs management
+            $this->register_action('plugin.enigma', array($this, 'preferences_ui'));
+
+            // grab keys/certs management iframe requests
+            $section = get_input_value('_section', RCUBE_INPUT_GET);
+            if ($this->rc->action == 'edit-prefs' && preg_match('/^enigma(certs|keys)/', $section)) {
+                $this->load_ui();
+                $this->ui->init($section);
+            }
+
+            // include main js script
+//            $this->include_script('enigma.js');
+        }
+    }
+
+    /**
+     * Plugin environment initialization.
+     */
+    function load_env()
+    {
+        if ($this->env_loaded)
+            return;
+
+        $this->env_loaded = true;
+
+        // Add include path for Enigma classes and drivers
+        $include_path = $this->home . '/lib' . PATH_SEPARATOR;
+        $include_path .= ini_get('include_path');
+        set_include_path($include_path);
+
+        // load the Enigma plugin configuration
+        $this->load_config();
+
+        // include localization (if wasn't included before)
+        $this->add_texts('localization/');
+    }
+
+    /**
+     * Plugin UI initialization.
+     */
+    function load_ui()
+    {
+        if ($this->ui)
+            return;
+
+        // load config/localization
+        $this->load_env();
+
+