Skip to content

Commit

Permalink
Enforce model aliases when generating order by clauses.
Browse files Browse the repository at this point in the history
Invalid SQL could be created by sorting on an invalid alias, with
a field that exists on the model.

Fixes #3797
  • Loading branch information
markstory committed Apr 27, 2013
1 parent 372cd6f commit c327bdc
Show file tree
Hide file tree
Showing 2 changed files with 23 additions and 5 deletions.
3 changes: 2 additions & 1 deletion lib/Cake/Controller/Component/PaginatorComponent.php
Expand Up @@ -372,6 +372,7 @@ public function validateSort(Model $object, array $options, array $whitelist = a
$field = key($options['order']);
if (!in_array($field, $whitelist)) {
$options['order'] = null;
return $options;
}
}

Expand All @@ -385,7 +386,7 @@ public function validateSort(Model $object, array $options, array $whitelist = a
}

if ($object->hasField($field)) {
$order[$alias . '.' . $field] = $value;
$order[$object->alias . '.' . $field] = $value;
} elseif ($object->hasField($key, true)) {
$order[$field] = $value;
} elseif (isset($object->{$alias}) && $object->{$alias}->hasField($field, true)) {
Expand Down
25 changes: 21 additions & 4 deletions lib/Cake/Test/Case/Controller/Component/PaginatorComponentTest.php
Expand Up @@ -969,10 +969,12 @@ public function testValidateSortMultiple() {
$model->alias = 'model';
$model->expects($this->any())->method('hasField')->will($this->returnValue(true));

$options = array('order' => array(
'author_id' => 'asc',
'title' => 'asc'
));
$options = array(
'order' => array(
'author_id' => 'asc',
'title' => 'asc'
)
);
$result = $this->Paginator->validateSort($model, $options);
$expected = array(
'model.author_id' => 'asc',
Expand Down Expand Up @@ -1002,6 +1004,21 @@ public function testValidateSortNoSort() {
$this->assertEquals($options['order'], $result['order']);
}

/**
* Test sorting with incorrect aliases on valid fields.
*
* @return void
*/
public function testValidateSortInvalidAlias() {
$model = $this->getMock('Model');
$model->alias = 'Model';
$model->expects($this->any())->method('hasField')->will($this->returnValue(true));

$options = array('sort' => 'Derp.id');
$result = $this->Paginator->validateSort($model, $options);
$this->assertEquals(array('Model.id' => 'asc'), $result['order']);
}

/**
* test that maxLimit is respected
*
Expand Down

0 comments on commit c327bdc

Please sign in to comment.