From a3463220c32a8436188438fba56ff496f52a3357 Mon Sep 17 00:00:00 2001 From: Ben Klang Date: Sun, 6 Jul 2008 18:21:49 +0000 Subject: [PATCH] Implement Perms-based filtering per-accountcode --- lib/Driver.php | 61 ++++++++++++++++++++++++++++++++++------- lib/Driver/asterisksql.php | 10 +++---- lib/Form/SearchCDR.php | 4 +-- lib/Operator.php | 67 +++++++++++++++++++++++----------------------- search.php | 10 ++++--- 5 files changed, 99 insertions(+), 53 deletions(-) diff --git a/lib/Driver.php b/lib/Driver.php index 7d51f6a56..130579dbc 100644 --- a/lib/Driver.php +++ b/lib/Driver.php @@ -3,7 +3,7 @@ * Operator_Driver:: defines an API for implementing storage backends for * Operator. * - * $Horde: incubator/operator/lib/Driver.php,v 1.3 2008/07/05 17:20:00 bklang Exp $ + * $Horde: incubator/operator/lib/Driver.php,v 1.4 2008/07/06 18:21:50 bklang Exp $ * * Copyright 2007-2008 The Horde Project * @@ -16,21 +16,62 @@ class Operator_Driver { /** - * Array holding the current foo list. Each array entry is a hash - * describing a foo. The array is indexed by the IDs. + * Search the database for call detail records, taking permissions into + * consideration. * - * @var array + * @return boolean|PEAR_Error True on success, PEAR_Error on failure. */ - var $_foos = array(); + function getRecords($start, $end, $accountcode = null, $dcontext = null, + $rowstart = 0, $rowlimit = 100) + { + if (empty($accountcode) || $accountcode == '%') { + $permentry = 'operator:accountcodes'; + } else { + $permentry = 'operator:accountcodes:' . $accountcode; + } + if (!Auth::isAdmin() && + !$GLOBALS['perms']->hasPermission($permentry, Auth::getAuth(), + PERMS_READ)) { + return PEAR::raiseError(_("You do not have permission to view call detail records for that account code.")); + } + + return $this->_getRecords($start, $end, $accountcode, $dcontext, + $rowstart, $rowlimit); + } /** - * Lists all foos. + * Get summary call statistics per-month for a given time range, account and + * destination. + * + * @param Horde_Date startdate Start of the statistics window + * @param Horde_Date enddate End of the statistics window + * @param string accountcode Name of the accont for statistics. Defaults + * to null meaning all accounts. + * @param string dcontext Destination of calls. Defaults to null. * - * @return array Returns a list of all foos. + * + * @return array|PEAR_Error Array of call statistics. The key of each + * element is the month name in date('Y-m') + * format and the value being an array of + * statistics for calls placed that month. This + * method will additionall return PEAR_Error + * on failure. */ - function listFoos() - { - return $this->_foos; + function getMonthlyCallStats($start, $end, $accountcode = null, + $dcontext = null){ + if (empty($accountcode) || $accountcode == '%') { + $permentry = 'operator:accountcodes'; + } else { + $permentry = 'operator:accountcodes:' . $accountcode; + } + if (!Auth::isAdmin() && + !$GLOBALS['perms']->hasPermission($permentry, Auth::getAuth(), + PERMS_READ)) { + return PEAR::raiseError(_("You do not have permission to view call detail records for that account code.")); + } + + return $this->_getMonthlyCallStats($start, $end, $accountcode, + $dcontext); } /** diff --git a/lib/Driver/asterisksql.php b/lib/Driver/asterisksql.php index f55b0bcc6..60538827b 100644 --- a/lib/Driver/asterisksql.php +++ b/lib/Driver/asterisksql.php @@ -20,7 +20,7 @@ * The table structure can be created by the scripts/sql/operator_foo.sql * script. * - * $Horde: incubator/operator/lib/Driver/asterisksql.php,v 1.9 2008/07/05 17:20:00 bklang Exp $ + * $Horde: incubator/operator/lib/Driver/asterisksql.php,v 1.10 2008/07/06 18:21:50 bklang Exp $ * * Copyright 2008 The Horde Project * @@ -72,12 +72,12 @@ class Operator_Driver_asterisksql extends Operator_Driver { } /** - * Get CDR data from the database + * Get call detail records from the database * * @return boolean|PEAR_Error True on success, PEAR_Error on failure. */ - function getData($start, $end, $accountcode = null, $dcontext = null, - $rowstart = 0, $rowlimit = 100) + function _getRecords($start, $end, $accountcode = null, $dcontext = null, + $rowstart = 0, $rowlimit = 100) { // Use the query to make the MySQL driver look like the CDR-CSV driver @@ -190,7 +190,7 @@ class Operator_Driver_asterisksql extends Operator_Driver { * method will additionall return PEAR_Error * on failure. */ - function getMonthlyCallStats($start, $end, $accountcode = null, + function _getMonthlyCallStats($start, $end, $accountcode = null, $dcontext = null) { if (!is_a($start, 'Horde_Date') || !is_a($end, 'Horde_Date')) { diff --git a/lib/Form/SearchCDR.php b/lib/Form/SearchCDR.php index a142de4ed..4ab29ecf3 100644 --- a/lib/Form/SearchCDR.php +++ b/lib/Form/SearchCDR.php @@ -2,7 +2,7 @@ /** * SearchCDRForm Class * - * $Horde: incubator/operator/lib/Form/SearchCDR.php,v 1.5 2008/07/04 04:23:15 bklang Exp $ + * $Horde: incubator/operator/lib/Form/SearchCDR.php,v 1.6 2008/07/06 18:21:50 bklang Exp $ * * Copyright 2008 Alkaloid Networks LLC * @@ -61,7 +61,7 @@ class SearchCDRForm extends Horde_Form { $params = array($start_year, $end_year, $picker, $format_in, $format_out, $show_seconds); - $this->addVariable(_("Account Code"), 'accountcode', 'enum', false, false, null, array(Operator::getAccountCodes())); + $this->addVariable(_("Account Code"), 'accountcode', 'enum', false, false, null, array(Operator::getAccountCodes(true))); $this->addVariable(_("Destination Context"), 'dcontext', 'text', false, false, _("An empty destination context will match all destination contexts.")); $this->addVariable(_("Start Date/Time"), 'startdate', 'datetime', true, false, null, $params); $this->addVariable(_("End Date/Time"), 'enddate', 'datetime', true, false, null, $params); diff --git a/lib/Operator.php b/lib/Operator.php index 42005656d..7ec58d3b4 100644 --- a/lib/Operator.php +++ b/lib/Operator.php @@ -2,7 +2,7 @@ /** * Operator Base Class. * - * $Horde: incubator/operator/lib/Operator.php,v 1.8 2008/07/05 17:20:00 bklang Exp $ + * $Horde: incubator/operator/lib/Operator.php,v 1.9 2008/07/06 18:21:50 bklang Exp $ * * Copyright 2008 The Horde Project * @@ -88,46 +88,47 @@ class Operator { * * @return array List of valid account codes. */ - function getAccountCodes() + function getAccountCodes($permfilter = false) { global $operator_driver; - if (!isset($GLOBALS['cache'])) { - $cache = &Horde_Cache::singleton($GLOBALS['conf']['cache']['driver'], Horde::getDriverConfig('cache', $GLOBALS['conf']['cache']['driver'])); - } else { - $cache =& $GLOBALS['cache']; - } - - // Use 0 lifetime to allow cache lifetime to be set when storing the - // object. - $accountcodes = $cache->get('operator-accountcodes', 0); - if ($accountcodes === false) { - $accountcodes = $operator_driver->getAccountCodes(); - - // Add an option to select all accounts - $keys = $accountcodes; - array_unshift($keys, '%'); - $values = $accountcodes; - array_unshift($values, _("-- All Accounts --")); + $accountcodes = $operator_driver->getAccountCodes(); - if ($index = array_search('', $values)) { - $values[$index] = _("-- Empty Accountcode --"); - } + // Add an option to select all accounts + $keys = $accountcodes; + array_unshift($keys, '%'); + $values = $accountcodes; + array_unshift($values, _("-- All Accounts --")); - // Make the index of each array entry the same as its value - $accountcodes = array_combine($keys, $values); + if ($index = array_search('', $values)) { + $values[$index] = _("-- Empty Accountcode --"); + } - $res = $cache->set('operator-accountcodes', - serialize($accountcodes), 600); - if ($res === false) { - Horde::logMessage('The cache system has experienced an error. Unable to continue.', __FILE__, __LINE__, PEAR_LOG_ERR); - $notification->push(_("Internal error. Details have been logged for the administrator.")); - $accountcodes = array(); + // Make the index of each array entry the same as its value + // array_combine() is PHP5-only + //$accountcodes = array_combine($keys, $values); + $accountcodes = array(); + + // Filter the returned list of account codes through Permissions + // if requested. + foreach ($keys as $index => $accountcode) { + if ($permfilter) { + if (empty($accountcode) || $accountcode == '%') { + $permitem = 'operator:accountcodes'; + } else { + $permitem = 'operator:accountcodes:' . $accountcode; + } + + if (Auth::isAdmin() || + $GLOBALS['perms']->hasPermission($permitem, + Auth::getAuth(), + PERMS_SHOW)) { + $accountcodes[$accountcode] = $values[$index]; + } + } else { + $accountcodes[$accountcode] = $values[$index]; } - } else { - $accountcodes = unserialize($accountcodes); } - return $accountcodes; } diff --git a/search.php b/search.php index 629fdec01..5434605f5 100644 --- a/search.php +++ b/search.php @@ -1,6 +1,6 @@ * @@ -48,8 +48,12 @@ if ($form->isSubmitted() && $form->validate($vars, true)) { if (is_a($start, 'PEAR_Error') || is_a($end, 'PEAR_Error')) { $notification->push(_("Invalid date requested.")); } else { - $data = $operator_driver->getData($start, $end, $accountcode, $dcontext, - $rowstart, $numrows); + $data = $operator_driver->getRecords($start, $end, $accountcode, + $dcontext, $rowstart, $numrows); + if (is_a($data, 'PEAR_Error')) { + $notification->push($data); + $data = array(); + } $_SESSION['operator']['lastsearch']['params'] = array( 'accountcode' => $vars->get('accountcode'), 'dcontext' => $vars->get('dcontext'), -- 2.11.0