Skip to content

Commit

Permalink
Allow continued manipulation in dispatcher rules.
Browse files Browse the repository at this point in the history
  • Loading branch information
mariuswilms committed Jan 26, 2015
1 parent 492d5f1 commit c7f0328
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 9 deletions.
26 changes: 17 additions & 9 deletions action/Dispatcher.php
Expand Up @@ -67,6 +67,16 @@ class Dispatcher extends \lithium\core\StaticObject {
* ));
* ```
*
* The following example shows two rules that continuously or independently transform the
* action parameter in order to allow any variations i.e. `'admin_index'`, `'api_index'`
* and `'admin_api_index'`.
* ```
* // ...
* 'api' => 'api_{:action}',
* 'admin' => 'admin_{:action}'
* // ...
* ```
*
* Here's another example. To support normalizing actions, set a rule named `'action'` with
* a value array containing a callback that uses `Inflector` to camelize the
* action:
Expand Down Expand Up @@ -167,8 +177,6 @@ public static function run($request, array $options = array()) {
* @return array Returns the `$params` array with formatting rules applied to array values.
*/
public static function applyRules(&$params) {
$result = array();
$values = array();
$rules = static::$_rules;

if (!$params) {
Expand All @@ -189,31 +197,31 @@ public static function applyRules(&$params) {
$controller = "{$params['library']}.{$controller}";
}
}
$values = compact('controller');
$params['controller'] = $controller;
}
$values += $params;

if (is_callable($rules)) {
$rules = $rules($params);
}
foreach ($rules as $rule => $value) {
if (!isset($values[$rule])) {
if (!isset($params[$rule])) {
continue;
}
foreach ($value as $k => $v) {
if (is_callable($v)) {
$result[$k] = $v($values);
$params[$k] = $v($params);
continue;
}
$match = preg_replace('/\{:\w+\}/', '@', $v);
$match = preg_replace('/@/', '.+', preg_quote($match, '/'));
if (preg_match('/' . $match . '/i', $values[$k])) {

if (preg_match('/' . $match . '/i', $params[$k])) {
continue;
}
$result[$k] = String::insert($v, $values);
$params[$k] = String::insert($v, $params);
}
}
return $result + $values;
return $params;
}

/**
Expand Down
18 changes: 18 additions & 0 deletions tests/cases/action/DispatcherTest.php
Expand Up @@ -168,6 +168,24 @@ public function testRunWithSpecialRuleAsCallable() {
$this->assertEqual($expected, $result->params);
}

public function testRunWithContinuingRules() {
MockDispatcher::config(array('rules' => array(
'api' => array('action' => 'api_{:action}'),
'admin' => array('action' => 'admin_{:action}')
)));

Router::connect('/', array(
'controller' => 'test', 'action' => 'test', 'admin' => true, 'api' => true
));
MockDispatcher::run(new Request(array('url' => '/')));

$result = end(MockDispatcher::$dispatched);
$expected = array(
'action' => 'admin_api_test', 'controller' => 'Test', 'admin' => true, 'api' => true
);
$this->assertEqual($expected, $result->params);
}

public function testControllerLookupFail() {
Dispatcher::config(array('classes' => array('router' => __CLASS__)));

Expand Down

0 comments on commit c7f0328

Please sign in to comment.