]> BookStack Code Mirror - bookstack/blob - app/Http/Controllers/ImageController.php
Added drawing update ability
[bookstack] / app / Http / Controllers / ImageController.php
1 <?php namespace BookStack\Http\Controllers;
2
3 use BookStack\Exceptions\ImageUploadException;
4 use BookStack\Repos\EntityRepo;
5 use BookStack\Repos\ImageRepo;
6 use Illuminate\Filesystem\Filesystem as File;
7 use Illuminate\Http\Request;
8 use BookStack\Image;
9 use BookStack\Repos\PageRepo;
10
11 class ImageController extends Controller
12 {
13     protected $image;
14     protected $file;
15     protected $imageRepo;
16
17     /**
18      * ImageController constructor.
19      * @param Image $image
20      * @param File $file
21      * @param ImageRepo $imageRepo
22      */
23     public function __construct(Image $image, File $file, ImageRepo $imageRepo)
24     {
25         $this->image = $image;
26         $this->file = $file;
27         $this->imageRepo = $imageRepo;
28         parent::__construct();
29     }
30
31     /**
32      * Get all images for a specific type, Paginated
33      * @param string $type
34      * @param int $page
35      * @return \Illuminate\Http\JsonResponse
36      */
37     public function getAllByType($type, $page = 0)
38     {
39         $imgData = $this->imageRepo->getPaginatedByType($type, $page);
40         return response()->json($imgData);
41     }
42
43     /**
44      * Search through images within a particular type.
45      * @param $type
46      * @param int $page
47      * @param Request $request
48      * @return mixed
49      */
50     public function searchByType($type, $page = 0, Request $request)
51     {
52         $this->validate($request, [
53             'term' => 'required|string'
54         ]);
55
56         $searchTerm = $request->get('term');
57         $imgData = $this->imageRepo->searchPaginatedByType($type, $page, 24, $searchTerm);
58         return response()->json($imgData);
59     }
60
61     /**
62      * Get all images for a user.
63      * @param int $page
64      * @return \Illuminate\Http\JsonResponse
65      */
66     public function getAllForUserType($page = 0)
67     {
68         $imgData = $this->imageRepo->getPaginatedByType('user', $page, 24, $this->currentUser->id);
69         return response()->json($imgData);
70     }
71
72     /**
73      * Get gallery images with a specific filter such as book or page
74      * @param $filter
75      * @param int $page
76      * @param Request $request
77      * @return \Illuminate\Contracts\Routing\ResponseFactory|\Illuminate\Http\JsonResponse|\Symfony\Component\HttpFoundation\Response
78      */
79     public function getGalleryFiltered($filter, $page = 0, Request $request)
80     {
81         $this->validate($request, [
82             'page_id' => 'required|integer'
83         ]);
84
85         $validFilters = collect(['page', 'book']);
86         if (!$validFilters->contains($filter)) return response('Invalid filter', 500);
87
88         $pageId = $request->get('page_id');
89         $imgData = $this->imageRepo->getGalleryFiltered($page, 24, strtolower($filter), $pageId);
90
91         return response()->json($imgData);
92     }
93
94     /**
95      * Handles image uploads for use on pages.
96      * @param string $type
97      * @param Request $request
98      * @return \Illuminate\Http\JsonResponse
99      * @throws \Exception
100      */
101     public function uploadByType($type, Request $request)
102     {
103         $this->checkPermission('image-create-all');
104         $this->validate($request, [
105             'file' => 'is_image'
106         ]);
107         // TODO - Restrict & validate types
108
109         $imageUpload = $request->file('file');
110
111         try {
112             $uploadedTo = $request->get('uploaded_to', 0);
113             $image = $this->imageRepo->saveNew($imageUpload, $type, $uploadedTo);
114         } catch (ImageUploadException $e) {
115             return response($e->getMessage(), 500);
116         }
117
118         return response()->json($image);
119     }
120
121     /**
122      * Upload a drawing to the system.
123      * @param Request $request
124      * @return \Illuminate\Contracts\Routing\ResponseFactory|\Illuminate\Http\JsonResponse|\Symfony\Component\HttpFoundation\Response
125      */
126     public function uploadDrawing(Request $request)
127     {
128         $this->validate($request, [
129             'image' => 'required|string',
130             'uploaded_to' => 'required|integer'
131         ]);
132         $this->checkPermission('image-create-all');
133         $imageBase64Data = $request->get('image');
134
135         try {
136             $uploadedTo = $request->get('uploaded_to', 0);
137             $image = $this->imageRepo->saveDrawing($imageBase64Data, $uploadedTo);
138         } catch (ImageUploadException $e) {
139             return response($e->getMessage(), 500);
140         }
141
142         return response()->json($image);
143     }
144
145     /**
146      * Replace the data content of a drawing.
147      * @param string $id
148      * @param Request $request
149      * @return \Illuminate\Contracts\Routing\ResponseFactory|\Illuminate\Http\JsonResponse|\Symfony\Component\HttpFoundation\Response
150      */
151     public function replaceDrawing(string $id, Request $request)
152     {
153         $this->validate($request, [
154             'image' => 'required|string'
155         ]);
156         $this->checkPermission('image-create-all');
157
158         $imageBase64Data = $request->get('image');
159         $image = $this->imageRepo->getById($id);
160         $this->checkOwnablePermission('image-update', $image);
161
162         try {
163             $image = $this->imageRepo->replaceDrawingContent($image, $imageBase64Data);
164         } catch (ImageUploadException $e) {
165             return response($e->getMessage(), 500);
166         }
167
168         return response()->json($image);
169     }
170
171     /**
172      * Get the content of an image based64 encoded.
173      * @param $id
174      * @return \Illuminate\Http\JsonResponse|mixed
175      */
176     public function getBase64Image($id)
177     {
178         $image = $this->imageRepo->getById($id);
179         $imageData = $this->imageRepo->getImageData($image);
180         if ($imageData === null) {
181             return $this->jsonError("Image data could not be found");
182         }
183         return response()->json([
184             'content' => base64_encode($imageData)
185         ]);
186     }
187
188     /**
189      * Generate a sized thumbnail for an image.
190      * @param $id
191      * @param $width
192      * @param $height
193      * @param $crop
194      * @return \Illuminate\Http\JsonResponse
195      * @throws ImageUploadException
196      * @throws \Exception
197      */
198     public function getThumbnail($id, $width, $height, $crop)
199     {
200         $this->checkPermission('image-create-all');
201         $image = $this->imageRepo->getById($id);
202         $thumbnailUrl = $this->imageRepo->getThumbnail($image, $width, $height, $crop == 'false');
203         return response()->json(['url' => $thumbnailUrl]);
204     }
205
206     /**
207      * Update image details
208      * @param integer $imageId
209      * @param Request $request
210      * @return \Illuminate\Http\JsonResponse
211      * @throws ImageUploadException
212      * @throws \Exception
213      */
214     public function update($imageId, Request $request)
215     {
216         $this->validate($request, [
217             'name' => 'required|min:2|string'
218         ]);
219         $image = $this->imageRepo->getById($imageId);
220         $this->checkOwnablePermission('image-update', $image);
221         $image = $this->imageRepo->updateImageDetails($image, $request->all());
222         return response()->json($image);
223     }
224
225     /**
226      * Deletes an image and all thumbnail/image files
227      * @param EntityRepo $entityRepo
228      * @param Request $request
229      * @param int $id
230      * @return \Illuminate\Http\JsonResponse
231      */
232     public function destroy(EntityRepo $entityRepo, Request $request, $id)
233     {
234         $image = $this->imageRepo->getById($id);
235         $this->checkOwnablePermission('image-delete', $image);
236
237         // Check if this image is used on any pages
238         $isForced = in_array($request->get('force', ''), [true, 'true']);
239         if (!$isForced) {
240             $pageSearch = $entityRepo->searchForImage($image->url);
241             if ($pageSearch !== false) {
242                 return response()->json($pageSearch, 400);
243             }
244         }
245
246         $this->imageRepo->destroyImage($image);
247         return response()->json(trans('components.images_deleted'));
248     }
249
250
251 }