From e750d1b8164a7a1e584c77d3ef4113b4fcf3da39 Mon Sep 17 00:00:00 2001
From: thomascube <thomas@roundcube.net>
Date: Fri, 30 Sep 2011 11:22:08 -0400
Subject: [PATCH] Restrict folders list to write-only in selectors for special folders and save-message-to option

---
 program/include/main.inc        |    4 ++--
 program/include/rcube_imap.php  |   38 ++++++++++++++++++++++++++++++++++----
 program/steps/mail/compose.inc  |    3 ++-
 program/steps/settings/func.inc |    2 +-
 4 files changed, 39 insertions(+), 8 deletions(-)

diff --git a/program/include/main.inc b/program/include/main.inc
index 4aefb3f..c7a6e7b 100644
--- a/program/include/main.inc
+++ b/program/include/main.inc
@@ -1214,9 +1214,9 @@
     $p['folder_name'] = '*';
 
   if ($p['unsubscribed'])
-    $list = $RCMAIL->imap->list_unsubscribed('', $p['folder_name'], $p['folder_filter']);
+    $list = $RCMAIL->imap->list_unsubscribed('', $p['folder_name'], $p['folder_filter'], $p['folder_rights']);
   else
-    $list = $RCMAIL->imap->list_mailboxes('', $p['folder_name'], $p['folder_filter']);
+    $list = $RCMAIL->imap->list_mailboxes('', $p['folder_name'], $p['folder_filter'], $p['folder_rights']);
 
   $delimiter = $RCMAIL->imap->get_hierarchy_delimiter();
 
diff --git a/program/include/rcube_imap.php b/program/include/rcube_imap.php
index 0f56515..f37cfda 100644
--- a/program/include/rcube_imap.php
+++ b/program/include/rcube_imap.php
@@ -2917,13 +2917,14 @@
      * @param   string  $root   Optional root folder
      * @param   string  $name   Optional name pattern
      * @param   string  $filter Optional filter
+     * @param   string  $rights Optional ACL requirements
      *
      * @return  array   List of mailboxes/folders
      * @access  public
      */
-    function list_mailboxes($root='', $name='*', $filter=null)
+    function list_mailboxes($root='', $name='*', $filter=null, $rights=null)
     {
-        $a_mboxes = $this->_list_mailboxes($root, $name, $filter);
+        $a_mboxes = $this->_list_mailboxes($root, $name, $filter, $rights);
 
         // INBOX should always be available
         if ((!$filter || $filter == 'mail') && !in_array('INBOX', $a_mboxes)) {
@@ -2943,17 +2944,19 @@
      * @param   string  $root   Optional root folder
      * @param   string  $name   Optional name pattern
      * @param   mixed   $filter Optional filter
+     * @param   string  $rights Optional ACL requirements
      *
      * @return  array   List of mailboxes/folders
      * @see     rcube_imap::list_mailboxes()
      * @access  private
      */
-    private function _list_mailboxes($root='', $name='*', $filter=null)
+    private function _list_mailboxes($root='', $name='*', $filter=null, $rights=null)
     {
         $cache_key = $root.':'.$name;
         if (!empty($filter)) {
             $cache_key .= ':'.(is_string($filter) ? $filter : serialize($filter));
         }
+        $cache_key .= ':'.$rights;
 
         $cache_key = 'mailboxes.'.md5($cache_key);
 
@@ -3021,6 +3024,11 @@
             $a_folders = array();
         }
 
+        // filter folders list according to rights requirements
+        if ($rights && $this->get_capability('ACL')) {
+            $a_folders = $this->filter_rights($a_folders, $rights);
+        }
+
         // write mailboxlist to cache
         $this->update_cache($cache_key, $a_folders);
 
@@ -3034,10 +3042,11 @@
      * @param string $root   IMAP root dir
      * @param string  $name   Optional name pattern
      * @param mixed   $filter Optional filter
+     * @param string  $rights Optional ACL requirements
      *
      * @return array Indexed array with folder names
      */
-    function list_unsubscribed($root='', $name='*', $filter=null)
+    function list_unsubscribed($root='', $name='*', $filter=null, $rights=null)
     {
         // @TODO: caching
         // Give plugins a chance to provide a list of mailboxes
@@ -3061,6 +3070,11 @@
             array_unshift($a_mboxes, 'INBOX');
         }
 
+        // filter folders list according to rights requirements
+        if ($rights && $this->get_capability('ACL')) {
+            $a_folders = $this->filter_rights($a_folders, $rights);
+        }
+
         // filter folders and sort them
         $a_mboxes = $this->_sort_mailbox_list($a_mboxes);
 
@@ -3069,6 +3083,22 @@
 
 
     /**
+     * Filter the given list of folders according to access rights
+     */
+    private function filter_rights($a_folders, $rights)
+    {
+        $regex = '/('.$rights.')/';
+        foreach ($a_folders as $idx => $folder) {
+            $myrights = join('', (array)$this->my_rights($folder));
+            if ($myrights !== null && !preg_match($regex, $myrights))
+                unset($a_folders[$idx]);
+        }
+
+        return $a_folders;
+    }
+
+
+    /**
      * Get mailbox quota information
      * added by Nuny
      *
diff --git a/program/steps/mail/compose.inc b/program/steps/mail/compose.inc
index aac05be..c31ec9b 100644
--- a/program/steps/mail/compose.inc
+++ b/program/steps/mail/compose.inc
@@ -1383,7 +1383,8 @@
   $attrib['name'] = '_store_target';
   $select = rcmail_mailbox_select(array_merge($attrib, array(
     'noselection' => '- '.rcube_label('dontsave').' -',
-    'folder_filter' => 'mail'
+    'folder_filter' => 'mail',
+    'folder_rights' => 'w',
   )));
   return $select->show($_SESSION['compose']['param']['sent_mbox'], $attrib);
 }
diff --git a/program/steps/settings/func.inc b/program/steps/settings/func.inc
index e6fd910..cb8b918 100644
--- a/program/steps/settings/func.inc
+++ b/program/steps/settings/func.inc
@@ -676,7 +676,7 @@
       // load folders list only when needed
       if ($current) {
         $select = rcmail_mailbox_select(array('noselection' => '---', 'realnames' => true,
-          'maxlength' => 30, 'exceptions' => array('INBOX')));
+          'maxlength' => 30, 'exceptions' => array('INBOX'), 'folder_filter' => 'mail', 'folder_rights' => 'w'));
       }
       else // dummy select
         $select = new html_select();

--
Gitblit v1.9.1