From 7f2c8a6286b87455bf12cbbb7bcb899352b61314 Mon Sep 17 00:00:00 2001 From: Roardom Date: Thu, 3 Aug 2023 12:00:55 +0000 Subject: [PATCH] add: staff history search --- .../Controllers/Staff/HistoryController.php | 27 ++ app/Http/Livewire/HistorySearch.php | 174 +++++++++ .../views/Staff/dashboard/index.blade.php | 6 + resources/views/Staff/history/index.blade.php | 22 ++ .../views/livewire/history-search.blade.php | 364 ++++++++++++++++++ routes/web.php | 7 + 6 files changed, 600 insertions(+) create mode 100644 app/Http/Controllers/Staff/HistoryController.php create mode 100644 app/Http/Livewire/HistorySearch.php create mode 100644 resources/views/Staff/history/index.blade.php create mode 100644 resources/views/livewire/history-search.blade.php diff --git a/app/Http/Controllers/Staff/HistoryController.php b/app/Http/Controllers/Staff/HistoryController.php new file mode 100644 index 000000000..bcf2853ae --- /dev/null +++ b/app/Http/Controllers/Staff/HistoryController.php @@ -0,0 +1,27 @@ + + * @license https://www.gnu.org/licenses/agpl-3.0.en.html/ GNU Affero General Public License v3.0 + */ + +namespace App\Http\Controllers\Staff; + +use App\Http\Controllers\Controller; + +class HistoryController extends Controller +{ + /** + * Display All Pages. + */ + public function index(): \Illuminate\Contracts\View\Factory|\Illuminate\View\View + { + return view('Staff.history.index'); + } +} diff --git a/app/Http/Livewire/HistorySearch.php b/app/Http/Livewire/HistorySearch.php new file mode 100644 index 000000000..5d8ed9fe2 --- /dev/null +++ b/app/Http/Livewire/HistorySearch.php @@ -0,0 +1,174 @@ + + * @license https://www.gnu.org/licenses/agpl-3.0.en.html/ GNU Affero General Public License v3.0 + */ + +namespace App\Http\Livewire; + +use App\Models\History; +use App\Models\Torrent; +use App\Models\User; +use Illuminate\Support\Facades\DB; +use Livewire\Component; +use Livewire\WithPagination; + +/** + * @property \Illuminate\Contracts\Pagination\LengthAwarePaginator $histories + */ +class HistorySearch extends Component +{ + use WithPagination; + + public int $perPage = 25; + public string $agent = ''; + public string $torrent = ''; + public string $user = ''; + public string $seeder = 'any'; + public string $active = 'any'; + public string $groupBy = 'none'; + public string $sortField = ''; + public string $sortDirection = 'desc'; + + protected $queryString = [ + 'page' => ['except' => 1], + 'perPage' => ['except' => 25], + 'agent' => ['except' => ''], + 'torrent' => ['except' => ''], + 'user' => ['except' => ''], + 'seeder' => ['except' => 'any'], + 'active' => ['except' => 'any'], + 'groupBy' => ['except' => 'none'], + 'sortField' => ['except' => ''], + 'sortDirection' => ['except' => 'desc'], + ]; + + final public function updatedPage(): void + { + $this->emit('paginationChanged'); + } + + final public function updatingUser(): void + { + $this->resetPage(); + } + + final public function updatingAgent(): void + { + $this->resetPage(); + } + + final public function updatingTorrent(): void + { + $this->resetPage(); + } + + final public function updatingSeeder(): void + { + $this->resetPage(); + } + + final public function updatingActive(): void + { + $this->resetPage(); + } + + final public function updatingGroupBy(): void + { + $this->resetPage(); + } + + final public function getHistoriesProperty(): \Illuminate\Contracts\Pagination\LengthAwarePaginator + { + return History::query() + ->with('user', 'torrent:id,name') + ->when( + $this->groupBy === 'user_id', + fn ($query) => $query->groupBy('user_id') + ->select([ + 'user_id', + DB::raw('COUNT(*) AS torrent_count'), + DB::raw('SUM(uploaded) AS uploaded_sum'), + DB::raw('SUM(actual_uploaded) AS actual_uploaded_sum'), + DB::raw('SUM(client_uploaded) AS client_uploaded_sum'), + DB::raw('SUM(downloaded) AS downloaded_sum'), + DB::raw('SUM(actual_downloaded) AS actual_downloaded_sum'), + DB::raw('SUM(client_downloaded) AS client_downloaded_sum'), + DB::raw('SUM(refunded_download) AS refunded_download_sum'), + DB::raw('AVG(seedtime) AS seedtime_avg'), + DB::raw('MIN(created_at) AS created_at_min'), + DB::raw('MAX(updated_at) AS updated_at_max'), + DB::raw('SUM(active AND seeder) AS seeding_count'), + DB::raw('SUM(active AND NOT seeder) AS leeching_count'), + DB::raw('SUM(prewarn = 1) AS prewarn_count'), + DB::raw('SUM(hitrun = 1) AS hitrun_count'), + DB::raw('SUM(immune = 1) AS immune_count'), + ]) + ->withCasts([ + 'created_at_min' => 'datetime', + 'updated_at_max' => 'datetime', + ]), + fn ($query) => $query + ->select([ + 'user_id', + 'torrent_id', + 'uploaded', + 'actual_uploaded', + 'client_uploaded', + 'downloaded', + 'actual_downloaded', + 'client_downloaded', + 'refunded_download', + 'seedtime', + 'created_at', + 'updated_at', + 'completed_at', + DB::raw('active AND seeder AS seeding'), + DB::raw('active AND NOT seeder AS leeching '), + 'prewarn', + 'hitrun', + 'immune', + ]) + ) + ->when($this->torrent !== '', fn ($query) => $query->whereIn( + 'history.torrent_id', + Torrent::select('id')->where('name', 'LIKE', '%'.str_replace(' ', '%', $this->torrent).'%') + )) + ->when($this->user !== '', fn ($query) => $query->whereIn( + 'history.user_id', + User::select('id')->where('username', 'LIKE', $this->user) + )) + ->when($this->agent !== '', fn ($query) => $query->where('history.agent', 'LIKE', $this->agent.'%')) + ->when($this->active === 'include', fn ($query) => $query->where('active', '=', true)) + ->when($this->active === 'exclude', fn ($query) => $query->where('active', '=', false)) + ->when($this->seeder === 'include', fn ($query) => $query->where('seeder', '=', true)) + ->when($this->seeder === 'exclude', fn ($query) => $query->where('seeder', '=', false)) + ->when($this->sortField !== '', fn ($query) => $query->orderBy($this->sortField, $this->sortDirection)) + ->paginate($this->perPage); + } + + final public function sortBy($field): void + { + if ($this->sortField === $field) { + $this->sortDirection = $this->sortDirection === 'asc' ? 'desc' : 'asc'; + } else { + $this->sortDirection = 'asc'; + } + + $this->sortField = $field; + } + + final public function render(): \Illuminate\Contracts\View\Factory|\Illuminate\Contracts\View\View|\Illuminate\Contracts\Foundation\Application + { + return view('livewire.history-search', [ + 'histories' => $this->histories, + ]); + } +} diff --git a/resources/views/Staff/dashboard/index.blade.php b/resources/views/Staff/dashboard/index.blade.php index 7f14deedb..bacdd260c 100644 --- a/resources/views/Staff/dashboard/index.blade.php +++ b/resources/views/Staff/dashboard/index.blade.php @@ -194,6 +194,12 @@ Peers

+

+ + + Histories + +

diff --git a/resources/views/Staff/history/index.blade.php b/resources/views/Staff/history/index.blade.php new file mode 100644 index 000000000..4a89e9121 --- /dev/null +++ b/resources/views/Staff/history/index.blade.php @@ -0,0 +1,22 @@ +@extends('layout.default') + +@section('title') + History - {{ config('other.title') }} +@endsection + +@section('breadcrumbs') +

+ +@endsection + +@section('page', 'page__history--index') + +@section('content') + @livewire('history-search') +@endsection diff --git a/resources/views/livewire/history-search.blade.php b/resources/views/livewire/history-search.blade.php new file mode 100644 index 000000000..7ddb378ec --- /dev/null +++ b/resources/views/livewire/history-search.blade.php @@ -0,0 +1,364 @@ +
+
+
+

{{ __('common.search') }}

+
+
+
+
+

+ + +

+

+ + +

+

+ + +

+

+ + +

+

+ + +

+

+ + +

+
+
+
+
+
+

Histories

+
+ Loading... +
+
+ @switch ($groupBy) + @case('user_id') + + + + + + + + + + + + + + + + + + + + + + + + @foreach ($histories as $history) + + + + + + + + + + + + + @if ($history->seedtime < config('hitrun.seedtime')) + + @else + + @endif + + + + + + + @endforeach + +
+ {{ __('user.user') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.user_id']) + + {{ __('torrent.torrents') }} + @include('livewire.includes._sort-icon', ['field' => 'torrent_count']) + + {{ __('user.credited-upload') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.uploaded_sum']) + + {{ __('user.upload-true') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.actual_uploaded_sum']) + + Client Upload + @include('livewire.includes._sort-icon', ['field' => 'histories.client_uploaded_sum']) + + {{ __('user.credited-download') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.downloaded_sum']) + + {{ __('user.download-true') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.actual_downloaded_sum']) + + Client Download + @include('livewire.includes._sort-icon', ['field' => 'histories.client_downloaded_sum']) + + {{ __('torrent.refunded') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.refunded_downloaded_sum']) + + {{ __('torrent.started') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.created_at_min']) + + Announced + @include('livewire.includes._sort-icon', ['field' => 'histories.updated_at_max']) + + {{ __('user.avg-seedtime') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.seedtime_avg']) + + {{ __('torrent.seeding') }} + @include('livewire.includes._sort-icon', ['field' => 'seeding_count']) + + {{ __('torrent.leeching') }} + @include('livewire.includes._sort-icon', ['field' => 'leeching_count']) + + + + + + +
+ + + {{ $history->torrent_count }} + + {{ App\Helpers\StringHelper::formatBytes($history->uploaded_sum, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->actual_uploaded_sum, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->client_uploaded_sum, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->downloaded_sum, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->actual_downloaded_sum, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->client_downloaded_sum, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->refunded_downloaded_sum, 2) }} + + + + + + {{ $weeks = intdiv($history->seedtime_avg ?? 0, 3600 * 24 * 7) }}w {{ intdiv(($history->seedtime_avg ?? 0) - $weeks * 3600 * 24 * 7, 3600) }}h + + {{ $weeks = intdiv($history->seedtime_avg ?? 0, 3600 * 24 * 7) }}w {{ intdiv(($history->seedtime_avg ?? 0) - $weeks * 3600 * 24 * 7, 3600) }}h + {{ $history->seeding_count }}{{ $history->leeching_count }}{{ $history->immune_count }}{{ $history->hitrun_count }}{{ $history->prewarn_count }}
+ @break + @default + + + + + + + + + + + + + + + + + + + + + + + + + + @foreach ($histories as $history) + + + + + + + + + + + + + + + @if ($history->seedtime < config('hitrun.seedtime')) + + @else + + @endif + + + + + + + @endforeach + +
+ {{ __('user.user') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.user_id']) + + {{ __('torrent.torrent') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.torrent_id']) + + {{ __('torrent.agent') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.agent']) + + {{ __('user.credited-upload') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.uploaded']) + + {{ __('user.upload-true') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.actual_uploaded']) + + Client Upload + @include('livewire.includes._sort-icon', ['field' => 'histories.client_uploaded']) + + {{ __('user.credited-download') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.downloaded']) + + {{ __('user.download-true') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.actual_downloaded']) + + Client Download + @include('livewire.includes._sort-icon', ['field' => 'histories.client_downloaded']) + + {{ __('torrent.refunded') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.refunded_downloaded']) + + {{ __('torrent.started') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.created_at']) + + Announced + @include('livewire.includes._sort-icon', ['field' => 'histories.updated_at']) + + {{ __('torrent.completed_at') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.completed_at']) + + {{ __('torrent.seedtime') }} + @include('livewire.includes._sort-icon', ['field' => 'histories.seedtime']) + + {{ __('torrent.seeding') }} + @include('livewire.includes._sort-icon', ['field' => 'seeding']) + + {{ __('torrent.leeching') }} + @include('livewire.includes._sort-icon', ['field' => 'leeching']) + + + + + + +
+ + + + {{ $history->torrent->name ?? '' }} + + {{ $history->agent }} + {{ App\Helpers\StringHelper::formatBytes($history->uploaded, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->actual_uploaded, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->client_uploaded, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->downloaded, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->actual_downloaded, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->client_downloaded, 2) }} + + {{ App\Helpers\StringHelper::formatBytes($history->refunded_downloaded, 2) }} + + + + + + + + {{ $weeks = intdiv($history->seedtime ?? 0, 3600 * 24 * 7) }}w {{ intdiv(($history->seedtime ?? 0) - $weeks * 3600 * 24 * 7, 3600) }}h + + {{ $weeks = intdiv($history->seedtime ?? 0, 3600 * 24 * 7) }}w {{ intdiv(($history->seedtime ?? 0) - $weeks * 3600 * 24 * 7, 3600) }}h + + @if ($history->active) + + @else + + @endif + + @if ($history->seeder) + + @else + + @endif + + @if ($history->immune) + + @else + + @endif + + @if ($history->hitrun) + + @else + + @endif + + @if ($history->prewarn) + + @else + + @endif +
+ @endswitch + {{ $histories->links('partials.pagination') }} +
+
+
diff --git a/routes/web.php b/routes/web.php index 3173dcb62..9452d4047 100644 --- a/routes/web.php +++ b/routes/web.php @@ -831,6 +831,13 @@ Route::middleware('language')->group(function (): void { }); }); + // History + Route::prefix('histories')->group(function (): void { + Route::name('histories.')->group(function (): void { + Route::get('/', [App\Http\Controllers\Staff\HistoryController::class, 'index'])->name('index'); + }); + }); + // Invites Log Route::prefix('invites')->group(function (): void { Route::name('invites.')->group(function (): void {