From: Dan Brown Date: Thu, 6 Feb 2025 14:58:08 +0000 (+0000) Subject: Sorting: Improved sort set display, delete, added action on edit X-Git-Tag: v25.02~1^2~17^2~7 X-Git-Url: http://source.bookstackapp.com/bookstack/commitdiff_plain/ccd94684ebc5d8b14a9fa4e7b0808501b3c80cd9 Sorting: Improved sort set display, delete, added action on edit - Changes to a sort set will now auto-apply to assinged books (basic chunck through all on save). - Added book count indicator to sort set list items. - Deletion now has confirmation and auto-handling of assigned books/settings. --- diff --git a/app/Sorting/BookSorter.php b/app/Sorting/BookSorter.php index e89fdaccc..fd99a8d37 100644 --- a/app/Sorting/BookSorter.php +++ b/app/Sorting/BookSorter.php @@ -16,6 +16,15 @@ class BookSorter ) { } + public function runBookAutoSortForAllWithSet(SortSet $set): void + { + $set->books()->chunk(50, function ($books) { + foreach ($books as $book) { + $this->runBookAutoSort($book); + } + }); + } + /** * Runs the auto-sort for a book if the book has a sort set applied to it. * This does not consider permissions since the sort operations are centrally diff --git a/app/Sorting/SortSetController.php b/app/Sorting/SortSetController.php index 8f5120791..b0ad2a7d7 100644 --- a/app/Sorting/SortSetController.php +++ b/app/Sorting/SortSetController.php @@ -52,7 +52,7 @@ class SortSetController extends Controller return view('settings.sort-sets.edit', ['set' => $set]); } - public function update(string $id, Request $request) + public function update(string $id, Request $request, BookSorter $bookSorter) { $this->validate($request, [ 'name' => ['required', 'string', 'min:1', 'max:200'], @@ -67,26 +67,44 @@ class SortSetController extends Controller $set->name = $request->input('name'); $set->setOperations($operations); + $changedSequence = $set->isDirty('sequence'); $set->save(); $this->logActivity(ActivityType::SORT_SET_UPDATE, $set); + if ($changedSequence) { + $bookSorter->runBookAutoSortForAllWithSet($set); + } + return redirect('/settings/sorting'); } - public function destroy(string $id) + public function destroy(string $id, Request $request) { $set = SortSet::query()->findOrFail($id); - - if ($set->books()->count() > 0) { - $this->showErrorNotification(trans('settings.sort_set_delete_fail_books')); - return redirect($set->getUrl()); + $confirmed = $request->input('confirm') === 'true'; + $booksAssigned = $set->books()->count(); + $warnings = []; + + if ($booksAssigned > 0) { + if ($confirmed) { + $set->books()->update(['sort_set_id' => null]); + } else { + $warnings[] = trans('settings.sort_set_delete_warn_books', ['count' => $booksAssigned]); + } } $defaultBookSortSetting = intval(setting('sorting-book-default', '0')); if ($defaultBookSortSetting === intval($id)) { - $this->showErrorNotification(trans('settings.sort_set_delete_fail_default')); - return redirect($set->getUrl()); + if ($confirmed) { + setting()->remove('sorting-book-default'); + } else { + $warnings[] = trans('settings.sort_set_delete_warn_default'); + } + } + + if (count($warnings) > 0) { + return redirect($set->getUrl() . '#delete')->withErrors(['delete' => $warnings]); } $set->delete(); diff --git a/lang/en/settings.php b/lang/en/settings.php index eb046d278..19ffd9240 100644 --- a/lang/en/settings.php +++ b/lang/en/settings.php @@ -83,9 +83,9 @@ return [ 'sort_set_create' => 'Create Sort Set', 'sort_set_edit' => 'Edit Sort Set', 'sort_set_delete' => 'Delete Sort Set', - 'sort_set_delete_desc' => 'Remove this sort set from the system. Deletion will only go ahead if the sort is not in active use.', - 'sort_set_delete_fail_books' => 'Unable to delete this sort set since it has books assigned.', - 'sort_set_delete_fail_default' => 'Unable to delete this sort set since it\'s used as the default book sort.', + 'sort_set_delete_desc' => 'Remove this sort set from the system. Books using this sort will revert to manual sorting.', + 'sort_set_delete_warn_books' => 'This sort set is currently used on :count book(s). Are you sure you want to delete this?', + 'sort_set_delete_warn_default' => 'This sort set is currently used as the default for books. Are you sure you want to delete this?', 'sort_set_details' => 'Sort Set Details', 'sort_set_details_desc' => 'Set a name for this sort set, which will appear in lists when users are selecting a sort.', 'sort_set_operations' => 'Sort Operations', diff --git a/resources/views/settings/categories/sorting.blade.php b/resources/views/settings/categories/sorting.blade.php index 0af3a8fb8..60fb329b6 100644 --- a/resources/views/settings/categories/sorting.blade.php +++ b/resources/views/settings/categories/sorting.blade.php @@ -1,7 +1,10 @@ @extends('settings.layout') @php - $sortSets = \BookStack\Sorting\SortSet::query()->orderBy('name', 'asc')->get(); + $sortSets = \BookStack\Sorting\SortSet::query() + ->withCount('books') + ->orderBy('name', 'asc') + ->get(); @endphp @section('card') diff --git a/resources/views/settings/sort-sets/edit.blade.php b/resources/views/settings/sort-sets/edit.blade.php index 3b88c1243..febcd9ffe 100644 --- a/resources/views/settings/sort-sets/edit.blade.php +++ b/resources/views/settings/sort-sets/edit.blade.php @@ -22,16 +22,26 @@ -
+
-
+

{{ trans('settings.sort_set_delete') }}

-

{{ trans('settings.sort_set_delete_desc') }}

+

{{ trans('settings.sort_set_delete_desc') }}

+ @if($errors->has('delete')) + @foreach($errors->get('delete') as $error) +

{{ $error }}

+ @endforeach + @endif
{{ method_field('DELETE') }} {{ csrf_field() }} + + @if($errors->has('delete')) + + @endif +
diff --git a/resources/views/settings/sort-sets/parts/sort-set-list-item.blade.php b/resources/views/settings/sort-sets/parts/sort-set-list-item.blade.php index e5ee1fb87..e977c286e 100644 --- a/resources/views/settings/sort-sets/parts/sort-set-list-item.blade.php +++ b/resources/views/settings/sort-sets/parts/sort-set-list-item.blade.php @@ -1,8 +1,12 @@ -
-
+
+ -
+
{{ implode(', ', array_map(fn ($op) => $op->getLabel(), $set->getOperations())) }}
+
+ @icon('book'){{ $set->books_count ?? 0 }} +
\ No newline at end of file