3 namespace BookStack\Entities\Repos;
5 use BookStack\Activity\TagRepo;
6 use BookStack\Entities\Models\BookChild;
7 use BookStack\Entities\Models\HasCoverInterface;
8 use BookStack\Entities\Models\HasDescriptionInterface;
9 use BookStack\Entities\Models\Entity;
10 use BookStack\Entities\Queries\PageQueries;
11 use BookStack\Exceptions\ImageUploadException;
12 use BookStack\References\ReferenceStore;
13 use BookStack\References\ReferenceUpdater;
14 use BookStack\Sorting\BookSorter;
15 use BookStack\Uploads\ImageRepo;
16 use BookStack\Util\HtmlDescriptionFilter;
17 use Illuminate\Http\UploadedFile;
21 public function __construct(
22 protected TagRepo $tagRepo,
23 protected ImageRepo $imageRepo,
24 protected ReferenceUpdater $referenceUpdater,
25 protected ReferenceStore $referenceStore,
26 protected PageQueries $pageQueries,
27 protected BookSorter $bookSorter,
32 * Create a new entity in the system.
33 * @template T of Entity
37 public function create(Entity $entity, array $input): Entity
39 $entity = (clone $entity)->refresh();
40 $entity->fill($input);
42 'created_by' => user()->id,
43 'updated_by' => user()->id,
44 'owned_by' => user()->id,
46 $entity->refreshSlug();
48 if ($entity instanceof HasDescriptionInterface) {
49 $this->updateDescription($entity, $input);
54 if (isset($input['tags'])) {
55 $this->tagRepo->saveTagsToEntity($entity, $input['tags']);
59 $entity->rebuildPermissions();
60 $entity->indexForSearch();
62 $this->referenceStore->updateForEntity($entity);
68 * Update the given entity.
69 * @template T of Entity
73 public function update(Entity $entity, array $input): Entity
75 $oldUrl = $entity->getUrl();
77 $entity->fill($input);
78 $entity->updated_by = user()->id;
80 if ($entity->isDirty('name') || empty($entity->slug)) {
81 $entity->refreshSlug();
84 if ($entity instanceof HasDescriptionInterface) {
85 $this->updateDescription($entity, $input);
90 if (isset($input['tags'])) {
91 $this->tagRepo->saveTagsToEntity($entity, $input['tags']);
95 $entity->indexForSearch();
96 $this->referenceStore->updateForEntity($entity);
98 if ($oldUrl !== $entity->getUrl()) {
99 $this->referenceUpdater->updateEntityReferences($entity, $oldUrl);
106 * Update the given items' cover image or clear it.
108 * @throws ImageUploadException
111 public function updateCoverImage(Entity&HasCoverInterface $entity, ?UploadedFile $coverImage, bool $removeImage = false): void
114 $imageType = 'cover_' . $entity->type;
115 $this->imageRepo->destroyImage($entity->coverInfo()->getImage());
116 $image = $this->imageRepo->saveNew($coverImage, $imageType, $entity->id, 512, 512, true);
117 $entity->coverInfo()->setImage($image);
122 $this->imageRepo->destroyImage($entity->coverInfo()->getImage());
123 $entity->coverInfo()->setImage(null);
129 * Sort the parent of the given entity if any auto sort actions are set for it.
130 * Typically ran during create/update/insert events.
132 public function sortParent(Entity $entity): void
134 if ($entity instanceof BookChild) {
135 $book = $entity->book;
136 $this->bookSorter->runBookAutoSort($book);
141 * Update the description of the given entity from input data.
143 protected function updateDescription(Entity $entity, array $input): void
145 if (!$entity instanceof HasDescriptionInterface) {
149 if (isset($input['description_html'])) {
150 $entity->descriptionInfo()->set(
151 HtmlDescriptionFilter::filterFromString($input['description_html']),
152 html_entity_decode(strip_tags($input['description_html']))
154 } else if (isset($input['description'])) {
155 $entity->descriptionInfo()->set('', $input['description']);