diff --git a/app/Actions/ActivityService.php b/app/Actions/ActivityService.php index 4e5b1f365..e1046db88 100644 --- a/app/Actions/ActivityService.php +++ b/app/Actions/ActivityService.php @@ -13,9 +13,6 @@ class ActivityService protected $user; protected $permissionService; - /** - * ActivityService constructor. - */ public function __construct(Activity $activity, PermissionService $permissionService) { $this->activity = $activity; @@ -26,23 +23,11 @@ class ActivityService /** * Add activity data to database. */ - public function add(Entity $entity, string $activityKey, ?int $bookId = null) + public function add(Entity $entity, string $type, ?int $bookId = null) { - $activity = $this->newActivityForUser($activityKey, $bookId); + $activity = $this->newActivityForUser($type, $bookId); $entity->activity()->save($activity); - $this->setNotification($activityKey); - } - - /** - * Adds a activity history with a message, without binding to a entity. - */ - public function addMessage(string $activityKey, string $message, ?int $bookId = null) - { - $this->newActivityForUser($activityKey, $bookId)->forceFill([ - 'extra' => $message - ])->save(); - - $this->setNotification($activityKey); + $this->setNotification($type); } /** diff --git a/app/Actions/ActivityType.php b/app/Actions/ActivityType.php new file mode 100644 index 000000000..5404d884c --- /dev/null +++ b/app/Actions/ActivityType.php @@ -0,0 +1,22 @@ +parent_id = $parent_id; $entity->comments()->save($comment); + Activity::add($entity, ActivityType::COMMENTED_ON, $entity->book->id); return $comment; } diff --git a/app/Entities/Repos/BookRepo.php b/app/Entities/Repos/BookRepo.php index b0ea7cb87..c2a613f71 100644 --- a/app/Entities/Repos/BookRepo.php +++ b/app/Entities/Repos/BookRepo.php @@ -1,11 +1,13 @@ baseRepo->create($book, $input); + Activity::add($book, ActivityType::BOOK_CREATE, $book->id); return $book; } @@ -100,6 +103,7 @@ class BookRepo public function update(Book $book, array $input): Book { $this->baseRepo->update($book, $input); + Activity::add($book, ActivityType::BOOK_UPDATE, $book->id); return $book; } @@ -129,6 +133,8 @@ class BookRepo { $trashCan = new TrashCan(); $trashCan->softDestroyBook($book); + Activity::add($book, ActivityType::BOOK_DELETE, $book->id); + $trashCan->autoClearOld(); } } diff --git a/app/Entities/Repos/BookshelfRepo.php b/app/Entities/Repos/BookshelfRepo.php index 49fb75f4c..2c80b2a7d 100644 --- a/app/Entities/Repos/BookshelfRepo.php +++ b/app/Entities/Repos/BookshelfRepo.php @@ -1,10 +1,12 @@ baseRepo->create($shelf, $input); $this->updateBooks($shelf, $bookIds); + Activity::add($shelf, ActivityType::BOOKSHELF_CREATE); return $shelf; } /** - * Create a new shelf in the system. + * Update an existing shelf in the system using the given input. */ public function update(Bookshelf $shelf, array $input, ?array $bookIds): Bookshelf { @@ -101,6 +104,7 @@ class BookshelfRepo $this->updateBooks($shelf, $bookIds); } + Activity::add($shelf, ActivityType::BOOKSHELF_UPDATE); return $shelf; } @@ -175,6 +179,7 @@ class BookshelfRepo { $trashCan = new TrashCan(); $trashCan->softDestroyShelf($shelf); + Activity::add($shelf, ActivityType::BOOKSHELF_DELETE); $trashCan->autoClearOld(); } } diff --git a/app/Entities/Repos/ChapterRepo.php b/app/Entities/Repos/ChapterRepo.php index 60599eac8..581da1fa3 100644 --- a/app/Entities/Repos/ChapterRepo.php +++ b/app/Entities/Repos/ChapterRepo.php @@ -1,11 +1,13 @@ book_id = $parentBook->id; $chapter->priority = (new BookContents($parentBook))->getLastPriority() + 1; $this->baseRepo->create($chapter, $input); + Activity::add($chapter, ActivityType::CHAPTER_CREATE, $parentBook->id); return $chapter; } @@ -55,6 +58,7 @@ class ChapterRepo public function update(Chapter $chapter, array $input): Chapter { $this->baseRepo->update($chapter, $input); + Activity::add($chapter, ActivityType::CHAPTER_UPDATE, $chapter->book->id); return $chapter; } @@ -74,6 +78,7 @@ class ChapterRepo { $trashCan = new TrashCan(); $trashCan->softDestroyChapter($chapter); + Activity::add($chapter, ActivityType::CHAPTER_DELETE, $chapter->book->id); $trashCan->autoClearOld(); } @@ -93,6 +98,7 @@ class ChapterRepo throw new MoveOperationException('Chapters can only be moved into books'); } + /** @var Book $parent */ $parent = Book::visible()->where('id', '=', $entityId)->first(); if ($parent === null) { throw new MoveOperationException('Book to move chapter into not found'); @@ -100,6 +106,8 @@ class ChapterRepo $chapter->changeBook($parent->id); $chapter->rebuildPermissions(); + Activity::add($chapter, ActivityType::CHAPTER_MOVE, $parent->id); + return $parent; } } diff --git a/app/Entities/Repos/PageRepo.php b/app/Entities/Repos/PageRepo.php index 80c8afe98..065f1606f 100644 --- a/app/Entities/Repos/PageRepo.php +++ b/app/Entities/Repos/PageRepo.php @@ -1,5 +1,6 @@ savePageRevision($draft, trans('entities.pages_initial_revision')); $draft->indexForSearch(); - return $draft->refresh(); + $draft->refresh(); + + Activity::add($draft, ActivityType::PAGE_CREATE, $draft->book->id); + return $draft; } /** @@ -203,6 +208,7 @@ class PageRepo $this->savePageRevision($page, $summary); } + Activity::add($page, ActivityType::PAGE_UPDATE, $page->book->id); return $page; } @@ -266,6 +272,7 @@ class PageRepo { $trashCan = new TrashCan(); $trashCan->softDestroyPage($page); + Activity::add($page, ActivityType::PAGE_DELETE, $page->book_id); $trashCan->autoClearOld(); } @@ -286,6 +293,7 @@ class PageRepo $page->save(); $page->indexForSearch(); + Activity::add($page, ActivityType::PAGE_RESTORE, $page->book->id); return $page; } @@ -296,7 +304,7 @@ class PageRepo * @throws MoveOperationException * @throws PermissionsException */ - public function move(Page $page, string $parentIdentifier): Book + public function move(Page $page, string $parentIdentifier): Entity { $parent = $this->findParentByIdentifier($parentIdentifier); if ($parent === null) { @@ -311,7 +319,8 @@ class PageRepo $page->changeBook($parent instanceof Book ? $parent->id : $parent->book->id); $page->rebuildPermissions(); - return ($parent instanceof Book ? $parent : $parent->book); + Activity::add($page, ActivityType::PAGE_MOVE, $page->book->id); + return $parent; } /** diff --git a/app/Http/Controllers/Api/BookApiController.php b/app/Http/Controllers/Api/BookApiController.php index 8333eba3a..8ec9fdc06 100644 --- a/app/Http/Controllers/Api/BookApiController.php +++ b/app/Http/Controllers/Api/BookApiController.php @@ -1,5 +1,6 @@ validate($request, $this->rules['create']); $book = $this->bookRepo->create($requestData); - Activity::add($book, 'book_create', $book->id); - return response()->json($book); } @@ -80,7 +79,6 @@ class BookApiController extends ApiController $requestData = $this->validate($request, $this->rules['update']); $book = $this->bookRepo->update($book, $requestData); - Activity::add($book, 'book_update', $book->id); return response()->json($book); } @@ -96,8 +94,6 @@ class BookApiController extends ApiController $this->checkOwnablePermission('book-delete', $book); $this->bookRepo->destroy($book); - Activity::addMessage('book_delete', $book->name); - return response('', 204); } } \ No newline at end of file diff --git a/app/Http/Controllers/Api/BookshelfApiController.php b/app/Http/Controllers/Api/BookshelfApiController.php index 14b5e053b..4650e1dde 100644 --- a/app/Http/Controllers/Api/BookshelfApiController.php +++ b/app/Http/Controllers/Api/BookshelfApiController.php @@ -1,5 +1,6 @@ get('books', []); $shelf = $this->bookshelfRepo->create($requestData, $bookIds); - Activity::add($shelf, 'bookshelf_create', $shelf->id); return response()->json($shelf); } @@ -94,12 +94,9 @@ class BookshelfApiController extends ApiController $this->checkOwnablePermission('bookshelf-update', $shelf); $requestData = $this->validate($request, $this->rules['update']); - $bookIds = $request->get('books', null); $shelf = $this->bookshelfRepo->update($shelf, $requestData, $bookIds); - Activity::add($shelf, 'bookshelf_update', $shelf->id); - return response()->json($shelf); } @@ -115,8 +112,6 @@ class BookshelfApiController extends ApiController $this->checkOwnablePermission('bookshelf-delete', $shelf); $this->bookshelfRepo->destroy($shelf); - Activity::addMessage('bookshelf_delete', $shelf->name); - return response('', 204); } } \ No newline at end of file diff --git a/app/Http/Controllers/Api/ChapterApiController.php b/app/Http/Controllers/Api/ChapterApiController.php index 50aa8834e..60e0f0131 100644 --- a/app/Http/Controllers/Api/ChapterApiController.php +++ b/app/Http/Controllers/Api/ChapterApiController.php @@ -1,5 +1,6 @@ checkOwnablePermission('chapter-create', $book); $chapter = $this->chapterRepo->create($request->all(), $book); - Activity::add($chapter, 'chapter_create', $book->id); - return response()->json($chapter->load(['tags'])); } @@ -83,8 +82,6 @@ class ChapterApiController extends ApiController $this->checkOwnablePermission('chapter-update', $chapter); $updatedChapter = $this->chapterRepo->update($chapter, $request->all()); - Activity::add($chapter, 'chapter_update', $chapter->book->id); - return response()->json($updatedChapter->load(['tags'])); } @@ -97,8 +94,6 @@ class ChapterApiController extends ApiController $this->checkOwnablePermission('chapter-delete', $chapter); $this->chapterRepo->destroy($chapter); - Activity::addMessage('chapter_delete', $chapter->name, $chapter->book->id); - return response('', 204); } } diff --git a/app/Http/Controllers/BookController.php b/app/Http/Controllers/BookController.php index 25dc65194..5a42daddb 100644 --- a/app/Http/Controllers/BookController.php +++ b/app/Http/Controllers/BookController.php @@ -1,12 +1,12 @@ bookRepo = $bookRepo; @@ -97,11 +94,10 @@ class BookController extends Controller $book = $this->bookRepo->create($request->all()); $this->bookRepo->updateCoverImage($book, $request->file('image', null)); - Activity::add($book, 'book_create', $book->id); if ($bookshelf) { $bookshelf->appendBook($book); - Activity::add($bookshelf, 'bookshelf_update'); + Activity::add($bookshelf, ActivityType::BOOKSHELF_UPDATE); } return redirect($book->getUrl()); @@ -162,8 +158,6 @@ class BookController extends Controller $resetCover = $request->has('image_reset'); $this->bookRepo->updateCoverImage($book, $request->file('image', null), $resetCover); - Activity::add($book, 'book_update', $book->id); - return redirect($book->getUrl()); } @@ -187,7 +181,6 @@ class BookController extends Controller $book = $this->bookRepo->getBySlug($bookSlug); $this->checkOwnablePermission('book-delete', $book); - Activity::add($book, 'book_delete', $book->id); $this->bookRepo->destroy($book); return redirect('/books'); diff --git a/app/Http/Controllers/BookSortController.php b/app/Http/Controllers/BookSortController.php index f5fb6f255..e94e4ecce 100644 --- a/app/Http/Controllers/BookSortController.php +++ b/app/Http/Controllers/BookSortController.php @@ -2,6 +2,7 @@ namespace BookStack\Http\Controllers; +use BookStack\Actions\ActivityType; use BookStack\Entities\Book; use BookStack\Entities\Managers\BookContents; use BookStack\Entities\Repos\BookRepo; @@ -74,7 +75,7 @@ class BookSortController extends Controller // Rebuild permissions and add activity for involved books. $booksInvolved->each(function (Book $book) { - Activity::add($book, 'book_sort', $book->id); + Activity::add($book, ActivityType::BOOK_SORT, $book->id); }); return redirect($book->getUrl()); diff --git a/app/Http/Controllers/BookshelfController.php b/app/Http/Controllers/BookshelfController.php index efe280235..8d2eec348 100644 --- a/app/Http/Controllers/BookshelfController.php +++ b/app/Http/Controllers/BookshelfController.php @@ -92,7 +92,6 @@ class BookshelfController extends Controller $shelf = $this->bookshelfRepo->create($request->all(), $bookIds); $this->bookshelfRepo->updateCoverImage($shelf, $request->file('image', null)); - Activity::add($shelf, 'bookshelf_create'); return redirect($shelf->getUrl()); } @@ -156,7 +155,6 @@ class BookshelfController extends Controller $shelf = $this->bookshelfRepo->update($shelf, $request->all(), $bookIds); $resetCover = $request->has('image_reset'); $this->bookshelfRepo->updateCoverImage($shelf, $request->file('image', null), $resetCover); - Activity::add($shelf, 'bookshelf_update'); return redirect($shelf->getUrl()); } @@ -182,7 +180,6 @@ class BookshelfController extends Controller $shelf = $this->bookshelfRepo->getBySlug($slug); $this->checkOwnablePermission('bookshelf-delete', $shelf); - Activity::add($shelf, 'bookshelf_delete'); $this->bookshelfRepo->destroy($shelf); return redirect('/shelves'); diff --git a/app/Http/Controllers/ChapterController.php b/app/Http/Controllers/ChapterController.php index 5d8631154..8eba43e21 100644 --- a/app/Http/Controllers/ChapterController.php +++ b/app/Http/Controllers/ChapterController.php @@ -1,6 +1,5 @@ checkOwnablePermission('chapter-create', $book); $chapter = $this->chapterRepo->create($request->all(), $book); - Activity::add($chapter, 'chapter_create', $book->id); return redirect($chapter->getUrl()); } @@ -100,7 +98,6 @@ class ChapterController extends Controller $this->checkOwnablePermission('chapter-update', $chapter); $this->chapterRepo->update($chapter, $request->all()); - Activity::add($chapter, 'chapter_update', $chapter->book->id); return redirect($chapter->getUrl()); } @@ -128,7 +125,6 @@ class ChapterController extends Controller $chapter = $this->chapterRepo->getBySlug($bookSlug, $chapterSlug); $this->checkOwnablePermission('chapter-delete', $chapter); - Activity::add($chapter, 'chapter_delete', $chapter->book->id); $this->chapterRepo->destroy($chapter); return redirect($chapter->book->getUrl()); @@ -173,8 +169,6 @@ class ChapterController extends Controller return redirect()->back(); } - Activity::add($chapter, 'chapter_move', $newBook->id); - $this->showSuccessNotification(trans('entities.chapter_move_success', ['bookName' => $newBook->name])); return redirect($chapter->getUrl()); } diff --git a/app/Http/Controllers/CommentController.php b/app/Http/Controllers/CommentController.php index 4eb56a4b0..2dc1a4de4 100644 --- a/app/Http/Controllers/CommentController.php +++ b/app/Http/Controllers/CommentController.php @@ -1,6 +1,7 @@ checkPermission('comment-create-all'); $comment = $this->commentRepo->create($page, $request->get('text'), $request->get('parent_id')); - Activity::add($page, 'commented_on', $page->book->id); return view('comments.comment', ['comment' => $comment]); } diff --git a/app/Http/Controllers/PageController.php b/app/Http/Controllers/PageController.php index 6396da23e..862ba3d7f 100644 --- a/app/Http/Controllers/PageController.php +++ b/app/Http/Controllers/PageController.php @@ -1,6 +1,7 @@ checkOwnablePermission('page-create', $draftPage->getParent()); $page = $this->pageRepo->publishDraft($draftPage, $request->all()); - Activity::add($page, 'page_create', $draftPage->book->id); return redirect($page->getUrl()); } @@ -224,7 +224,6 @@ class PageController extends Controller $this->checkOwnablePermission('page-update', $page); $this->pageRepo->update($page, $request->all()); - Activity::add($page, 'page_update', $page->book->id); return redirect($page->getUrl()); } @@ -304,11 +303,9 @@ class PageController extends Controller { $page = $this->pageRepo->getBySlug($bookSlug, $pageSlug); $this->checkOwnablePermission('page-delete', $page); + $parent = $page->getParent(); - $book = $page->book; - $parent = $page->chapter ?? $book; $this->pageRepo->destroy($page); - Activity::add($page, 'page_delete', $page->book_id); return redirect($parent->getUrl()); } @@ -393,7 +390,6 @@ class PageController extends Controller return redirect()->back(); } - Activity::add($page, 'page_move', $page->book->id); $this->showSuccessNotification(trans('entities.pages_move_success', ['parentName' => $parent->name])); return redirect($page->getUrl()); } @@ -438,8 +434,6 @@ class PageController extends Controller return redirect()->back(); } - Activity::add($pageCopy, 'page_create', $pageCopy->book->id); - $this->showSuccessNotification(trans('entities.pages_copy_success')); return redirect($pageCopy->getUrl()); } diff --git a/app/Http/Controllers/PageRevisionController.php b/app/Http/Controllers/PageRevisionController.php index 797f5db8f..b56235d5b 100644 --- a/app/Http/Controllers/PageRevisionController.php +++ b/app/Http/Controllers/PageRevisionController.php @@ -1,5 +1,6 @@ pageRepo->restoreRevision($page, $revisionId); - Activity::add($page, 'page_restore', $page->book->id); return redirect($page->getUrl()); } diff --git a/tests/CommandsTest.php b/tests/CommandsTest.php index bfc0ac0eb..7e931ee96 100644 --- a/tests/CommandsTest.php +++ b/tests/CommandsTest.php @@ -1,5 +1,6 @@ asEditor(); $page = Page::first(); - \Activity::add($page, 'page_update', $page->book->id); + \Activity::add($page, ActivityType::PAGE_UPDATE, $page->book->id); $this->assertDatabaseHas('activities', [ 'key' => 'page_update', diff --git a/tests/User/UserProfileTest.php b/tests/User/UserProfileTest.php index b564ed8c2..cc39c0d8e 100644 --- a/tests/User/UserProfileTest.php +++ b/tests/User/UserProfileTest.php @@ -1,6 +1,7 @@ getNewBlankUser(); $this->actingAs($newUser); $entities = $this->createEntityChainBelongingToUser($newUser, $newUser); - Activity::add($entities['book'], 'book_update', $entities['book']->id); - Activity::add($entities['page'], 'page_create', $entities['book']->id); + Activity::add($entities['book'], ActivityType::BOOK_UPDATE, $entities['book']->id); + Activity::add($entities['page'], ActivityType::PAGE_CREATE, $entities['book']->id); $this->asAdmin()->visit('/user/' . $newUser->id) ->seeInElement('#recent-user-activity', 'updated book') @@ -74,8 +75,8 @@ class UserProfileTest extends BrowserKitTest $newUser = $this->getNewBlankUser(); $this->actingAs($newUser); $entities = $this->createEntityChainBelongingToUser($newUser, $newUser); - Activity::add($entities['book'], 'book_update', $entities['book']->id); - Activity::add($entities['page'], 'page_create', $entities['book']->id); + Activity::add($entities['book'], ActivityType::BOOK_UPDATE, $entities['book']->id); + Activity::add($entities['page'], ActivityType::PAGE_CREATE, $entities['book']->id); $this->asAdmin()->visit('/')->clickInElement('#recent-activity', $newUser->name) ->seePageIs('/user/' . $newUser->id)