Rewrote the basic filter definition.
authorGunnar Wrobel <p@rdus.de>
Thu, 15 Jul 2010 20:26:41 +0000 (22:26 +0200)
committerGunnar Wrobel <p@rdus.de>
Wed, 25 Aug 2010 17:21:37 +0000 (19:21 +0200)
22 files changed:
framework/Kolab_Filter/lib/Horde/Kolab/Filter.php [new file with mode: 0644]
framework/Kolab_Filter/lib/Horde/Kolab/Filter/Base.php
framework/Kolab_Filter/lib/Horde/Kolab/Filter/Configuration.php [new file with mode: 0644]
framework/Kolab_Filter/lib/Horde/Kolab/Filter/Exception/IoError.php [new file with mode: 0644]
framework/Kolab_Filter/lib/Horde/Kolab/Filter/Factory.php [new file with mode: 0644]
framework/Kolab_Filter/lib/Horde/Kolab/Filter/Incoming.php
framework/Kolab_Filter/lib/Horde/Kolab/Filter/Temporary.php [new file with mode: 0644]
framework/Kolab_Filter/lib/Horde/Kolab/Filter/Temporary/File.php [new file with mode: 0644]
framework/Kolab_Filter/package.xml
framework/Kolab_Filter/test/Horde/Kolab/Filter/AllTests.php
framework/Kolab_Filter/test/Horde/Kolab/Filter/Autoload.php
framework/Kolab_Filter/test/Horde/Kolab/Filter/ContentTest.php [deleted file]
framework/Kolab_Filter/test/Horde/Kolab/Filter/ContentTestOld.php [new file with mode: 0644]
framework/Kolab_Filter/test/Horde/Kolab/Filter/Helper/AddressFilter.php [new file with mode: 0644]
framework/Kolab_Filter/test/Horde/Kolab/Filter/IncomingTest.php [deleted file]
framework/Kolab_Filter/test/Horde/Kolab/Filter/Integration/CliTest.php
framework/Kolab_Filter/test/Horde/Kolab/Filter/Integration/IncomingTest.php [new file with mode: 0644]
framework/Kolab_Filter/test/Horde/Kolab/Filter/LoadTest.php [deleted file]
framework/Kolab_Filter/test/Horde/Kolab/Filter/ResourceTest.php [deleted file]
framework/Kolab_Filter/test/Horde/Kolab/Filter/ResourceTestOld.php [new file with mode: 0644]
framework/Kolab_Filter/test/Horde/Kolab/Filter/StoryTestCase.php
framework/Kolab_Filter/test/Horde/Kolab/Filter/Unit/Helper/AddressFilter.php [new file with mode: 0644]

diff --git a/framework/Kolab_Filter/lib/Horde/Kolab/Filter.php b/framework/Kolab_Filter/lib/Horde/Kolab/Filter.php
new file mode 100644 (file)
index 0000000..674ce72
--- /dev/null
@@ -0,0 +1,66 @@
+<?php
+/**
+ * The main entry point for the Kolab_Filter application.
+ *
+ * PHP version 5
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/** Setup default autoloading */
+require_once 'Horde/Autoloader/Default.php';
+
+/**
+ * The main entry point for the Kolab_Filter application.
+ *
+ * Copyright 2010 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you did not
+ * receive this file, see
+ * http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+class Horde_Kolab_Filter
+{
+    public function __construct(Horde_Injector $injector = null)
+    {
+        if ($injector === null) {
+            $this->injector = new Horde_Injector(new Horde_Injector_TopLevel());
+
+            $this->injector->bindFactory(
+                'Horde_Log_Logger', 'Horde_Kolab_Filter_Factory', 'getLogger'
+            );
+            $this->injector->bindImplementation(
+                'Horde_Kolab_Filter_Temporary', 'Horde_Kolab_Filter_Temporary_File'
+            );
+        } else {
+            $this->injector = $injector;
+        }
+    }
+
+    /**
+     * Run the mail filter.
+     *
+     * @param string $type The type of filtering to run (Incoming|Content).
+     */
+    public function main($type, $inh = STDIN, $transport = null)
+    {
+        /** Setup all configuration information */
+        /* $configuration = $this->injector->getInstance('Horde_Kolab_Filter_Configuration'); */
+        /* $configuration->init(); */
+
+        /** Now run the filter */
+        $filter = $this->injector->getInstance('Horde_Kolab_Filter_' . $type);
+        $filter->init();
+        $filter->parse($inh, $transport);
+    }
+}
\ No newline at end of file
index d7240f2..2f89303 100644 (file)
@@ -25,92 +25,42 @@ class Horde_Kolab_Filter_Base
     var $_id = '';
 
     /**
-     * A temporary buffer file for storing the message.
+     * Configuration.
      *
-     * @var string
-     */
-    var $_tmpfile;
-
-    /**
-     * The file handle for the temporary file.
-     *
-     * @var int
-     */
-    var $_tmpfh;
-
-    /**
-     * The message sender.
-     *
-     * @var string
-     */
-    var $_sender;
-
-    /**
-     * The message recipients.
-     *
-     * @var array
+     * @param Horde_Kolab_Filter_Configuration 
      */
-    var $_recipients = array();
-
-    /**
-     * The client host trying to send the message.
-     *
-     * @var string
-     */
-    var $_client_address;
-
-    /**
-     * The client host trying to send the message.
-     *
-     * @var string
-     */
-    var $_fqhostname;
-
-    /**
-     * The authenticated username of the sender.
-     *
-     * @var string
-     */
-    var $_sasl_username;
-
-    /**
-     * Comman line parser.
-     *
-     * @param Horde_Kolab_Filter_Cli 
-     */
-    private $_cli;
+    private $_config;
 
     /**
      * The log backend that needs to implement the debug(), info() and err()
      * methods.
      *
-     * @param mixed 
+     * @param Horde_Kolab_Filter_Logger
      */
-    private $_logger;
+    protected $_logger;
 
     /**
      * Constructor.
      *
-     * @param mixed $logger The logger.
+     * @param Horde_Kolab_Filter_Configuration $config     The configuration.
+     * @param Horde_Kolab_Filter_Logger        $logger     The logging backend.
      */
     public function __construct(
-        Horde_Kolab_Filter_Cli $cli,
-        $logger
+        Horde_Kolab_Filter_Configuration $config,
+        Horde_Log_Logger $logger
     ) {
-        $this->_cli    = $cli;
-        $this->_logger = $logger;
+        $this->_config    = $config;
+        $this->_logger    = $logger;
     }
 
     /**
-     * Initialize the class.
+     * Initialize the filter.
+     *
+     * @return NULL
      */
-    function init()
+    public function init()
     {
-        /* Parse our arguments */
-        $result = $this->_parseArgs();
-        if (is_a($result, 'PEAR_Error')) {
-            return $result;
-        }
+        $this->_config->init();
     }
 
     /**
@@ -118,147 +68,40 @@ class Horde_Kolab_Filter_Base
      *
      * @param int    $inh  The file handle pointing to the message.
      * @param string $transport  The name of the transport driver.
+     *
+     * @return NULL
      */
-    function parse($inh = STDIN, $transport = null)
+    public function parse($inh = STDIN, $transport = null)
     {
-        /* Setup the temporary storage */
-        $result = $this->_initTmp();
-        if ($result instanceOf PEAR_Error) {
-            return $result;
-        }
+        /* $this->_logger->debug( */
+        /*     sprintf( */
+        /*         "Arguments: %s", */
+        /*         print_r($this->_config->getArguments(), true) */
+        /*     ) */
+        /* ); */
 
         $this->_logger->debug(
             sprintf(
                 "%s starting up (sender=%s, recipients=%s, client_address=%s)",
                 get_class($this),
-                $this->_sender,
-                join(', ',$this->_recipients),
-                $this->_client_address
+                $this->_config->getSender(),
+                join(', ',$this->_config->getRecipients()),
+                $this->_config->getClientAddress()
             )
         );
 
-        $result = $this->_parse($inh, $transport);
-        if (is_a($result, 'PEAR_Error')) {
-            return $result;
-        }
+        $this->_parse($inh, $transport);
 
-        Horde::logMessage(sprintf("%s successfully completed (sender=%s, recipients=%s, client_address=%s, id=%s)",
-                                  get_class($this), $this->_sender,
-                                  join(', ',$this->_recipients),
-                                  $this->_client_address, $this->_id),
-                          'INFO');
-    }
-
-    /**
-     * Creates a buffer for temporary storage of the message.
-     *
-     * @return mixed A PEAR_Error in case of an error, nothing otherwise.
-     */
-    function _initTmp()
-    {
-        global $conf;
-
-        if (isset($conf['kolab']['filter']['tempdir'])) {
-            $tmpdir = $conf['kolab']['filter']['tempdir'];
-        } else {
-            $tmpdir = Horde::getTempDir();
-        }
-
-        /* Temp file for storing the message */
-        $this->_tmpfile = @tempnam($tmpdir, 'IN.' . get_class($this) . '.');
-        $this->_tmpfh = @fopen($this->_tmpfile, "w");
-        if( !$this->_tmpfh ) {
-            $msg = $php_errormsg;
-            return PEAR::raiseError(sprintf("Error: Could not open %s for writing: %s",
-                                            $this->_tmpfile, $msg),
-                                    OUT_LOG | EX_IOERR);
-        }
-
-        register_shutdown_function(array($this, '_cleanupTmp'));
-    }
-
-    /**
-     * A shutdown function for removing the temporary file.
-     */
-    function _cleanupTmp() {
-        if (@file_exists($this->_tmpfile)) {
-            @unlink($this->_tmpfile);
-        }
-    }
-
-    /**
-     * Parse the command line arguments provided to the filter and
-     * setup the class.
-     *
-     * @return mixed A PEAR_Error in case of an error, nothing otherwise.
-     */
-    function _parseArgs()
-    {
-        global $conf;
-
-        $values = $this->_cli->getOptions();
-
-        if (!empty($values['config']) && file_exists($values['config'])) {
-            require_once $values['config'];
-        }
-
-        $this->_sender = strtolower($values['sender']);
-        $this->_recipients = array_map('strtolower', $values['recipient']);
-        $this->_client_address = $values['client'];
-        $this->_fqhostname = strtolower($values['host']);
-        $this->_sasl_username = strtolower($values['user']);
-
-        Horde::logMessage(sprintf("Arguments: %s", print_r($values, true)), 'DEBUG');
-
-        $GLOBALS['registry']->setCharset('utf-8');
-
-        if (!empty($conf['kolab']['filter']['locale_path'])
-            && !empty($conf['kolab']['filter']['locale'])) {
-            $GLOBALS['registry']->setTextdomain('Kolab_Filter', $conf['kolab']['filter']['locale_path']);
-            setlocale(LC_ALL, $conf['kolab']['filter']['locale']);
-        }
-
-        /* This is used as the default domain for unqualified adresses */
-        global $_SERVER;
-        if (!array_key_exists('SERVER_NAME', $_SERVER)) {
-            $_SERVER['SERVER_NAME'] = $conf['kolab']['imap']['server'];
-        }
-
-        if (!array_key_exists('REMOTE_ADDR', $_SERVER)) {
-            $_SERVER['REMOTE_ADDR'] = $conf['kolab']['imap']['server'];
-        }
-
-        if (!array_key_exists('REMOTE_HOST', $_SERVER)) {
-            $_SERVER['REMOTE_HOST'] = $conf['kolab']['imap']['server'];
-        }
-
-        /* Always display all possible problems */
-        ini_set('error_reporting', E_ALL);
-        ini_set('track_errors', '1');
-
-        /* Setup error logging */
-        if (isset($conf['kolab']['filter']['error_log'])) {
-            ini_set('log_errors', '1');
-            ini_set('error_log', $conf['kolab']['filter']['error_log']);
-        }
-
-        /* Print PHP messages to StdOut if we are debugging */
-        if (isset($conf['kolab']['filter']['debug'])
-            && $conf['kolab']['filter']['debug']) {
-            ini_set('display_errors', '1');
-        }
-
-        /* Provide basic syslog debugging if nothing has been
-         * specified
-         */
-        if (!isset($conf['log'])) {
-            $conf['log']['enabled']          = true;
-            $conf['log']['priority']         = 'DEBUG';
-            $conf['log']['type']             = 'syslog';
-            $conf['log']['name']             = LOG_MAIL;
-            $conf['log']['ident']            = 'kolabfilter';
-            $conf['log']['params']           = array();
-        }
+        $this->_logger->info(
+            sprintf(
+                "%s successfully completed (sender=%s, recipients=%s, client_address=%s, id=%s)",
+                get_class($this),
+                $this->_config->getSender(),
+                join(', ',$this->_config->getRecipients()),
+                $this->_config->getClientAddress(),
+                $this->_id
+           )
+       );
     }
 }
 
diff --git a/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Configuration.php b/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Configuration.php
new file mode 100644 (file)
index 0000000..1b812e8
--- /dev/null
@@ -0,0 +1,193 @@
+<?php
+/**
+ * The configuration of the Kolab_Filter package.
+ *
+ * PHP version 5
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/**
+ * The configuration of the Kolab_Filter package.
+ *
+ * Copyright 2008 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you did not
+ * receive this file, see
+ * http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+class Horde_Kolab_Filter_Configuration
+{
+    /**
+     * The message sender.
+     *
+     * @var string
+     */
+    private $_sender;
+
+    /**
+     * The message recipients.
+     *
+     * @var array
+     */
+    private $_recipients = array();
+
+    /**
+     * The client host trying to send the message.
+     *
+     * @var string
+     */
+    private $_client_address;
+
+    /**
+     * The client host trying to send the message.
+     *
+     * @var string
+     */
+    private $_fqhostname;
+
+    /**
+     * The authenticated username of the sender.
+     *
+     * @var string
+     */
+    private $_sasl_username;
+
+    /**
+     * The parameters from the configuration file.
+     *
+     * @var array
+     */
+    private $_conf;
+
+    /**
+     * Command line parser.
+     *
+     * @param Horde_Kolab_Filter_Cli 
+     */
+    private $_cli;
+
+    /**
+     * Constructor.
+     *
+     * @param Horde_Kolab_Filter_Cli $cli The CLI parser.
+     */
+    public function __construct(
+        Horde_Kolab_Filter_Cli $cli
+    ) {
+        $this->_cli = $cli;
+    }
+
+    /**
+     * Initialize the configuration.
+     *
+     * @return NULL
+     */
+    public function init()
+    {
+        $values = $this->_cli->getOptions();
+
+        $this->_sender = strtolower($values['sender']);
+        $this->_recipients = array_map('strtolower', $values['recipient']);
+        $this->_client_address = $values['client'];
+        $this->_fqhostname = strtolower($values['host']);
+        $this->_sasl_username = strtolower($values['user']);
+
+        global $conf;
+
+        if (!empty($values['config']) && file_exists($values['config'])) {
+            require_once $values['config'];
+        }
+
+        Horde_Nls::setCharset('utf-8');
+
+        if (!empty($conf['kolab']['filter']['locale_path'])
+            && !empty($conf['kolab']['filter']['locale'])) {
+            Horde_Nls::setTextdomain('Kolab_Filter', $conf['kolab']['filter']['locale_path'], Horde_Nls::getCharset());
+            setlocale(LC_ALL, $conf['kolab']['filter']['locale']);
+        }
+
+        /* This is used as the default domain for unqualified adresses */
+        if (!array_key_exists('SERVER_NAME', $_SERVER)) {
+            $_SERVER['SERVER_NAME'] = $conf['kolab']['imap']['server'];
+        }
+
+        if (!array_key_exists('REMOTE_ADDR', $_SERVER)) {
+            $_SERVER['REMOTE_ADDR'] = $conf['kolab']['imap']['server'];
+        }
+
+        if (!array_key_exists('REMOTE_HOST', $_SERVER)) {
+            $_SERVER['REMOTE_HOST'] = $conf['kolab']['imap']['server'];
+        }
+
+        /* Always display all possible problems */
+        ini_set('error_reporting', E_ALL);
+        ini_set('track_errors', '1');
+
+        /* Setup error logging */
+        if (isset($conf['kolab']['filter']['error_log'])) {
+            ini_set('log_errors', '1');
+            ini_set('error_log', $conf['kolab']['filter']['error_log']);
+        }
+
+        /* Print PHP messages to StdOut if we are debugging */
+        if (isset($conf['kolab']['filter']['debug'])
+            && $conf['kolab']['filter']['debug']) {
+            ini_set('display_errors', '1');
+        }
+
+        /* Provide basic syslog debugging if nothing has been
+         * specified
+         */
+        if (!isset($conf['log'])) {
+            $conf['log']['enabled']          = true;
+            $conf['log']['priority']         = 'DEBUG';
+            $conf['log']['type']             = 'syslog';
+            $conf['log']['name']             = LOG_MAIL;
+            $conf['log']['ident']            = 'kolabfilter';
+            $conf['log']['params']           = array();
+        }
+
+        $this->_conf = $conf;
+    }
+
+    public function getSender()
+    {
+        return $this->_sender;
+    }
+
+    public function getRecipients()
+    {
+        return $this->_recipients;
+    }
+
+    public function getClientAddress()
+    {
+        return $this->_client_address;
+    }
+
+    public function getFqHostname()
+    {
+        return $this->_fqhostname;
+    }
+
+    public function getSaslUsername()
+    {
+        return $this->_sasl_username;
+    }
+
+    public function getConf()
+    {
+        return $this->_conf;
+    }
+}
\ No newline at end of file
diff --git a/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Exception/IoError.php b/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Exception/IoError.php
new file mode 100644 (file)
index 0000000..156e5dc
--- /dev/null
@@ -0,0 +1,46 @@
+<?php
+/**
+ * This class provides an error thrown when an I/O error occured.
+ *
+ * PHP version 5
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/**
+ * This class provides an error thrown when an I/O error occured.
+ *
+ * Copyright 2010 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you
+ * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html.
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+class Horde_Kolab_Filter_Exception_IoError
+extends Horde_Kolab_Filter_Exception
+{
+    /**
+     * Construct the exception
+     *
+     * @param string $msg
+     * @param Exception $previous
+     */
+    public function __construct($msg = '', Exception $previous = null)
+    {
+        parent::__construct(
+            $msg,
+            Horde_Kolab_Filter_Exception::OUT_LOG |
+            Horde_Kolab_Filter_Exception::EX_IOERR,
+            $previous
+        );
+    }
+}
diff --git a/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Factory.php b/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Factory.php
new file mode 100644 (file)
index 0000000..01cd29b
--- /dev/null
@@ -0,0 +1,98 @@
+<?php
+/**
+ * A factory for Kolab_Filter objects.
+ *
+ * PHP version 5
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/**
+ * A factory for Kolab_Filter objects.
+ *
+ * Copyright 2010 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you did not
+ * receive this file, see
+ * http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+class Horde_Kolab_Filter_Factory
+{
+    /**
+     * Creates the logger.
+     *
+     * @param Horde_Injector $injector The injector provides the required
+     *                                 configuration.
+     *
+     * @return Horde_Log_Logger The logger.
+     */
+    public function getLogger(Horde_Injector $injector)
+    {
+        $configuration = $injector->getInstance('Horde_Kolab_Filter_Configuration');
+
+        $conf = $configuration->getConf();
+        switch ($conf['log']['type']) {
+        case 'file':
+        case 'stream':
+            $append = ($conf['log']['type'] == 'file')
+                ? ($conf['log']['params']['append'] ? 'a+' : 'w+')
+                : null;
+            $format = isset($conf['log']['params']['format'])
+                ? $conf['log']['params']['format']
+                : 'default';
+
+            switch ($format) {
+            case 'custom':
+                $formatter = new Horde_Log_Formatter_Xml(array('format' => $conf['log']['params']['template']));
+                break;
+
+            case 'default':
+            default:
+                // Use Horde_Log defaults.
+                $formatter = null;
+                break;
+
+            case 'xml':
+                $formatter = new Horde_Log_Formatter_Xml();
+                break;
+            }
+
+            try {
+                $handler = new Horde_Log_Handler_Stream($conf['log']['name'], $append, $formatter);
+            } catch (Horde_Log_Exception $e) {
+                return new Horde_Log_Logger(new Horde_Log_Handler_Null());
+            }
+            break;
+        case 'syslog':
+            try {
+                $handler = new Horde_Log_Handler_Syslog();
+            } catch (Horde_Log_Exception $e) {
+                return new Horde_Log_Logger(new Horde_Log_Handler_Null());
+            }
+            break;
+        case 'mock':
+            $handler = new Horde_Log_Handler_Mock();
+            break;
+        case 'null':
+        default:
+            // Use default null handler.
+            return new Horde_Log_Logger(new Horde_Log_Handler_Null());
+            break;
+        }
+        if (!defined('Horde_Log::' . $conf['log']['priority'])) {
+            $conf['log']['priority'] = 'NOTICE';
+        }
+        $handler->addFilter(constant('Horde_Log::' . $conf['log']['priority']));
+        return new Horde_Log_Logger($handler);
+    }
+}
\ No newline at end of file
index 544133e..279e306 100644 (file)
@@ -24,6 +24,12 @@ require_once dirname(__FILE__) . '/Transport.php';
  */
 class Horde_Kolab_Filter_Incoming extends Horde_Kolab_Filter_Base
 {
+    /**
+     * A temporary storage place for incoming messages.
+     *
+     * @param Horde_Kolab_Filter_Temporary
+     */
+    private $_temporary;
 
     /**
      * An array of headers to be added to the message
@@ -33,6 +39,34 @@ class Horde_Kolab_Filter_Incoming extends Horde_Kolab_Filter_Base
     var $_add_headers;
 
     /**
+     * Constructor.
+     *
+     * @param Horde_Kolab_Filter_Configuration $config     The configuration.
+     * @param Horde_Kolab_Filter_Temporary     $temporaray Temporary storage
+     *                                                     location.
+     * @param Horde_Kolab_Filter_Logger        $logger     The logging backend.
+     */
+    public function __construct(
+        Horde_Kolab_Filter_Configuration $config,
+        Horde_Kolab_Filter_Temporary $temporary,
+        Horde_Log_Logger $logger
+    ) {
+        parent::__construct($config, $logger);
+        $this->_temporary = $temporary;
+    }
+
+    /**
+     * Initialize the filter.
+     *
+     * @return NULL
+     */
+    public function init()
+    {
+        parent::init();
+        $this->_temporary->init();
+    }
+
+    /**
      * Handle the message.
      *
      * @param int    $inh        The file handle pointing to the message.
@@ -44,11 +78,6 @@ class Horde_Kolab_Filter_Incoming extends Horde_Kolab_Filter_Base
     {
         global $conf;
 
-        $result = $this->init();
-        if (is_a($result, 'PEAR_Error')) {
-            return $result;
-        }
-
         if (empty($transport)) {
             if (isset($conf['kolab']['filter']['delivery_backend'])) {
                 $transport = $conf['kolab']['filter']['delivery_backend'];
@@ -57,6 +86,8 @@ class Horde_Kolab_Filter_Incoming extends Horde_Kolab_Filter_Base
             }
         }
 
+        $this->_tmpfh = $this->_temporary->getHandle();
+
         $ical = false;
         $add_headers = array();
         $headers_done = false;
@@ -161,7 +192,7 @@ class Horde_Kolab_Filter_Incoming extends Horde_Kolab_Filter_Base
 
         /* Check if we still have recipients */
         if (empty($this->_recipients)) {
-            Horde::logMessage("No recipients left.", 'DEBUG');
+            $this->_logger->debug("No recipients left.", 'DEBUG');
             return;
         } else {
             $result = $this->_deliver($transport);
@@ -170,7 +201,7 @@ class Horde_Kolab_Filter_Incoming extends Horde_Kolab_Filter_Base
             }
         }
 
-        Horde::logMessage("Filter_Incoming successfully completed.", 'DEBUG');
+        $this->_logger->debug("Filter_Incoming successfully completed.", 'DEBUG');
     }
 
     private function _transportItipReply(Horde_Kolab_Resource_Reply $reply)
@@ -287,7 +318,7 @@ class Horde_Kolab_Filter_Incoming extends Horde_Kolab_Filter_Base
             }
             $transport = &Horde_Kolab_Filter_Transport::factory($transport, $params);
 
-            $tmpf = @fopen($this->_tmpfile, 'r');
+            $tmpf = $this->_temporary->getReadHandle();
             if (!$tmpf) {
                 $msg = $php_errormsg;
                 return PEAR::raiseError(sprintf("Error: Could not open %s for writing: %s",
diff --git a/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Temporary.php b/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Temporary.php
new file mode 100644 (file)
index 0000000..87c9ab8
--- /dev/null
@@ -0,0 +1,31 @@
+<?php
+/**
+ * Definition of a temporary storage place for incoming messages.
+ *
+ * PHP version 5
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/**
+ * Definition of a temporary storage place for incoming messages.
+ *
+ * Copyright 2010 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you did not
+ * receive this file, see
+ * http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+interface Horde_Kolab_Filter_Temporary
+{
+}
\ No newline at end of file
diff --git a/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Temporary/File.php b/framework/Kolab_Filter/lib/Horde/Kolab/Filter/Temporary/File.php
new file mode 100644 (file)
index 0000000..fc203e4
--- /dev/null
@@ -0,0 +1,126 @@
+<?php
+/**
+ * File based temporary storage place for incoming messages.
+ *
+ * PHP version 5
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/**
+ * File based temporary storage place for incoming messages.
+ *
+ * Copyright 2004-2010 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you did not
+ * receive this file, see
+ * http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @category Kolab
+ * @package  Kolab_Filter
+ * @author   Gunnar Wrobel <wrobel@pardus.de>
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link     http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+class Horde_Kolab_Filter_Temporary_File
+implements Horde_Kolab_Filter_Temporary
+{
+    /**
+     * A temporary buffer file for storing the message.
+     *
+     * @var string
+     */
+    var $_tmpfile;
+
+    /**
+     * The file handle for the temporary file.
+     *
+     * @var int
+     */
+    var $_tmpfh;
+
+    /**
+     * Configuration.
+     *
+     * @param Horde_Kolab_Filter_Configuration 
+     */
+    private $_config;
+
+    /**
+     * Constructor.
+     *
+     * @param Horde_Kolab_Filter_Configuration $config The configuration.
+     */
+    public function __construct(
+        Horde_Kolab_Filter_Configuration $config
+    ) {
+        $this->_config = $config;
+    }
+
+    
+    /**
+     * Creates a buffer for temporary storage of the message.
+     *
+     * @return NULL
+     */
+    public function init()
+    {
+        $conf = $this->_config->getConf();
+
+        if (isset($conf['kolab']['filter']['tempdir'])) {
+            $tmpdir = $conf['kolab']['filter']['tempdir'];
+        } else {
+            $tmpdir = Horde_Util::getTempDir();
+        }
+
+        $this->_tmpfile = @tempnam($tmpdir, 'IN.' . get_class($this) . '.');
+        $this->_tmpfh = @fopen($this->_tmpfile, 'w');
+        if (!$this->_tmpfh) {
+            throw new Horde_Kolab_Filter_Exception_IoError(
+                sprintf(
+                    "Error: Could not open %s for writing: %s",
+                    $this->_tmpfile,
+                    $php_errormsg
+                )
+            );
+        }
+
+        register_shutdown_function(array($this, 'cleanup'));
+    }
+
+    /**
+     * Return the file handle for writing data.
+     *
+     * @return resource The file handle.
+     */
+    public function getHandle()
+    {
+        return $this->_tmpfh;
+    }
+
+    /**
+     * Return the file handle for reading data.
+     *
+     * @return resource The file handle.
+     */
+    public function getReadHandle()
+    {
+        return @fopen($this->_tmpfile, 'r');;
+    }
+
+    /**
+     * A shutdown function for removing the temporary file.
+     *
+     * @return NULL
+     */
+    public function cleanup()
+    {
+        if (@file_exists($this->_tmpfile)) {
+            @unlink($this->_tmpfile);
+        }
+    }
+}
\ No newline at end of file
index 1d192a0..00fe5aa 100644 (file)
@@ -65,6 +65,7 @@ http://pear.php.net/dtd/package-2.0.xsd">
    <dir name="lib">
     <dir name="Horde">
      <dir name="Kolab">
+      <file name="Filter.php" role="php" />
       <dir name="Test">
        <file name="Filter.php" role="php" />
       </dir> <!-- /lib/Horde/Kolab/Test -->
@@ -78,15 +79,22 @@ http://pear.php.net/dtd/package-2.0.xsd">
        <dir name="Cli">
         <file name="Parser.php" role="php" />
        </dir> <!-- /lib/Horde/Kolab/Filter/Cli -->
+       <file name="Configuration.php" role="php" />
        <file name="Content.php" role="php" />
        <file name="Base.php" role="php" />
        <file name="Exception.php" role="php" />
        <dir name="Exception">
+        <file name="IoError.php" role="php" />
         <file name="Usage.php" role="php" />
        </dir> <!-- /lib/Horde/Kolab/Filter/Exception -->
+       <file name="Factory.php" role="php" />
        <file name="Incoming.php" role="php" />
        <file name="Outlook.php" role="php" />
        <file name="Response.php" role="php" />
+       <file name="Temporary.php" role="php" />
+       <dir name="Temporary">
+        <file name="File.php" role="php" />
+       </dir> <!-- /lib/Horde/Kolab/Filter/Temporary -->
        <file name="Transport.php" role="php" />
        <dir name="Transport">
         <file name="drop.php" role="php" />
@@ -253,15 +261,20 @@ http://pear.php.net/dtd/package-2.0.xsd">
    <install name="lib/Horde/Kolab/Resource/Freebusy/Kolab.php" as="Horde/Kolab/Resource/Freebusy/Kolab.php" />
    <install name="lib/Horde/Kolab/Resource/Freebusy/Mock.php" as="Horde/Kolab/Resource/Freebusy/Mock.php" />
    <install name="lib/Horde/Kolab/Test/Filter.php" as="Horde/Kolab/Test/Filter.php" />
+   <install name="lib/Horde/Kolab/Filter.php" as="Horde/Kolab/Filter.php" />
    <install name="lib/Horde/Kolab/Filter/Cli.php" as="Horde/Kolab/Filter/Cli.php" />
    <install name="lib/Horde/Kolab/Filter/Cli/Parser.php" as="Horde/Kolab/Filter/Cli/Parser.php" />
+   <install name="lib/Horde/Kolab/Filter/Configuration.php" as="Horde/Kolab/Filter/Configuration.php" />
    <install name="lib/Horde/Kolab/Filter/Content.php" as="Horde/Kolab/Filter/Content.php" />
    <install name="lib/Horde/Kolab/Filter/Base.php" as="Horde/Kolab/Filter/Base.php" />
    <install name="lib/Horde/Kolab/Filter/Exception.php" as="Horde/Kolab/Filter/Exception.php" />
    <install name="lib/Horde/Kolab/Filter/Exception/Usage.php" as="Horde/Kolab/Filter/Exception/Usage.php" />
+   <install name="lib/Horde/Kolab/Filter/Factory.php" as="Horde/Kolab/Filter/Factory.php" />
    <install name="lib/Horde/Kolab/Filter/Incoming.php" as="Horde/Kolab/Filter/Incoming.php" />
    <install name="lib/Horde/Kolab/Filter/Outlook.php" as="Horde/Kolab/Filter/Outlook.php" />
    <install name="lib/Horde/Kolab/Filter/Response.php" as="Horde/Kolab/Filter/Response.php" />
+   <install name="lib/Horde/Kolab/Filter/Temporary.php" as="Horde/Kolab/Filter/Temporary.php" />
+   <install name="lib/Horde/Kolab/Filter/Temporary/File.php" as="Horde/Kolab/Filter/Temporary/File.php" />
    <install name="lib/Horde/Kolab/Filter/Transport.php" as="Horde/Kolab/Filter/Transport.php" />
    <install name="lib/Horde/Kolab/Filter/Transport/DovecotLDA.php" as="Horde/Kolab/Filter/Transport/DovecotLDA.php" />
    <install name="lib/Horde/Kolab/Filter/Transport/drop.php" as="Horde/Kolab/Filter/Transport/drop.php" />
index 66b842c..0b4246d 100644 (file)
@@ -1,22 +1,22 @@
 <?php
 /**
- * All tests for the Kolab_Storage:: package.
+ * All tests for the Kolab_Filter:: package.
  *
  * PHP version 5
  *
  * @category   Kolab
- * @package    Kolab_Storage
+ * @package    Kolab_Filter
  * @subpackage UnitTests
  * @author     Gunnar Wrobel <wrobel@pardus.de>
  * @license    http://www.fsf.org/copyleft/lgpl.html LGPL
- * @link       http://pear.horde.org/index.php?package=Kolab_Storage
+ * @link       http://pear.horde.org/index.php?package=Kolab_Filter
  */
 
 /**
  * Define the main method
  */
 if (!defined('PHPUnit_MAIN_METHOD')) {
-    define('PHPUnit_MAIN_METHOD', 'Horde_Kolab_Storage_AllTests::main');
+    define('PHPUnit_MAIN_METHOD', 'Horde_Kolab_Filter_AllTests::main');
 }
 
 /**
@@ -25,10 +25,10 @@ if (!defined('PHPUnit_MAIN_METHOD')) {
 require_once 'Horde/Test/AllTests.php';
 
 /**
- * @package    Horde_Kolab_Storage
+ * @package    Horde_Kolab_Filter
  * @subpackage UnitTests
  */
-class Horde_Kolab_Storage_AllTests extends Horde_Test_AllTests
+class Horde_Kolab_Filter_AllTests extends Horde_Test_AllTests
 {
     /**
      * Main entry point for running the suite.
@@ -63,15 +63,15 @@ class Horde_Kolab_Storage_AllTests extends Horde_Test_AllTests
      */
     public static function detectTestFixture(PHPUnit_Framework_TestSuite $suite)
     {
-        $config = getenv('KOLAB_STORAGE_TEST_CONFIG');
+        $config = getenv('KOLAB_FILTER_TEST_CONFIG');
         if ($config === false) {
             $config = dirname(__FILE__) . '/conf.php';
         }
         if (file_exists($config)) {
             require $config;
-            if (isset($conf['kolab']['storage']['test'])) {
+            if (isset($conf['kolab']['filter']['test'])) {
                 $fixture = new stdClass;
-                $fixture->conf = $conf['kolab']['storage']['test'];
+                $fixture->conf = $conf['kolab']['filter']['test'];
                 $fixture->drivers = array();
                 $suite->setSharedFixture($fixture);
             }
@@ -80,8 +80,8 @@ class Horde_Kolab_Storage_AllTests extends Horde_Test_AllTests
     }
 }
 
-Horde_Kolab_Storage_AllTests::init('Horde_Kolab_Storage', __FILE__);
+Horde_Kolab_Filter_AllTests::init('Horde_Kolab_Filter', __FILE__);
 
-if (PHPUnit_MAIN_METHOD == 'Horde_Kolab_Storage_AllTests::main') {
-    Horde_Kolab_Storage_AllTests::main();
+if (PHPUnit_MAIN_METHOD == 'Horde_Kolab_Filter_AllTests::main') {
+    Horde_Kolab_Filter_AllTests::main();
 }
index d92650c..fe49a4f 100644 (file)
@@ -36,3 +36,6 @@ error_reporting(E_ALL | E_STRICT);
 
 /** Load the basic test definition */
 require_once dirname(__FILE__) . '/StoryTestCase.php';
+
+/** Load the test helpers */
+require_once dirname(__FILE__) . '/Helper/AddressFilter.php';
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/ContentTest.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/ContentTest.php
deleted file mode 100644 (file)
index 1b1b076..0000000
+++ /dev/null
@@ -1,199 +0,0 @@
-<?php
-/**
- * Test the content filter class within the Kolab filter implementation.
- *
- * @package Horde_Kolab_Filter
- */
-
-/**
- *  We need the unit test framework
- */
-require_once 'Horde/Kolab/Test/Filter.php';
-
-require_once 'Horde.php';
-require_once 'Horde/Kolab/Filter/Content.php';
-
-/**
- * Test the content filter.
- *
- * Copyright 2008 Klarälvdalens Datakonsult AB
- *
- * See the enclosed file COPYING for license information (LGPL). If you
- * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
- *
- * @author  Gunnar Wrobel <wrobel@pardus.de>
- * @package Horde_Kolab_Filter
- */
-class Horde_Kolab_Filter_ContentTest extends Horde_Kolab_Test_Filter
-{
-
-    /**
-     * Set up testing.
-     */
-    protected function setUp()
-    {
-        $result = $this->prepareBasicSetup();
-
-        $this->server  = &$result['server'];
-        $this->storage = &$result['storage'];
-        $this->auth    = &$result['auth'];
-
-        global $conf;
-
-        $conf['kolab']['imap']['server'] = 'localhost';
-        $conf['kolab']['imap']['port']   = 0;
-        $conf['kolab']['imap']['allow_special_users'] = true;
-        $conf['kolab']['filter']['reject_forged_from_header'] = false;
-        $conf['kolab']['filter']['email_domain'] = 'example.org';
-        $conf['kolab']['filter']['privileged_networks'] = '127.0.0.1,192.168.0.0/16';
-        $conf['kolab']['filter']['verify_from_header'] = true;
-        $conf['kolab']['filter']['calendar_id'] = 'calendar';
-        $conf['kolab']['filter']['calendar_pass'] = 'calendar';
-        $conf['kolab']['filter']['lmtp_host'] = 'imap.example.org';
-        $conf['kolab']['filter']['simple_locks'] = true;
-        $conf['kolab']['filter']['simple_locks_timeout'] = 3;
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getNewFolder();
-        $folder->setName('Kalender');
-        $result = $folder->save(array('type' => 'event',
-                                      'default' => true));
-        $this->assertNoError($result);
-    }
-
-    /**
-     * Test sending messages through the content filter.
-     *
-     * @dataProvider addressCombinations
-     */
-    public function testContentHandler($infile, $outfile, $user, $client, $from,
-                                       $to, $host, $params = array())
-    {
-        $this->sendFixture($infile, $outfile, $user, $client, $from, $to,
-                           $host, $params);
-    }
-
-    /**
-     * Provides various test situations for the Kolab content filter.
-     */
-    public function addressCombinations()
-    {
-        return array(
-            /**
-             * Test a simple message
-             */
-            array(dirname(__FILE__) . '/fixtures/vacation.eml',
-                  dirname(__FILE__) . '/fixtures/vacation.ret',
-                  '', '', 'me@example.org', 'you@example.net', 'example.org',
-                  array('unmodified_content' => true)),
-            /**
-             * Test a simple message
-             */
-            array(dirname(__FILE__) . '/fixtures/tiny.eml',
-                  dirname(__FILE__) . '/fixtures/tiny.ret',
-                  '', '', 'me@example.org', 'you@example.org', 'example.org',
-                  array('unmodified_content' => true)),
-            /**
-             * Test a simple message
-             */
-            array(dirname(__FILE__) . '/fixtures/simple.eml',
-                  dirname(__FILE__) . '/fixtures/simple_out.ret',
-                  '', '', 'me@example.org', 'you@example.org', 'example.org',
-                  array('unmodified_content' => true)),
-            /**
-             * Test sending from a remote server without authenticating. This
-             * will be considered forging the sender.
-             */
- /*           array(dirname(__FILE__) . '/fixtures/forged.eml',
-                  dirname(__FILE__) . '/fixtures/forged.ret',
-                  '', '10.0.0.1', 'me@example.org', 'you@example.org', 'example.org',
-                  array('unmodified_content' => true)),*/
-            /**
-             * Test sending from a remote server without authenticating but
-             * within the priviledged network. This will not be considered
-             * forging the sender.
-             */
-            array(dirname(__FILE__) . '/fixtures/forged.eml',
-                  dirname(__FILE__) . '/fixtures/privileged.ret',
-                  '', '192.168.178.1', 'me@example.org', 'you@example.org', 'example.org',
-                  array('unmodified_content' => true)),
-            /**
-             * Test authenticated sending of a message from a remote client.
-             */
-            array(dirname(__FILE__) . '/fixtures/validation.eml',
-                  dirname(__FILE__) . '/fixtures/validation.ret',
-                  'me@example.org', 'remote.example.org', 'me@example.org', 'you@example.org', 'example.org'),
-            /**
-             * Test authenticated sending of a message from a remote client
-             * using an alias.
-             */
-            array(dirname(__FILE__) . '/fixtures/validation.eml',
-                  dirname(__FILE__) . '/fixtures/validation.ret',
-                  'me@example.org', 'remote.example.org', 'me.me@example.org', 'you@example.org', 'example.org'),
-            /**
-             * Test authenticated sending of a message from a remote client
-             * using an alias with capitals (MEME@example.org).
-             */
-            array(dirname(__FILE__) . '/fixtures/validation.eml',
-                  dirname(__FILE__) . '/fixtures/validation.ret',
-                  'me@example.org', 'remote.example.org', 'meme@example.org', 'you@example.org', 'example.org'),
-            /**
-             * Test authenticated sending of a message from a remote client
-             * as delegate
-             */
-            array(dirname(__FILE__) . '/fixtures/validation.eml',
-                  dirname(__FILE__) . '/fixtures/validation.ret',
-                  'me@example.org', 'remote.example.org', 'else@example.org', 'you@example.org', 'example.org'),
-            /**
-             * Test authenticated sending of a message from a remote client
-             * with an address that is not allowed.
-             */
-            array(dirname(__FILE__) . '/fixtures/validation.eml',
-                  dirname(__FILE__) . '/fixtures/validation.ret',
-                  'me@example.org', 'remote.example.org', 'else3@example.org', 'you@example.org', 'example.org',
-                  array('error' =>'Invalid From: header. else3@example.org looks like a forged sender')),
-            /**
-             * Test forwarding an invitation
-             */
-            array(dirname(__FILE__) . '/fixtures/invitation_forward.eml',
-                  dirname(__FILE__) . '/fixtures/invitation_forward.ret',
-                  'me@example.org', '10.0.2.1', 'me@example.org', 'you@example.org', 'example.org'),
-        );
-    }
-
-    /**
-     * Test rejecting a forged from header.
-     */
-    public function testRejectingForgedFromHeader()
-    {
-        global $conf;
-
-        $conf['kolab']['filter']['reject_forged_from_header'] = true;
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/forged.eml',
-                           dirname(__FILE__) . '/fixtures/forged.ret',
-                           '', '10.0.0.1', 'me@example.org', 'you@example.org', 'example.org',
-                           array('error' =>'Invalid From: header. me@example.org looks like a forged sender',
-                                 'unmodified_content' => true));
-    }
-
-    /**
-     * Test translated forged from headers.
-     */
-    public function testTranslatedForgedFromHeader()
-    {
-        $this->markTestIncomplete('Some the translation does not kick in.');
-        global $conf;
-
-        $conf['kolab']['filter']['locale_path'] = dirname(__FILE__) . '/../../../../../data/Kolab_Filter/locale';
-        $conf['kolab']['filter']['locale'] = 'de_DE';
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/forged.eml',
-                           dirname(__FILE__) . '/fixtures/forged_trans.ret',
-                           '', '10.0.0.1', 'me@example.org', 'you@example.org', 'example.org',
-                           array('unmodified_content' => true));
-    }
-
-}
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/ContentTestOld.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/ContentTestOld.php
new file mode 100644 (file)
index 0000000..1b1b076
--- /dev/null
@@ -0,0 +1,199 @@
+<?php
+/**
+ * Test the content filter class within the Kolab filter implementation.
+ *
+ * @package Horde_Kolab_Filter
+ */
+
+/**
+ *  We need the unit test framework
+ */
+require_once 'Horde/Kolab/Test/Filter.php';
+
+require_once 'Horde.php';
+require_once 'Horde/Kolab/Filter/Content.php';
+
+/**
+ * Test the content filter.
+ *
+ * Copyright 2008 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you
+ * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @author  Gunnar Wrobel <wrobel@pardus.de>
+ * @package Horde_Kolab_Filter
+ */
+class Horde_Kolab_Filter_ContentTest extends Horde_Kolab_Test_Filter
+{
+
+    /**
+     * Set up testing.
+     */
+    protected function setUp()
+    {
+        $result = $this->prepareBasicSetup();
+
+        $this->server  = &$result['server'];
+        $this->storage = &$result['storage'];
+        $this->auth    = &$result['auth'];
+
+        global $conf;
+
+        $conf['kolab']['imap']['server'] = 'localhost';
+        $conf['kolab']['imap']['port']   = 0;
+        $conf['kolab']['imap']['allow_special_users'] = true;
+        $conf['kolab']['filter']['reject_forged_from_header'] = false;
+        $conf['kolab']['filter']['email_domain'] = 'example.org';
+        $conf['kolab']['filter']['privileged_networks'] = '127.0.0.1,192.168.0.0/16';
+        $conf['kolab']['filter']['verify_from_header'] = true;
+        $conf['kolab']['filter']['calendar_id'] = 'calendar';
+        $conf['kolab']['filter']['calendar_pass'] = 'calendar';
+        $conf['kolab']['filter']['lmtp_host'] = 'imap.example.org';
+        $conf['kolab']['filter']['simple_locks'] = true;
+        $conf['kolab']['filter']['simple_locks_timeout'] = 3;
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getNewFolder();
+        $folder->setName('Kalender');
+        $result = $folder->save(array('type' => 'event',
+                                      'default' => true));
+        $this->assertNoError($result);
+    }
+
+    /**
+     * Test sending messages through the content filter.
+     *
+     * @dataProvider addressCombinations
+     */
+    public function testContentHandler($infile, $outfile, $user, $client, $from,
+                                       $to, $host, $params = array())
+    {
+        $this->sendFixture($infile, $outfile, $user, $client, $from, $to,
+                           $host, $params);
+    }
+
+    /**
+     * Provides various test situations for the Kolab content filter.
+     */
+    public function addressCombinations()
+    {
+        return array(
+            /**
+             * Test a simple message
+             */
+            array(dirname(__FILE__) . '/fixtures/vacation.eml',
+                  dirname(__FILE__) . '/fixtures/vacation.ret',
+                  '', '', 'me@example.org', 'you@example.net', 'example.org',
+                  array('unmodified_content' => true)),
+            /**
+             * Test a simple message
+             */
+            array(dirname(__FILE__) . '/fixtures/tiny.eml',
+                  dirname(__FILE__) . '/fixtures/tiny.ret',
+                  '', '', 'me@example.org', 'you@example.org', 'example.org',
+                  array('unmodified_content' => true)),
+            /**
+             * Test a simple message
+             */
+            array(dirname(__FILE__) . '/fixtures/simple.eml',
+                  dirname(__FILE__) . '/fixtures/simple_out.ret',
+                  '', '', 'me@example.org', 'you@example.org', 'example.org',
+                  array('unmodified_content' => true)),
+            /**
+             * Test sending from a remote server without authenticating. This
+             * will be considered forging the sender.
+             */
+ /*           array(dirname(__FILE__) . '/fixtures/forged.eml',
+                  dirname(__FILE__) . '/fixtures/forged.ret',
+                  '', '10.0.0.1', 'me@example.org', 'you@example.org', 'example.org',
+                  array('unmodified_content' => true)),*/
+            /**
+             * Test sending from a remote server without authenticating but
+             * within the priviledged network. This will not be considered
+             * forging the sender.
+             */
+            array(dirname(__FILE__) . '/fixtures/forged.eml',
+                  dirname(__FILE__) . '/fixtures/privileged.ret',
+                  '', '192.168.178.1', 'me@example.org', 'you@example.org', 'example.org',
+                  array('unmodified_content' => true)),
+            /**
+             * Test authenticated sending of a message from a remote client.
+             */
+            array(dirname(__FILE__) . '/fixtures/validation.eml',
+                  dirname(__FILE__) . '/fixtures/validation.ret',
+                  'me@example.org', 'remote.example.org', 'me@example.org', 'you@example.org', 'example.org'),
+            /**
+             * Test authenticated sending of a message from a remote client
+             * using an alias.
+             */
+            array(dirname(__FILE__) . '/fixtures/validation.eml',
+                  dirname(__FILE__) . '/fixtures/validation.ret',
+                  'me@example.org', 'remote.example.org', 'me.me@example.org', 'you@example.org', 'example.org'),
+            /**
+             * Test authenticated sending of a message from a remote client
+             * using an alias with capitals (MEME@example.org).
+             */
+            array(dirname(__FILE__) . '/fixtures/validation.eml',
+                  dirname(__FILE__) . '/fixtures/validation.ret',
+                  'me@example.org', 'remote.example.org', 'meme@example.org', 'you@example.org', 'example.org'),
+            /**
+             * Test authenticated sending of a message from a remote client
+             * as delegate
+             */
+            array(dirname(__FILE__) . '/fixtures/validation.eml',
+                  dirname(__FILE__) . '/fixtures/validation.ret',
+                  'me@example.org', 'remote.example.org', 'else@example.org', 'you@example.org', 'example.org'),
+            /**
+             * Test authenticated sending of a message from a remote client
+             * with an address that is not allowed.
+             */
+            array(dirname(__FILE__) . '/fixtures/validation.eml',
+                  dirname(__FILE__) . '/fixtures/validation.ret',
+                  'me@example.org', 'remote.example.org', 'else3@example.org', 'you@example.org', 'example.org',
+                  array('error' =>'Invalid From: header. else3@example.org looks like a forged sender')),
+            /**
+             * Test forwarding an invitation
+             */
+            array(dirname(__FILE__) . '/fixtures/invitation_forward.eml',
+                  dirname(__FILE__) . '/fixtures/invitation_forward.ret',
+                  'me@example.org', '10.0.2.1', 'me@example.org', 'you@example.org', 'example.org'),
+        );
+    }
+
+    /**
+     * Test rejecting a forged from header.
+     */
+    public function testRejectingForgedFromHeader()
+    {
+        global $conf;
+
+        $conf['kolab']['filter']['reject_forged_from_header'] = true;
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/forged.eml',
+                           dirname(__FILE__) . '/fixtures/forged.ret',
+                           '', '10.0.0.1', 'me@example.org', 'you@example.org', 'example.org',
+                           array('error' =>'Invalid From: header. me@example.org looks like a forged sender',
+                                 'unmodified_content' => true));
+    }
+
+    /**
+     * Test translated forged from headers.
+     */
+    public function testTranslatedForgedFromHeader()
+    {
+        $this->markTestIncomplete('Some the translation does not kick in.');
+        global $conf;
+
+        $conf['kolab']['filter']['locale_path'] = dirname(__FILE__) . '/../../../../../data/Kolab_Filter/locale';
+        $conf['kolab']['filter']['locale'] = 'de_DE';
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/forged.eml',
+                           dirname(__FILE__) . '/fixtures/forged_trans.ret',
+                           '', '10.0.0.1', 'me@example.org', 'you@example.org', 'example.org',
+                           array('unmodified_content' => true));
+    }
+
+}
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/Helper/AddressFilter.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/Helper/AddressFilter.php
new file mode 100644 (file)
index 0000000..1a94330
--- /dev/null
@@ -0,0 +1,79 @@
+<?php
+/**
+ * Rewrites address information in a mail template.
+ *
+ * PHP version 5
+ *
+ * @category   Kolab
+ * @package    Kolab_Filter
+ * @subpackage UnitTests
+ * @author     Gunnar Wrobel <wrobel@pardus.de>
+ * @license    http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link       http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/**
+ * Rewrites address information in a mail template.
+ *
+ * Copyright 2010 The Horde Project (http://www.horde.org/)
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you
+ * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @category   Kolab
+ * @package    Kolab_Filter
+ * @subpackage UnitTests
+ * @author     Gunnar Wrobel <wrobel@pardus.de>
+ * @license    http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link       http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+class Horde_Kolab_Filter_Helper_AddressFilter
+extends php_user_filter
+{
+    public $_previous = '';
+
+    public $_sender;
+
+    public $_recipient;
+
+    public function onCreate()
+    {
+        $this->_sender = isset($this->params['sender']) ? $this->params['sender'] : '';
+        $this->_recipient = isset($this->params['recipient']) ? $this->params['recipient'] : '';
+        $this->_previous = '';
+    }
+
+    public function filter($in, $out, &$consumed, $closing)
+    {
+        while ($bucket = stream_bucket_make_writeable($in)) {
+            if (!empty($this->_previous)) {
+                $bucket->data = $this->_previous . $bucket->data;
+                $this->_previous = '';
+            }
+            if (!feof($this->stream) && preg_match('/(%[12]\$|%[12]|%)$/', $bucket->data)) {
+                $this->_previous .= $bucket->data;
+                return PSFS_FEED_ME;
+            }
+            $consumed += $bucket->datalen;
+            if (preg_match('/%([12])\$s/', $bucket->data, $matches)) {
+                if ($matches[1] == '1') {
+                    $bucket->data = preg_replace('/%1\$s/', $this->_sender, $bucket->data);
+                } else {
+                    $bucket->data = preg_replace('/%2\$s/', $this->_recipient, $bucket->data);
+                }
+            }
+            $bucket->datalen = strlen($bucket->data);
+            stream_bucket_append($out, $bucket);
+        }
+        if (!empty($this->_previous)) {
+            if ($closing) {
+                $bucket = stream_bucket_new($this->stream, $this->_previous);
+                $bucket->data = $this->_previous;
+                $consumed += strlen($this->_previous);
+                $this->_previous = '';
+                stream_bucket_append($out, $bucket);
+            }
+        }
+        return PSFS_PASS_ON;
+    }
+}
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/IncomingTest.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/IncomingTest.php
deleted file mode 100644 (file)
index 15c5034..0000000
+++ /dev/null
@@ -1,85 +0,0 @@
-<?php
-/**
- * Test the incoming filter class within the Kolab filter implementation.
- *
- * @package Horde_Kolab_Filter
- */
-
-/**
- *  We need the base class
- */
-require_once 'Horde/Kolab/Test/Filter.php';
-
-/**
- *  We need the unit test framework
- */
-require_once 'PHPUnit/Extensions/OutputTestCase.php';
-
-require_once 'Horde.php';
-require_once 'Horde/Kolab/Filter/Incoming.php';
-
-/**
- * Test the incoming filter.
- *
- * Copyright 2008 Klarälvdalens Datakonsult AB
- *
- * See the enclosed file COPYING for license information (LGPL). If you
- * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
- *
- * @author  Gunnar Wrobel <wrobel@pardus.de>
- * @package Horde_Kolab_Filter
- */
-class Horde_Kolab_Filter_IncomingTest extends Horde_Kolab_Test_Filter
-{
-
-    /**
-     * Set up testing.
-     */
-    protected function setUp()
-    {
-        global $conf;
-
-        $conf = array();
-
-        $test = new Horde_Kolab_Test_Filter();
-        $test->prepareBasicSetup();
-
-        $conf['log']['enabled']          = false;
-
-        $conf['kolab']['filter']['debug'] = true;
-
-        $conf['kolab']['imap']['server'] = 'localhost';
-        $conf['kolab']['imap']['port']   = 0;
-
-        $_SERVER['SERVER_NAME'] = 'localhost';
-    }
-
-
-    /**
-     * Test receiving the simple.eml message.
-     */
-    public function testSimpleIn()
-    {
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/simple.eml',
-                           dirname(__FILE__) . '/fixtures/simple2.ret',
-                           '', '', 'wrobel@example.org', 'me@example.org',
-                           'home.example.org', $params);
-    }
-
-    /**
-     * Test handling the line end with incoming messages.
-     */
-    public function testIncomingLineEnd()
-    {
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/empty.eml',
-                           dirname(__FILE__) . '/fixtures/empty2.ret',
-                           '', '127.0.0.1', 'wrobel@example.org', 'me@example.org',
-                           'home.example.org', $params);
-    }
-}
index 72abeb6..7b24692 100644 (file)
@@ -32,37 +32,19 @@ require_once dirname(__FILE__) . '/../Autoload.php';
  * @license    http://www.fsf.org/copyleft/lgpl.html LGPL
  * @link       http://pear.horde.org/index.php?package=Kolab_Filter
  */
-class Horde_Kolab_Filter_Integration_CliTest extends PHPUnit_Framework_TestCase
+class Horde_Kolab_Filter_Integration_CliTest
+extends PHPUnit_Framework_TestCase
 {
-
-    /**
-     * Set up testing.
-     */
-    protected function setUp()
-    {
-        $GLOBALS['conf']['log']['enabled']          = false;
-
-        $_SERVER['SERVER_NAME'] = 'localhost';
-        $_SERVER['REMOTE_ADDR'] = 'ADDR';
-        $_SERVER['REMOTE_HOST'] = 'HOST';
-    }
-
-
     /**
      * Test incorrect usage of the Filter.
      */
     public function testIncorrectUsage()
     {
         $_SERVER['argv'] = array($_SERVER['argv'][0]);
-        $parser   = new Horde_Kolab_Filter_Incoming(
-            new Horde_Kolab_Filter_Cli(),
-            new Horde_Log_Logger(
-                new Horde_Log_Handler_Mock()
-            )
-        );
+        $filter = new Horde_Kolab_Filter();
         $inh = fopen(dirname(__FILE__) . '/../fixtures/tiny.eml', 'r');
         try {
-            $result = $parser->parse($inh, 'echo');
+            $result = $filter->main('Incoming', $inh, 'echo');
         } catch (Horde_Kolab_Filter_Exception $e) {
             $this->assertContains(
                 'Please provide one or more recipients.',
@@ -82,15 +64,10 @@ class Horde_Kolab_Filter_Integration_CliTest extends PHPUnit_Framework_TestCase
             $_SERVER['argv'][0],
             '--recipient'
         );
-        $parser   = new Horde_Kolab_Filter_Incoming(
-            new Horde_Kolab_Filter_Cli(),
-            new Horde_Log_Logger(
-                new Horde_Log_Handler_Mock()
-            )
-        );
+        $filter = new Horde_Kolab_Filter();
         $inh = fopen(dirname(__FILE__) . '/../fixtures/tiny.eml', 'r');
         try {
-            $result = $parser->parse($inh, 'echo');
+            $result = $filter->main('Incoming', $inh, 'echo');
         } catch (Horde_Kolab_Filter_Exception $e) {
             $this->assertContains(
                 'error: --recipient option requires an argument',
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/Integration/IncomingTest.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/Integration/IncomingTest.php
new file mode 100644 (file)
index 0000000..4a92e7f
--- /dev/null
@@ -0,0 +1,65 @@
+<?php
+/**
+ * Test the incoming filter.
+ *
+ * PHP version 5
+ *
+ * @category   Kolab
+ * @package    Kolab_Filter
+ * @subpackage UnitTests
+ * @author     Gunnar Wrobel <wrobel@pardus.de>
+ * @license    http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link       http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/**
+ * Prepare the test setup.
+ */
+require_once dirname(__FILE__) . '/../Autoload.php';
+
+/**
+ * Test the incoming filter.
+ *
+ * Copyright 2008-2010 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you
+ * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @category   Kolab
+ * @package    Kolab_Filter
+ * @subpackage UnitTests
+ * @author     Gunnar Wrobel <wrobel@pardus.de>
+ * @license    http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link       http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+class Horde_Kolab_Filter_Integration_IncomingTest
+extends Horde_Kolab_Filter_StoryTestCase
+{
+    /**
+     * Test receiving the simple.eml message.
+     */
+    public function testSimpleIn()
+    {
+        $this->given('an incoming message on host', 'home.example.org')
+            ->and('the SMTP sender address is', 'wrobel@example.org')
+            ->and('the SMTP recipient address is', 'me@example.org')
+            ->and('the unmodified message content is', dirname(__FILE__) . '/../fixtures/simple.eml')
+            ->when('handling the message')
+            ->then('the result will be the same as the content in', dirname(__FILE__) . '/../fixtures/simple2.ret');
+    }
+
+    /**
+     * Test handling the line end with incoming messages.
+     */
+    public function testIncomingLineEnd()
+    {
+        $this->given('an incoming message on host', 'home.example.org')
+            ->and('the SMTP sender address is', 'wrobel@example.org')
+            ->and('the SMTP recipient address is', 'me@example.org')
+            ->and('the client address is', '127.0.0.1')
+            ->and('the hostname is', 'home.example.com')
+            ->and('the unmodified message content is', dirname(__FILE__) . '/../fixtures/empty.eml')
+            ->when('handling the message')
+            ->then('the result will be the same as the content in', dirname(__FILE__) . '/../fixtures/empty2.ret');
+    }
+}
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/LoadTest.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/LoadTest.php
deleted file mode 100644 (file)
index d4faa30..0000000
+++ /dev/null
@@ -1,117 +0,0 @@
-<?php
-/**
- * Test the incoming filter class for its load behaviour..
- *
- * @package Horde_Kolab_Filter
- */
-
-/**
- *  We need the unit test framework
- */
-require_once 'PHPUnit/Framework.php';
-require_once 'PHPUnit/Extensions/PerformanceTestCase.php';
-
-require_once 'Horde.php';
-require_once 'Horde/Kolab/Filter/Incoming.php';
-
-/**
- * Test the incoming filter load.
- *
- * Copyright 2008 Klarälvdalens Datakonsult AB
- *
- * See the enclosed file COPYING for license information (LGPL). If you
- * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
- *
- * @author  Gunnar Wrobel <wrobel@pardus.de>
- * @package Horde_Kolab_Filter
- */
-class Horde_Kolab_Filter_LoadTest extends PHPUnit_Extensions_PerformanceTestCase
-{
-
-    /**
-     * Set up testing.
-     */
-    protected function setUp()
-    {
-        global $conf;
-
-        $conf = array();
-        $conf['log']['enabled']          = false;
-
-        $conf['kolab']['filter']['debug'] = true;
-
-        $conf['kolab']['server'] = array(
-            'driver' => 'test',
-            'params' => array(
-                'data' => array(
-                    'cn=me' => array(
-                        'dn' => 'cn=me',
-                        'data' => array(
-                            'objectClass' => array('kolabInetOrgPerson'),
-                            'mail' => array('me@example.com'),
-                            'kolabImapHost' => array('localhost'),
-                            'uid' => array('me'),
-                        )
-                    ),
-                    'cn=you' => array(
-                        'dn' => 'cn=you',
-                        'data' => array(
-                            'objectClass' => array('kolabInetOrgPerson'),
-                            'mail' => array('you@example.com'),
-                            'kolabImapHost' => array('localhost'),
-                            'uid' => array('you'),
-                        )
-                    ),
-                ),
-            )
-        );
-        $conf['kolab']['imap']['server'] = 'localhost';
-        $conf['kolab']['imap']['port']   = 0;
-        $conf['kolab']['imap']['allow_special_users'] = true;
-
-        $_SERVER['SERVER_NAME'] = 'localhost';
-   }
-
-
-    /**
-     * Test the time the script takes in handling some messages.
-     */
-    public function testLoad()
-    {
-        $this->setMaxRunningTime(3);
-
-        $tmpdir = Horde::getTempDir();
-        $tmpfile = @tempnam($tmpdir, 'BIG.eml.');
-        $tmpfh = @fopen($tmpfile, "w");
-        $head = file_get_contents(dirname(__FILE__) . '/fixtures/tiny.eml');
-        $body = '';
-        for ($i = 0; $i < 50000;$i++) {
-            $body .= md5(microtime());
-            if (($i % 2) == 0) {
-                $body .= "\n";
-            }
-        }
-        @fwrite($tmpfh, $head);
-        @fwrite($tmpfh, $body);
-        @fclose($tmpfh);
-
-        $_SERVER['argv'] = array($_SERVER['argv'][0], '--sender=me@example.com', '--recipient=you@example.com', '--user=', '--host=example.com');
-
-        for ($i = 0; $i < 10; $i++) {
-
-            $parser = &new Horde_Kolab_Filter_Incoming();
-            $inh = fopen(dirname(__FILE__) . '/fixtures/tiny.eml', 'r');
-            $parser->parse($inh, 'drop');
-
-            $parser = &new Horde_Kolab_Filter_Incoming();
-            $inh = fopen(dirname(__FILE__) . '/fixtures/simple.eml', 'r');
-            $parser->parse($inh, 'drop');
-
-            $parser = &new Horde_Kolab_Filter_Incoming();
-            $inh = fopen($tmpfile, 'r');
-            $parser->parse($inh, 'drop');
-
-        }
-       unlink($tmpfile);
-    }
-}
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/ResourceTest.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/ResourceTest.php
deleted file mode 100644 (file)
index 69d1274..0000000
+++ /dev/null
@@ -1,371 +0,0 @@
-<?php
-/**
- * Test resource handling within the Kolab filter implementation.
- *
- * @package Horde_Kolab_Filter
- */
-
-/**
- *  We need the base class
- */
-require_once 'Horde/Kolab/Test/Filter.php';
-
-require_once 'Horde.php';
-require_once 'Horde/Kolab/Resource.php';
-require_once 'Horde/Kolab/Filter/Incoming.php';
-require_once 'Horde/Icalendar.php';
-require_once 'Horde/Icalendar/Vfreebusy.php';
-
-/**
- * Test resource handling
- *
- * Copyright 2008 Klarälvdalens Datakonsult AB
- *
- * See the enclosed file COPYING for license information (LGPL). If you
- * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
- *
- * @author  Gunnar Wrobel <wrobel@pardus.de>
- * @package Horde_Kolab_Filter
- */
-class Horde_Kolab_Filter_ResourceTest extends Horde_Kolab_Test_Filter
-{
-
-    /**
-     * Set up testing.
-     */
-    protected function setUp()
-    {
-        $result = $this->prepareBasicSetup();
-
-        $this->server  = &$result['server'];
-        $this->storage = &$result['storage'];
-        $this->auth    = &$result['auth'];
-
-        global $conf;
-
-        $conf['kolab']['imap']['server'] = 'localhost';
-        $conf['kolab']['imap']['port']   = 0;
-        $conf['kolab']['imap']['allow_special_users'] = true;
-        $conf['kolab']['filter']['reject_forged_from_header'] = false;
-        $conf['kolab']['filter']['email_domain'] = 'example.org';
-        $conf['kolab']['filter']['privileged_networks'] = '127.0.0.1,192.168.0.0/16';
-        $conf['kolab']['filter']['verify_from_header'] = true;
-        $conf['kolab']['filter']['calendar_id'] = 'calendar';
-        $conf['kolab']['filter']['calendar_pass'] = 'calendar';
-        $conf['kolab']['filter']['lmtp_host'] = 'imap.example.org';
-        $conf['kolab']['filter']['simple_locks'] = true;
-        $conf['kolab']['filter']['simple_locks_timeout'] = 3;
-
-        $conf['kolab']['filter']['itipreply']['driver'] = 'echo';
-        $conf['kolab']['filter']['itipreply']['params']['host'] = 'localhsot';
-        $conf['kolab']['filter']['itipreply']['params']['port'] = 25;
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getNewFolder();
-        $folder->setName('Kalender');
-        $result = $folder->save(array('type' => 'event',
-                                      'default' => true));
-        $this->assertNoError($result);
-    }
-
-    /**
-     * Test retrieval of the resource information
-     */
-    public function testGetResourceData()
-    {
-        $r = &new Kolab_Resource();
-        $d = $r->_getResourceData('test@example.org', 'wrobel@example.org');
-        $this->assertNoError($d);
-        $this->assertEquals('wrobel@example.org', $d['id']);
-        $this->assertEquals('home.example.org', $d['homeserver']);
-        $this->assertEquals('ACT_REJECT_IF_CONFLICTS', $d['action']);
-        $this->assertEquals('cn=Gunnar Wrobel', $d['cn']);
-    }
-
-    /**
-     * Test manual actions
-     */
-    public function testManual()
-    {
-        $r = &new Kolab_Resource();
-        $this->assertTrue($r->handleMessage('otherhost', 'test@example.org', 'wrobel@example.org', null));
-        $r = &new Kolab_Resource();
-        $this->assertTrue($r->handleMessage('localhost', 'test@example.org', 'wrobel@example.org', null));
-    }
-
-
-    /**
-     * Test invitation.
-     */
-    public function testRecurrenceInvitation()
-    {
-        $this->markTestIncomplete('Fails for unknown reason.');
-
-        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20080926T000000Z'));
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20081126T000000Z'));
-
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/recur_invitation.eml',
-                           dirname(__FILE__) . '/fixtures/recur_invitation.ret2',
-                           '', '', 'test@example.org', 'wrobel@example.org',
-                           'home.example.org', $params);
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getFolder('INBOX/Kalender');
-        $data = $folder->getData();
-        $events = $data->getObjects();
-        $this->assertEquals(1222419600, $events[0]['start-date']);
-
-        $result = $data->deleteAll();
-        $this->assertNoError($result);
-    }
-
-    /**
-     * Test an that contains a long string.
-     */
-    public function testLongStringInvitation()
-    {
-        $this->markTestIncomplete('Fails for unknown reason.');
-
-        require_once 'Horde/Icalendar/Vfreebusy.php';
-        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20080926T000000Z'));
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20081126T000000Z'));
-
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/longstring_invitation.eml',
-                           dirname(__FILE__) . '/fixtures/longstring_invitation.ret',
-                           '', '', 'test@example.org', 'wrobel@example.org',
-                           'home.example.org', $params);
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getFolder('INBOX/Kalender');
-        $data = $folder->getData();
-        $events = $data->getObjects();
-        $summaries = array();
-        foreach ($events as $event) {
-            $summaries[] = $event['summary'];
-        }
-        $this->assertContains('invitationtest2', $summaries);
-
-        $result = $data->deleteAll();
-        $this->assertNoError($result);
-    }
-
-    /**
-     * Test an invitation that books a whole day.
-     */
-    public function testWholeDayInvitation()
-    {
-        require_once 'Horde/Icalendar/Vfreebusy.php';
-        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20090401T000000Z'));
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20090601T000000Z'));
-
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/invitation_whole_day.eml',
-                           dirname(__FILE__) . '/fixtures/invitation_whole_day.ret',
-                           '', '', 'test@example.org', 'wrobel@example.org',
-                           'home.example.org', $params);
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getFolder('INBOX/Kalender');
-        $data = $folder->getData();
-        $events = $data->getObjects();
-        $summaries = array();
-        foreach ($events as $event) {
-            $summaries[] = $event['summary'];
-        }
-        $this->assertContains('issue3558', $summaries);
-
-        $result = $data->deleteAll();
-        $this->assertNoError($result);
-    }
-
-    /**
-     * Test an invitation with plus addressing.
-     */
-    public function testInvitationWithPlusAddressing()
-    {
-        require_once 'Horde/Icalendar/Vfreebusy.php';
-        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20090401T000000Z'));
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20090601T000000Z'));
-
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/invitation_plus_addressing.eml',
-                           dirname(__FILE__) . '/fixtures/invitation_plus_addressing.ret',
-                           '', '', 'test@example.org', 'wrobel+laptop@example.org',
-                           'home.example.org', $params);
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getFolder('INBOX/Kalender');
-        $data = $folder->getData();
-        $events = $data->getObjects();
-        $summaries = array();
-        foreach ($events as $event) {
-            $summaries[] = $event['summary'];
-        }
-        $this->assertContains('issue3521', $summaries);
-
-        $result = $data->deleteAll();
-        $this->assertNoError($result);
-    }
-
-    /**
-     * Test invitation when no default has been given.
-     */
-    public function testRecurrenceNodefault()
-    {
-        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20080926T000000Z'));
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20081126T000000Z'));
-
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/recur_invitation.eml',
-                           dirname(__FILE__) . '/fixtures/recur_invitation.ret',
-                           '', '', 'wrobel@example.org', 'else@example.org', 
-                           'home.example.org', $params);
-    }
-
-    /**
-     * Test an issue with recurring invitations.
-     *
-     * https://issues.kolab.org/issue3868
-     */
-    public function testIssue3868()
-    {
-        $this->markTestIncomplete('Fails for unknown reason.');
-
-        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20090901T000000Z'));
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20091101T000000Z'));
-
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/recur_invitation2.eml',
-                           dirname(__FILE__) . '/fixtures/null.ret',
-                           '', '', 'test@example.org', 'wrobel@example.org',
-                           'home.example.org', $params);
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getFolder('INBOX/Kalender');
-        $data = $folder->getData();
-        $events = $data->getObjects();
-        $this->assertEquals(1251950400, $events[0]['start-date']);
-
-        $result = $data->deleteAll();
-        $this->assertNoError($result);
-    }
-
-    /**
-     * Test all day events
-     */
-    public function testAllDay()
-    {
-        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20090901T000000Z'));
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20091101T000000Z'));
-
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/allday_invitation.eml',
-                           dirname(__FILE__) . '/fixtures/null.ret',
-                           '', '', 'test@example.org', 'wrobel@example.org',
-                           'home.example.org', $params);
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getFolder('INBOX/Kalender');
-        $data = $folder->getData();
-        $events = $data->getObjects();
-
-        $this->assertEquals(1251928800, $events[0]['start-date']);
-        $this->assertEquals(1252015200, $events[0]['end-date']);
-
-        $result = $data->deleteAll();
-        $this->assertNoError($result);
-    }
-
-    /**
-     * Test that the attendee status gets transferred.
-     */
-    public function testAttendeeStatusInvitation()
-    {
-        $this->markTestIncomplete('Sends mail');
-
-        require_once 'Horde/Icalendar/Vfreebusy.php';
-        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20080926T000000Z'));
-        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20081126T000000Z'));
-
-        $params = array('unmodified_content' => true,
-                        'incoming' => true);
-
-        $this->sendFixture(dirname(__FILE__) . '/fixtures/attendee_status_invitation.eml',
-                           dirname(__FILE__) . '/fixtures/null.ret',
-                           '', '', 'test@example.org', 'wrobel@example.org',
-                           'home.example.org', $params);
-
-        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
-        $this->assertNoError($result);
-
-        $folder = $this->storage->getFolder('INBOX/Kalender');
-        $data = $folder->getData();
-        $events = $data->getObjects();
-        $summaries = array();
-        foreach ($events as $event) {
-            foreach ($event['attendee'] as $attendee) {
-                switch ($attendee['smtp-address']) {
-                case 'needs@example.org':
-                    $this->assertEquals('none', $attendee['status']);
-                    break;
-                case 'accepted@example.org':
-                    $this->assertEquals('accepted', $attendee['status']);
-                    break;
-                case 'declined@example.org':
-                    $this->assertEquals('declined', $attendee['status']);
-                    break;
-                case 'tentative@example.org':
-                    $this->assertEquals('tentative', $attendee['status']);
-                    break;
-                case 'delegated@example.org':
-                    $this->assertEquals('none', $attendee['status']);
-                    break;
-                default:
-                    $this->fail('Unexpected attendee!');
-                    break;
-                }
-            }
-        }
-        $result = $data->deleteAll();
-        $this->assertNoError($result);
-    }
-
-}
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/ResourceTestOld.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/ResourceTestOld.php
new file mode 100644 (file)
index 0000000..69d1274
--- /dev/null
@@ -0,0 +1,371 @@
+<?php
+/**
+ * Test resource handling within the Kolab filter implementation.
+ *
+ * @package Horde_Kolab_Filter
+ */
+
+/**
+ *  We need the base class
+ */
+require_once 'Horde/Kolab/Test/Filter.php';
+
+require_once 'Horde.php';
+require_once 'Horde/Kolab/Resource.php';
+require_once 'Horde/Kolab/Filter/Incoming.php';
+require_once 'Horde/Icalendar.php';
+require_once 'Horde/Icalendar/Vfreebusy.php';
+
+/**
+ * Test resource handling
+ *
+ * Copyright 2008 Klarälvdalens Datakonsult AB
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you
+ * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @author  Gunnar Wrobel <wrobel@pardus.de>
+ * @package Horde_Kolab_Filter
+ */
+class Horde_Kolab_Filter_ResourceTest extends Horde_Kolab_Test_Filter
+{
+
+    /**
+     * Set up testing.
+     */
+    protected function setUp()
+    {
+        $result = $this->prepareBasicSetup();
+
+        $this->server  = &$result['server'];
+        $this->storage = &$result['storage'];
+        $this->auth    = &$result['auth'];
+
+        global $conf;
+
+        $conf['kolab']['imap']['server'] = 'localhost';
+        $conf['kolab']['imap']['port']   = 0;
+        $conf['kolab']['imap']['allow_special_users'] = true;
+        $conf['kolab']['filter']['reject_forged_from_header'] = false;
+        $conf['kolab']['filter']['email_domain'] = 'example.org';
+        $conf['kolab']['filter']['privileged_networks'] = '127.0.0.1,192.168.0.0/16';
+        $conf['kolab']['filter']['verify_from_header'] = true;
+        $conf['kolab']['filter']['calendar_id'] = 'calendar';
+        $conf['kolab']['filter']['calendar_pass'] = 'calendar';
+        $conf['kolab']['filter']['lmtp_host'] = 'imap.example.org';
+        $conf['kolab']['filter']['simple_locks'] = true;
+        $conf['kolab']['filter']['simple_locks_timeout'] = 3;
+
+        $conf['kolab']['filter']['itipreply']['driver'] = 'echo';
+        $conf['kolab']['filter']['itipreply']['params']['host'] = 'localhsot';
+        $conf['kolab']['filter']['itipreply']['params']['port'] = 25;
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getNewFolder();
+        $folder->setName('Kalender');
+        $result = $folder->save(array('type' => 'event',
+                                      'default' => true));
+        $this->assertNoError($result);
+    }
+
+    /**
+     * Test retrieval of the resource information
+     */
+    public function testGetResourceData()
+    {
+        $r = &new Kolab_Resource();
+        $d = $r->_getResourceData('test@example.org', 'wrobel@example.org');
+        $this->assertNoError($d);
+        $this->assertEquals('wrobel@example.org', $d['id']);
+        $this->assertEquals('home.example.org', $d['homeserver']);
+        $this->assertEquals('ACT_REJECT_IF_CONFLICTS', $d['action']);
+        $this->assertEquals('cn=Gunnar Wrobel', $d['cn']);
+    }
+
+    /**
+     * Test manual actions
+     */
+    public function testManual()
+    {
+        $r = &new Kolab_Resource();
+        $this->assertTrue($r->handleMessage('otherhost', 'test@example.org', 'wrobel@example.org', null));
+        $r = &new Kolab_Resource();
+        $this->assertTrue($r->handleMessage('localhost', 'test@example.org', 'wrobel@example.org', null));
+    }
+
+
+    /**
+     * Test invitation.
+     */
+    public function testRecurrenceInvitation()
+    {
+        $this->markTestIncomplete('Fails for unknown reason.');
+
+        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20080926T000000Z'));
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20081126T000000Z'));
+
+        $params = array('unmodified_content' => true,
+                        'incoming' => true);
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/recur_invitation.eml',
+                           dirname(__FILE__) . '/fixtures/recur_invitation.ret2',
+                           '', '', 'test@example.org', 'wrobel@example.org',
+                           'home.example.org', $params);
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getFolder('INBOX/Kalender');
+        $data = $folder->getData();
+        $events = $data->getObjects();
+        $this->assertEquals(1222419600, $events[0]['start-date']);
+
+        $result = $data->deleteAll();
+        $this->assertNoError($result);
+    }
+
+    /**
+     * Test an that contains a long string.
+     */
+    public function testLongStringInvitation()
+    {
+        $this->markTestIncomplete('Fails for unknown reason.');
+
+        require_once 'Horde/Icalendar/Vfreebusy.php';
+        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20080926T000000Z'));
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20081126T000000Z'));
+
+        $params = array('unmodified_content' => true,
+                        'incoming' => true);
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/longstring_invitation.eml',
+                           dirname(__FILE__) . '/fixtures/longstring_invitation.ret',
+                           '', '', 'test@example.org', 'wrobel@example.org',
+                           'home.example.org', $params);
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getFolder('INBOX/Kalender');
+        $data = $folder->getData();
+        $events = $data->getObjects();
+        $summaries = array();
+        foreach ($events as $event) {
+            $summaries[] = $event['summary'];
+        }
+        $this->assertContains('invitationtest2', $summaries);
+
+        $result = $data->deleteAll();
+        $this->assertNoError($result);
+    }
+
+    /**
+     * Test an invitation that books a whole day.
+     */
+    public function testWholeDayInvitation()
+    {
+        require_once 'Horde/Icalendar/Vfreebusy.php';
+        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20090401T000000Z'));
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20090601T000000Z'));
+
+        $params = array('unmodified_content' => true,
+                        'incoming' => true);
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/invitation_whole_day.eml',
+                           dirname(__FILE__) . '/fixtures/invitation_whole_day.ret',
+                           '', '', 'test@example.org', 'wrobel@example.org',
+                           'home.example.org', $params);
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getFolder('INBOX/Kalender');
+        $data = $folder->getData();
+        $events = $data->getObjects();
+        $summaries = array();
+        foreach ($events as $event) {
+            $summaries[] = $event['summary'];
+        }
+        $this->assertContains('issue3558', $summaries);
+
+        $result = $data->deleteAll();
+        $this->assertNoError($result);
+    }
+
+    /**
+     * Test an invitation with plus addressing.
+     */
+    public function testInvitationWithPlusAddressing()
+    {
+        require_once 'Horde/Icalendar/Vfreebusy.php';
+        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20090401T000000Z'));
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20090601T000000Z'));
+
+        $params = array('unmodified_content' => true,
+                        'incoming' => true);
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/invitation_plus_addressing.eml',
+                           dirname(__FILE__) . '/fixtures/invitation_plus_addressing.ret',
+                           '', '', 'test@example.org', 'wrobel+laptop@example.org',
+                           'home.example.org', $params);
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getFolder('INBOX/Kalender');
+        $data = $folder->getData();
+        $events = $data->getObjects();
+        $summaries = array();
+        foreach ($events as $event) {
+            $summaries[] = $event['summary'];
+        }
+        $this->assertContains('issue3521', $summaries);
+
+        $result = $data->deleteAll();
+        $this->assertNoError($result);
+    }
+
+    /**
+     * Test invitation when no default has been given.
+     */
+    public function testRecurrenceNodefault()
+    {
+        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20080926T000000Z'));
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20081126T000000Z'));
+
+        $params = array('unmodified_content' => true,
+                        'incoming' => true);
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/recur_invitation.eml',
+                           dirname(__FILE__) . '/fixtures/recur_invitation.ret',
+                           '', '', 'wrobel@example.org', 'else@example.org', 
+                           'home.example.org', $params);
+    }
+
+    /**
+     * Test an issue with recurring invitations.
+     *
+     * https://issues.kolab.org/issue3868
+     */
+    public function testIssue3868()
+    {
+        $this->markTestIncomplete('Fails for unknown reason.');
+
+        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20090901T000000Z'));
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20091101T000000Z'));
+
+        $params = array('unmodified_content' => true,
+                        'incoming' => true);
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/recur_invitation2.eml',
+                           dirname(__FILE__) . '/fixtures/null.ret',
+                           '', '', 'test@example.org', 'wrobel@example.org',
+                           'home.example.org', $params);
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getFolder('INBOX/Kalender');
+        $data = $folder->getData();
+        $events = $data->getObjects();
+        $this->assertEquals(1251950400, $events[0]['start-date']);
+
+        $result = $data->deleteAll();
+        $this->assertNoError($result);
+    }
+
+    /**
+     * Test all day events
+     */
+    public function testAllDay()
+    {
+        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20090901T000000Z'));
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20091101T000000Z'));
+
+        $params = array('unmodified_content' => true,
+                        'incoming' => true);
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/allday_invitation.eml',
+                           dirname(__FILE__) . '/fixtures/null.ret',
+                           '', '', 'test@example.org', 'wrobel@example.org',
+                           'home.example.org', $params);
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getFolder('INBOX/Kalender');
+        $data = $folder->getData();
+        $events = $data->getObjects();
+
+        $this->assertEquals(1251928800, $events[0]['start-date']);
+        $this->assertEquals(1252015200, $events[0]['end-date']);
+
+        $result = $data->deleteAll();
+        $this->assertNoError($result);
+    }
+
+    /**
+     * Test that the attendee status gets transferred.
+     */
+    public function testAttendeeStatusInvitation()
+    {
+        $this->markTestIncomplete('Sends mail');
+
+        require_once 'Horde/Icalendar/Vfreebusy.php';
+        $GLOBALS['KOLAB_FILTER_TESTING'] = new Horde_Icalendar_Vfreebusy();
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTSTART', Horde_Icalendar::_parseDateTime('20080926T000000Z'));
+        $GLOBALS['KOLAB_FILTER_TESTING']->setAttribute('DTEND', Horde_Icalendar::_parseDateTime('20081126T000000Z'));
+
+        $params = array('unmodified_content' => true,
+                        'incoming' => true);
+
+        $this->sendFixture(dirname(__FILE__) . '/fixtures/attendee_status_invitation.eml',
+                           dirname(__FILE__) . '/fixtures/null.ret',
+                           '', '', 'test@example.org', 'wrobel@example.org',
+                           'home.example.org', $params);
+
+        $result = $this->auth->authenticate('wrobel', array('password' => 'none'));
+        $this->assertNoError($result);
+
+        $folder = $this->storage->getFolder('INBOX/Kalender');
+        $data = $folder->getData();
+        $events = $data->getObjects();
+        $summaries = array();
+        foreach ($events as $event) {
+            foreach ($event['attendee'] as $attendee) {
+                switch ($attendee['smtp-address']) {
+                case 'needs@example.org':
+                    $this->assertEquals('none', $attendee['status']);
+                    break;
+                case 'accepted@example.org':
+                    $this->assertEquals('accepted', $attendee['status']);
+                    break;
+                case 'declined@example.org':
+                    $this->assertEquals('declined', $attendee['status']);
+                    break;
+                case 'tentative@example.org':
+                    $this->assertEquals('tentative', $attendee['status']);
+                    break;
+                case 'delegated@example.org':
+                    $this->assertEquals('none', $attendee['status']);
+                    break;
+                default:
+                    $this->fail('Unexpected attendee!');
+                    break;
+                }
+            }
+        }
+        $result = $data->deleteAll();
+        $this->assertNoError($result);
+    }
+
+}
index 6b6c285..d6fa53c 100644 (file)
@@ -42,7 +42,41 @@ extends PHPUnit_Extensions_Story_TestCase
     public function runGiven(&$world, $action, $arguments)
     {
         switch($action) {
-        case 'that no Kolab server configuration file can be found':
+        case 'an incoming message on host':
+            $world['hostname'] = $arguments[0];
+            $world['type'] = 'Incoming';
+            break;
+        case 'the SMTP sender address is':
+            $world['sender'] = $arguments[0];
+            break;
+        case 'the SMTP recipient address is':
+            $world['recipient'] = $arguments[0];
+            break;
+        case 'the client address is':
+            $world['client'] = $arguments[0];
+            break;
+        case 'the hostname is':
+            $world['hostname'] = $arguments[0];
+            break;
+        case 'the unmodified message content is':
+            $world['infile'] = $arguments[0];
+            $world['fp']     = fopen($world['infile'], 'r');
+            break;
+        case 'the modified message template is':
+            $world['infile'] = $arguments[0];
+            $world['fp']     = fopen($world['infile'], 'r');
+            stream_filter_register(
+                'addresses', 'Horde_Kolab_Filter_Helper_AddressFilter'
+            );
+            stream_filter_append(
+                $world['fp'],
+                'addresses',
+                STREAM_FILTER_READ,
+                array(
+                    'recipient' => $world['recipient'],
+                    'sender'    => $world['sender']
+                )
+            );
             break;
         default:
             return $this->notImplemented($action);
@@ -61,7 +95,13 @@ extends PHPUnit_Extensions_Story_TestCase
     public function runWhen(&$world, $action, $arguments)
     {
         switch($action) {
-        case 'reading the configuration':
+        case 'handling the message':
+            $_SERVER['argv'] = $this->_prepareArguments($world);
+            $filter = new Horde_Kolab_Filter();
+            ob_start();
+            $result = $filter->main($world['type'], $world['fp'], 'echo');
+            $world['output'] = ob_get_contents();
+            ob_end_clean();
             break;
         default:
             return $this->notImplemented($action);
@@ -80,11 +120,49 @@ extends PHPUnit_Extensions_Story_TestCase
     public function runThen(&$world, $action, $arguments)
     {
         switch($action) {
-        case 'the Config Object will throw an exception of type':
+        case 'the result will be the same as the content in':
+            $out = file_get_contents($arguments[0]);
+            $this->_cleanAndCompareOutput($out, $world['output']);
             break;
         default:
             return $this->notImplemented($action);
         }
     }
 
+    private function _prepareArguments(&$world)
+    {
+        $recipient = isset($world['recipient']) ? $world['recipient'] : '';
+        $sender    = isset($world['sender']) ? $world['sender'] : '';
+        $user      = isset($world['user']) ? $world['user'] : '';
+        $hostname  = isset($world['hostname']) ? $world['hostname'] : '';
+        $client    = isset($world['client']) ? $world['client'] : '';
+        return array(
+            $_SERVER['argv'][0],
+            '--sender=' . $sender,
+            '--recipient=' . $recipient,
+            '--user=' . $user,
+            '--host=' . $hostname,
+            '--client=' . $client
+        );
+
+    }
+
+    private function _cleanAndCompareOutput($received, $expected)
+    {
+        $replace = array(
+            '/^Received:.*$/m' => '',
+            '/^Date:.*$/m' => '',
+            '/DTSTAMP:.*$/m' => '',
+            '/^--+=.*$/m' => '----',
+            '/^Message-ID.*$/m' => '----',
+            '/boundary=.*$/m' => '----',
+            '/\s/' => '',
+        );
+        foreach ($replace as $pattern => $replacement) {
+            $received = preg_replace($pattern, $replacement, $received);
+            $expected = preg_replace($pattern, $replacement, $expected);
+        }
+
+        $this->assertEquals($received, $expected);
+    }
 }
\ No newline at end of file
diff --git a/framework/Kolab_Filter/test/Horde/Kolab/Filter/Unit/Helper/AddressFilter.php b/framework/Kolab_Filter/test/Horde/Kolab/Filter/Unit/Helper/AddressFilter.php
new file mode 100644 (file)
index 0000000..6be8645
--- /dev/null
@@ -0,0 +1,113 @@
+<?php
+/**
+ * Test the address rewriting filter.
+ *
+ * PHP version 5
+ *
+ * @category   Kolab
+ * @package    Kolab_Filter
+ * @subpackage UnitTests
+ * @author     Gunnar Wrobel <wrobel@pardus.de>
+ * @license    http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link       http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+
+/**
+ * Prepare the test setup.
+ */
+require_once dirname(__FILE__) . '/../../Autoload.php';
+
+/**
+ * Test the address rewriting filter.
+ *
+ * Copyright 2010 The Horde Project (http://www.horde.org/)
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you
+ * did not receive this file, see http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ *
+ * @category   Kolab
+ * @package    Kolab_Filter
+ * @subpackage UnitTests
+ * @author     Gunnar Wrobel <wrobel@pardus.de>
+ * @license    http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @link       http://pear.horde.org/index.php?package=Kolab_Filter
+ */
+class Horde_Kolab_Filter_Unit_Helper_AddressFilterTest
+extends PHPUnit_Framework_TestCase
+{
+    public function testFilter()
+    {
+        $fp = fopen('php://memory', 'w+');
+        fputs($fp, "hello\n");
+        rewind($fp);
+        stream_filter_register('addresses', 'Horde_Kolab_Filter_Helper_AddressFilter');
+        stream_filter_append($fp, 'addresses');
+        $this->assertEquals("hello\n", stream_get_contents($fp));
+    }
+
+    public function testFilterEmptiesUnsetParameterOne()
+    {
+        $fp = fopen('php://memory', 'w+');
+        fputs($fp, "hello%1\$s\n");
+        rewind($fp);
+        stream_filter_register('addresses', 'Horde_Kolab_Filter_Helper_AddressFilter');
+        stream_filter_append($fp, 'addresses');
+        $this->assertEquals("hello\n", stream_get_contents($fp));
+    }
+
+    public function testFilterEmptiesUnsetParameterTwo()
+    {
+        $fp = fopen('php://memory', 'w+');
+        fputs($fp, "hello%2\$s\n");
+        rewind($fp);
+        stream_filter_register('addresses', 'Horde_Kolab_Filter_Helper_AddressFilter');
+        stream_filter_append($fp, 'addresses');
+        $this->assertEquals("hello\n", stream_get_contents($fp));
+    }
+
+    public function testFilterSetsParameterSender()
+    {
+        $fp = fopen('php://memory', 'w+');
+        fputs($fp, "hello %1\$s\n");
+        rewind($fp);
+        stream_filter_register('addresses', 'Horde_Kolab_Filter_Helper_AddressFilter');
+        stream_filter_append($fp, 'addresses', STREAM_FILTER_READ, array('sender' => 'sender'));
+        $this->assertEquals("hello sender\n", stream_get_contents($fp));
+    }
+
+    public function testFilterSetsParameterRecipient()
+    {
+        $fp = fopen('php://memory', 'w+');
+        fputs($fp, "hello %2\$s\n");
+        rewind($fp);
+        stream_filter_register('addresses', 'Horde_Kolab_Filter_Helper_AddressFilter');
+        stream_filter_append($fp, 'addresses', STREAM_FILTER_READ, array('recipient' => 'recipient'));
+        $this->assertEquals("hello recipient\n", stream_get_contents($fp));
+    }
+
+    /**
+     * @dataProvider provideBrokenParameters
+     */
+    public function testFilterHandlesBrokenParameter($param)
+    {
+        $fp = fopen('php://memory', 'w+');
+        $append = "hello $param\n";
+        fputs($fp, str_repeat('a', 16384 - strlen($append)) . $append . str_repeat('test', 300));
+        rewind($fp);
+        stream_filter_register('addresses', 'Horde_Kolab_Filter_Helper_AddressFilter');
+        stream_filter_append($fp, 'addresses');
+        fread($fp, 16384 - strlen($append));
+        $this->assertEquals("hello $param\n", fread($fp, strlen($append)));
+    }
+
+    public function provideBrokenParameters()
+    {
+        return array(
+            array("%"),
+            array("%1"),
+            array("%2"),
+            array("%2\$"),
+            array("%2\$\ns"),
+        );
+    }
+}
\ No newline at end of file