Skip to content

Commit e4f30b0

Browse files
authored
Feature/add sort and search (#93)
* Updated main list page to allow sorting by description and searching also
1 parent db7bab0 commit e4f30b0

File tree

7 files changed

+110
-9
lines changed

7 files changed

+110
-9
lines changed

resources/views/tasks/form.blade.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -228,7 +228,7 @@
228228
<label class="uk-margin">
229229
Auto Cleanup results after
230230
<br>
231-
<input type="number" name="auto_cleanup_num" id="auto_cleanup_num" value="{{ old('auto_cleanup_num', $task->auto_cleanup_num) }}" />
231+
<input type="number" name="auto_cleanup_num" id="auto_cleanup_num" value="{{ old('auto_cleanup_num', $task->auto_cleanup_num) ?? 0 }}" />
232232
<br>
233233
<label>
234234
<input type="radio" name="auto_cleanup_type" value="days" {{old('auto_cleanup_type', $task->auto_cleanup_type) !== 'results' ? '' : 'checked'}}> Days

resources/views/tasks/index.blade.php

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -6,20 +6,24 @@
66
@section('title')
77
<div class="uk-flex uk-flex-between uk-flex-middle">
88
<h4 class="uk-card-title uk-margin-remove">Tasks</h4>
9-
<form class="uk-display-inline uk-search uk-search-default">
10-
<span class="uk-icon uk-search-icon">
9+
{!! Form::open([
10+
'id' => 'totem__search__form',
11+
'url' => Request::fullUrl(),
12+
'method' => 'GET',
13+
'class' => 'uk-display-inline uk-search uk-search-default'
14+
]) !!}
15+
<span class="uk-icon uk-search-icon" style="cursor: pointer; pointer-events: auto;" onclick="totem__search__form.submit()">
1116
<icon name="search" :scale="100"></icon>
1217
</span>
13-
14-
<input class="uk-search-input" type="search" placeholder="Search...">
15-
</form>
18+
{!! Form::text('q', request('q'), ['class' => 'uk-search-input', 'placeholder' => 'Search...']) !!}
19+
{!! Form::close() !!}
1620
</div>
1721
@stop
1822
@section('main-panel-content')
1923
<table class="uk-table uk-table-responsive" cellpadding="0" cellspacing="0" class="mb1">
2024
<thead>
2125
<tr>
22-
<th>Description</th>
26+
<th>{!! Html::columnSort('Description', 'description') !!}</th>
2327
<th>Average Runtime</th>
2428
<th>Last Run</th>
2529
<th>Next Run</th>

src/Http/Controllers/TasksController.php

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,15 @@ public function __construct(TaskInterface $tasks)
3535
public function index()
3636
{
3737
return view('totem::tasks.index', [
38-
'tasks' => $this->tasks->builder()->orderBy('description')->paginate(20),
38+
'tasks' => $this->tasks
39+
->builder()
40+
->sortableBy([
41+
'description',
42+
], ['description'=>'asc'])
43+
->when(request('q'), function ($query) {
44+
$query->where('description', 'LIKE', '%'.request('q').'%');
45+
})
46+
->paginate(20),
3947
]);
4048
}
4149

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
<?php
2+
3+
namespace Studio\Totem\Providers;
4+
5+
use Illuminate\Support\ServiceProvider;
6+
7+
class TotemFormServiceProvider extends ServiceProvider
8+
{
9+
/**
10+
* Bootstrap the application services.
11+
*
12+
* @return void
13+
*/
14+
public function boot()
15+
{
16+
$this->app['html']->macro('columnSort', function (string $label, string $columnKey, bool $isDefault = false) {
17+
$icon = '';
18+
19+
if (request()->has('sort_by')) {
20+
if (request()->input('sort_by') == $columnKey) {
21+
$icon = ' <span class="fa fa-caret-'
22+
.(request()->input('sort_direction', 'asc') == 'asc' ? 'up' : 'down')
23+
.'"></span>';
24+
}
25+
} elseif ($isDefault) {
26+
$icon = ' <span class="fa fa-caret-'
27+
.(request()->input('sort_direction', 'asc') == 'asc' ? 'up' : 'down')
28+
.'"></span>';
29+
}
30+
31+
$order = 'asc';
32+
if (request()->has('sort_direction')) {
33+
$order = (request()->input('sort_direction') == 'desc' ? 'asc' : 'desc');
34+
} elseif ($isDefault) {
35+
$order = 'desc';
36+
}
37+
38+
$url = request()->fullUrlWithQuery([
39+
'sort_by' => $columnKey,
40+
'sort_direction' => $order,
41+
'filter' => request('filter'),
42+
'limit' => request('limit'),
43+
]);
44+
45+
return app('html')->toHtmlString(
46+
'<a href="'
47+
.$url
48+
.'">'
49+
.$label
50+
.$icon
51+
.'</a>'
52+
);
53+
});
54+
}
55+
}

src/Providers/TotemServiceProvider.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,7 @@ public function register()
4949
$this->app->alias('totem.tasks', TaskInterface::class);
5050
$this->app->register(TotemRouteServiceProvider::class);
5151
$this->app->register(TotemEventServiceProvider::class);
52+
$this->app->register(TotemFormServiceProvider::class);
5253

5354
$this->mergeConfigFrom(
5455
__DIR__.'/../../config/totem.php',

src/Task.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,11 @@
66
use Cron\CronExpression;
77
use Studio\Totem\Traits\HasFrequencies;
88
use Illuminate\Notifications\Notifiable;
9+
use Studio\Totem\Traits\FrontendSortable;
910

1011
class Task extends TotemModel
1112
{
12-
use Notifiable, HasFrequencies;
13+
use Notifiable, HasFrequencies, FrontendSortable;
1314

1415
/**
1516
* The attributes that are mass assignable.

src/Traits/FrontendSortable.php

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
<?php
2+
3+
namespace Studio\Totem\Traits;
4+
5+
use Illuminate\Database\Eloquent\Builder;
6+
7+
trait FrontendSortable
8+
{
9+
/**
10+
* @param \Illuminate\Database\Eloquent\Builder $builder
11+
* @param array $sortableColumns
12+
* @param array $defaultSort
13+
*
14+
* @return \Illuminate\Database\Eloquent\Builder
15+
*/
16+
public function scopeSortableBy(Builder $builder, array $sortableColumns, array $defaultSort = ['name' => 'asc']) : Builder
17+
{
18+
$request = request();
19+
$sorted = $request->has('sort_by') && in_array($request->input('sort_by'), $sortableColumns);
20+
21+
return $builder->when($sorted, function (Builder $query) use ($request) {
22+
$query->orderBy(
23+
$request->input('sort_by'),
24+
(($request->input('sort_direction', 'asc') == 'desc') ? 'desc' : 'asc')
25+
);
26+
}, function (Builder $query) use ($defaultSort) {
27+
foreach ($defaultSort as $key => $direction) {
28+
$query->orderBy($key, $direction);
29+
}
30+
});
31+
}
32+
}

0 commit comments

Comments
 (0)