Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ A front-end control for sorting SilverStripe lists easily. The aim of this modul

## Requirements

* SilverStripe 4+ or 5+
* SilverStripe ^6

## Usage

Expand All @@ -21,10 +21,10 @@ public function getSorter(){
'Title', //DB field name only
'Popularity' => 'Popularity DESC', //map title to sort sql
'Price' => ['BasePrice' => 'ASC'], //map title to data list sort
ListSorter_Option::create('Age', ['Created' => 'DESC'], //object
ListSorter_Option::create('Age', ['Created' => 'ASC']) //reverse
)
;
ListSorterOption::create('Age', ['Created' => 'DESC']), //object
ListSorterOption::create('Age', ['Created' => 'ASC']) //reverse
];

return ListSorter::create($this->request,$sorts);
}
```
Expand Down
2 changes: 1 addition & 1 deletion composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
}
],
"require": {
"silverstripe/framework": "^4.0 | ^5.0"
"silverstripe/framework": "^6"
},
"extra": {
"branch-alias": {
Expand Down
32 changes: 19 additions & 13 deletions src/ListSorter.php
Original file line number Diff line number Diff line change
@@ -1,19 +1,23 @@
<?php

declare(strict_types=1);

namespace SilverShop\ListSorter;

use SilverStripe\Model\List\ArrayList;
use SilverStripe\Model\ModelData;
use SilverStripe\Control\HTTPRequest;
use SilverStripe\ORM\ArrayList;
use SilverStripe\ORM\DataList;
use SilverStripe\View\ViewableData;

/**
* Control for front-end sorting manipulations
*/
class ListSorter extends ViewableData
class ListSorter extends ModelData
{
private $request;
private $sortOptions = [];
private HTTPRequest $request;

private array $sortOptions = [];

private $current;

public function __construct(HTTPRequest $request, $options = null)
Expand All @@ -29,35 +33,35 @@ public function __construct(HTTPRequest $request, $options = null)
*
* @param array $options
*/
public function setSortOptions($options)
public function setSortOptions($options): void
{
$this->sortOptions = [];
foreach ($options as $key => $value) {
if (is_numeric($key)) {
$key = $value;
}

if ($value instanceof ListSorterOption) {
$this->addSortOption($value);
} else {
$this->addSortOption(
new ListSorterOption($key, $value)
ListSorterOption::create($key, $value)
);
}
}
}

/**
* Add sort option, and set according to sort request param.
*
* @param ListSorterOption $option
*/
public function addSortOption(ListSorterOption $option)
public function addSortOption(ListSorterOption $option): void
{
$this->sortOptions[(string)$option] = $option;
$requestparam = $this->request->getVar('sort');
if ((string)$option === $requestparam) {
$this->current = $option;
}

if ((string)$option->getReverseOption() === $requestparam) {
$this->current = $option->getReverseOption();
}
Expand All @@ -78,12 +82,12 @@ protected function getCurrentOption()
*
* @param $option
*/
public function setCurrentOption(ListSorterOption $option)
public function setCurrentOption(ListSorterOption $option): void
{
$this->current = $option;
}

protected function isCurrent(ListSorterOption $option)
protected function isCurrent(ListSorterOption $option): bool
{
return $option === $this->getCurrentOption();
}
Expand All @@ -99,8 +103,10 @@ public function getSorts()
if ($option->isReversable()) {
$option = $option->getReverseOption();
}

$option = $option->customise(['IsCurrent' => true]);
}

$sorts->push($option);
}

Expand All @@ -116,7 +122,7 @@ public function getSorts()
public function sortList($list)
{
if ($current = $this->getCurrentOption()) {
$list = $list->sort($current->getSortSet());
return $list->sort($current->getSortSet());
}

return $list;
Expand Down
28 changes: 17 additions & 11 deletions src/ListSorterOption.php
Original file line number Diff line number Diff line change
@@ -1,27 +1,32 @@
<?php

declare(strict_types=1);

namespace SilverShop\ListSorter;

use SilverStripe\Model\ModelData;
use SilverStripe\Control\HTTP;
use SilverStripe\View\ViewableData;

/**
* Encapsulate sort option title, sorting SQL,
* GET parameter key, and reverse option.
*/
class ListSorterOption extends ViewableData
class ListSorterOption extends ModelData
{
protected $title;

protected $id;

protected $sortSet;

protected $reverseOption;

public function __construct($title, $sortset, ListSorterOption $reverseOption = null)
{
$this->title = $title;
$this->setID($title);
$this->sortSet = $sortset;
if ($reverseOption) {
if ($reverseOption instanceof \SilverShop\ListSorter\ListSorterOption) {
$this->setReverseOption($reverseOption);
}
}
Expand All @@ -31,7 +36,7 @@ public function getTitle()
return $this->title;
}

public function setTitle($title)
public function setTitle($title): static
{
$this->title = $title;
return $this;
Expand All @@ -42,15 +47,17 @@ public function getSortSet()
return $this->sortSet;
}

public function setReverseOption(ListSorterOption $option)
public function setReverseOption(ListSorterOption $option): static
{
$this->reverseOption = $option;
if (!$option->isReversable()) {
if ($this->getID() === $option->getID()) {
$option->setID((string)$option . "_rev");
$option->setID($option . "_rev");
}

$option->setReverseOption($this);
}

return $this;
}

Expand All @@ -59,12 +66,12 @@ public function getReverseOption()
return $this->reverseOption;
}

public function isReversable()
public function isReversable(): bool
{
return (bool)$this->reverseOption;
}

public function setID($id)
public function setID($id): static
{
$this->id = strtolower(trim($id));
return $this;
Expand All @@ -75,7 +82,7 @@ public function getID()
return $this->id;
}

public function __toString()
public function __toString(): string
{
return $this->id;
}
Expand All @@ -93,9 +100,8 @@ public function getLink()
*/
private function generateLink($id)
{
$url = Http::setGetVar('sort', $id, null, '&');
//TODO: strip "start" pagination parameter,
//as most users won't want to remain on paginated page when sorting
return $url;
return Http::setGetVar('sort', $id, null, '&');
}
}
12 changes: 7 additions & 5 deletions tests/php/ListSorterTest.php
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
<?php

declare(strict_types=1);

namespace SilverShop\ListSorter\Tests;

use SilverStripe\Control\HTTPRequest;
Expand All @@ -8,15 +10,15 @@
use SilverShop\ListSorter\ListSorterOption;
use SilverShop\ListSorter\Tests\Stubs\ListSorterPerson;

class ListSorterTest extends SapphireTest
final class ListSorterTest extends SapphireTest
{
protected static $fixture_file = 'fixture.yaml';

protected static $extra_dataobjects = [
ListSorterPerson::class
];

public function testSorting()
public function testSorting(): void
{
$list = ListSorterPerson::get();

Expand Down Expand Up @@ -74,7 +76,7 @@ public function testSorting()
);
}

public function testListSorterOption()
public function testListSorterOption(): void
{
$option = ListSorterOption::create(
'Age Title',
Expand All @@ -86,13 +88,13 @@ public function testListSorterOption()
$this->assertEquals('age title', $option->getID());
$this->assertEquals('age title', (string)$option);
$this->assertTrue($option->isReversable());
$this->assertEquals('/?colors=always&url=%2F&sort=age+title', $option->getLink());
$this->assertEquals('/?url=%2F&sort=age+title', $option->getLink());

$reverse = $option->getReverseOption();
$this->assertEquals('Age Title', $reverse->getTitle());
$this->assertEquals('age title_rev', $reverse->getID());
$this->assertEquals('age title_rev', (string)$reverse);
$this->assertTrue($reverse->isReversable());
$this->assertEquals('/?colors=always&url=%2F&sort=age+title_rev', $reverse->getLink());
$this->assertEquals('/?url=%2F&sort=age+title_rev', $reverse->getLink());
}
}
6 changes: 5 additions & 1 deletion tests/php/Stubs/ListSorterPerson.php
Original file line number Diff line number Diff line change
@@ -1,13 +1,17 @@
<?php

declare(strict_types=1);

namespace SilverShop\ListSorter\Tests\Stubs;

use SilverStripe\Dev\TestOnly;
use SilverStripe\ORM\DataObject;

class ListSorterPerson extends DataObject implements TestOnly
{
private static $db = [
private static string $table_name = 'ListSorterPerson';

private static array $db = [
'Title' => 'Varchar',
'Age' => 'Int'
];
Expand Down
Loading