1
19
20 package com.liferay.portlet.imagegallery.service.impl;
21
22 import com.liferay.portal.PortalException;
23 import com.liferay.portal.SystemException;
24 import com.liferay.portal.kernel.image.ImageProcessor;
25 import com.liferay.portal.kernel.image.ImageProcessorUtil;
26 import com.liferay.portal.kernel.log.Log;
27 import com.liferay.portal.kernel.log.LogFactoryUtil;
28 import com.liferay.portal.kernel.search.SearchException;
29 import com.liferay.portal.kernel.util.ByteArrayMaker;
30 import com.liferay.portal.kernel.util.FileUtil;
31 import com.liferay.portal.kernel.util.GetterUtil;
32 import com.liferay.portal.kernel.util.OrderByComparator;
33 import com.liferay.portal.kernel.util.StringPool;
34 import com.liferay.portal.kernel.util.StringUtil;
35 import com.liferay.portal.kernel.util.Validator;
36 import com.liferay.portal.model.Image;
37 import com.liferay.portal.model.ResourceConstants;
38 import com.liferay.portal.model.User;
39 import com.liferay.portal.util.PropsKeys;
40 import com.liferay.portal.util.PropsUtil;
41 import com.liferay.portal.util.PropsValues;
42 import com.liferay.portlet.imagegallery.DuplicateImageNameException;
43 import com.liferay.portlet.imagegallery.ImageNameException;
44 import com.liferay.portlet.imagegallery.ImageSizeException;
45 import com.liferay.portlet.imagegallery.NoSuchImageException;
46 import com.liferay.portlet.imagegallery.model.IGFolder;
47 import com.liferay.portlet.imagegallery.model.IGImage;
48 import com.liferay.portlet.imagegallery.model.impl.IGImageImpl;
49 import com.liferay.portlet.imagegallery.service.base.IGImageLocalServiceBaseImpl;
50 import com.liferay.portlet.imagegallery.util.Indexer;
51
52 import com.sun.media.jai.codec.ImageCodec;
53 import com.sun.media.jai.codec.ImageEncoder;
54
55 import java.awt.image.RenderedImage;
56
57 import java.io.File;
58 import java.io.IOException;
59
60 import java.util.Date;
61 import java.util.List;
62
63 import javax.imageio.ImageIO;
64
65
71 public class IGImageLocalServiceImpl extends IGImageLocalServiceBaseImpl {
72
73 public IGImage addImage(
74 long userId, long folderId, String name, String description,
75 File file, String contentType, String[] tagsEntries,
76 boolean addCommunityPermissions, boolean addGuestPermissions)
77 throws PortalException, SystemException {
78
79 return addImage(
80 null, userId, folderId, name, description, file, contentType,
81 tagsEntries, Boolean.valueOf(addCommunityPermissions),
82 Boolean.valueOf(addGuestPermissions), null, null);
83 }
84
85 public IGImage addImage(
86 String uuid, long userId, long folderId, String name,
87 String description, File file, String contentType,
88 String[] tagsEntries, boolean addCommunityPermissions,
89 boolean addGuestPermissions)
90 throws PortalException, SystemException {
91
92 return addImage(
93 uuid, userId, folderId, name, description, file, contentType,
94 tagsEntries, Boolean.valueOf(addCommunityPermissions),
95 Boolean.valueOf(addGuestPermissions), null, null);
96 }
97
98 public IGImage addImage(
99 long userId, long folderId, String name, String description,
100 File file, String contentType, String[] tagsEntries,
101 String[] communityPermissions, String[] guestPermissions)
102 throws PortalException, SystemException {
103
104 return addImage(
105 null, userId, folderId, name, description, file, contentType,
106 tagsEntries, null, null, communityPermissions, guestPermissions);
107 }
108
109 public IGImage addImage(
110 String uuid, long userId, long folderId, String name,
111 String description, File file, String contentType,
112 String[] tagsEntries, Boolean addCommunityPermissions,
113 Boolean addGuestPermissions, String[] communityPermissions,
114 String[] guestPermissions)
115 throws PortalException, SystemException {
116
117 try {
118
119
121 String extension = FileUtil.getExtension(file.getName());
122
123 if (Validator.isNotNull(name) &&
124 StringUtil.endsWith(name, extension)) {
125
126 name = FileUtil.stripExtension(name);
127 }
128
129 String nameWithExtension = name + StringPool.PERIOD + extension;
130 byte[] bytes = FileUtil.getBytes(file);
131
132 validate(folderId, nameWithExtension, file, bytes);
133
134 User user = userPersistence.findByPrimaryKey(userId);
135 IGFolder folder = igFolderPersistence.findByPrimaryKey(folderId);
136 RenderedImage renderedImage = ImageProcessorUtil.read(
137 file).getRenderedImage();
138 Date now = new Date();
139
140 long imageId = counterLocalService.increment();
141
142 if (Validator.isNull(name)) {
143 name = String.valueOf(imageId);
144 }
145
146 IGImage image = igImagePersistence.create(imageId);
147
148 image.setUuid(uuid);
149 image.setCompanyId(user.getCompanyId());
150 image.setUserId(user.getUserId());
151 image.setCreateDate(now);
152 image.setModifiedDate(now);
153 image.setFolderId(folderId);
154 image.setName(name);
155 image.setDescription(description);
156 image.setSmallImageId(counterLocalService.increment());
157 image.setLargeImageId(counterLocalService.increment());
158
159 if (PropsValues.IG_IMAGE_CUSTOM_1_MAX_DIMENSION > 0) {
160 image.setCustom1ImageId(counterLocalService.increment());
161 }
162
163 if (PropsValues.IG_IMAGE_CUSTOM_2_MAX_DIMENSION > 0) {
164 image.setCustom2ImageId(counterLocalService.increment());
165 }
166
167 igImagePersistence.update(image, false);
168
169
171 saveImages(
172 image.getLargeImageId(), renderedImage, image.getSmallImageId(),
173 image.getCustom1ImageId(), image.getCustom2ImageId(), file,
174 bytes, contentType);
175
176
178 if ((addCommunityPermissions != null) &&
179 (addGuestPermissions != null)) {
180
181 addImageResources(
182 folder, image, addCommunityPermissions.booleanValue(),
183 addGuestPermissions.booleanValue());
184 }
185 else {
186 addImageResources(
187 folder, image, communityPermissions, guestPermissions);
188 }
189
190
192 updateTagsAsset(userId, image, tagsEntries);
193
194
196 try {
197 Indexer.addImage(
198 image.getCompanyId(), folder.getGroupId(), folderId,
199 imageId, name, description, image.getModifiedDate(),
200 tagsEntries);
201 }
202 catch (SearchException se) {
203 _log.error("Indexing " + imageId, se);
204 }
205
206 return image;
207 }
208 catch (IOException ioe) {
209 throw new ImageSizeException(ioe);
210 }
211 }
212
213 public void addImageResources(
214 long folderId, long imageId, boolean addCommunityPermissions,
215 boolean addGuestPermissions)
216 throws PortalException, SystemException {
217
218 IGFolder folder = igFolderPersistence.findByPrimaryKey(folderId);
219 IGImage image = igImagePersistence.findByPrimaryKey(imageId);
220
221 addImageResources(
222 folder, image, addCommunityPermissions, addGuestPermissions);
223 }
224
225 public void addImageResources(
226 IGFolder folder, IGImage image, boolean addCommunityPermissions,
227 boolean addGuestPermissions)
228 throws PortalException, SystemException {
229
230 resourceLocalService.addResources(
231 image.getCompanyId(), folder.getGroupId(), image.getUserId(),
232 IGImage.class.getName(), image.getImageId(), false,
233 addCommunityPermissions, addGuestPermissions);
234 }
235
236 public void addImageResources(
237 long folderId, long imageId, String[] communityPermissions,
238 String[] guestPermissions)
239 throws PortalException, SystemException {
240
241 IGFolder folder = igFolderPersistence.findByPrimaryKey(folderId);
242 IGImage image = igImagePersistence.findByPrimaryKey(imageId);
243
244 addImageResources(
245 folder, image, communityPermissions, guestPermissions);
246 }
247
248 public void addImageResources(
249 IGFolder folder, IGImage image, String[] communityPermissions,
250 String[] guestPermissions)
251 throws PortalException, SystemException {
252
253 resourceLocalService.addModelResources(
254 image.getCompanyId(), folder.getGroupId(), image.getUserId(),
255 IGImage.class.getName(), image.getImageId(), communityPermissions,
256 guestPermissions);
257 }
258
259 public void deleteImage(long imageId)
260 throws PortalException, SystemException {
261
262 IGImage image = igImagePersistence.findByPrimaryKey(imageId);
263
264 deleteImage(image);
265 }
266
267 public void deleteImage(IGImage image)
268 throws PortalException, SystemException {
269
270
272 try {
273 Indexer.deleteImage(image.getCompanyId(), image.getImageId());
274 }
275 catch (SearchException se) {
276 _log.error("Deleting index " + image.getImageId(), se);
277 }
278
279
281 tagsAssetLocalService.deleteAsset(
282 IGImage.class.getName(), image.getImageId());
283
284
286 resourceLocalService.deleteResource(
287 image.getCompanyId(), IGImage.class.getName(),
288 ResourceConstants.SCOPE_INDIVIDUAL, image.getImageId());
289
290
292 imageLocalService.deleteImage(image.getSmallImageId());
293 imageLocalService.deleteImage(image.getLargeImageId());
294
295
297 igImagePersistence.remove(image);
298 }
299
300 public void deleteImages(long folderId)
301 throws PortalException, SystemException {
302
303 List<IGImage> images = igImagePersistence.findByFolderId(folderId);
304
305 for (IGImage image : images) {
306 deleteImage(image);
307 }
308 }
309
310 public int getFoldersImagesCount(List<Long> folderIds)
311 throws SystemException {
312
313 return igImageFinder.countByFolderIds(folderIds);
314 }
315
316 public List<IGImage> getGroupImages(long groupId, int start, int end)
317 throws SystemException {
318
319 return igImageFinder.findByGroupId(groupId, start, end);
320 }
321
322 public List<IGImage> getGroupImages(
323 long groupId, long userId, int start, int end)
324 throws SystemException {
325
326 if (userId <= 0) {
327 return igImageFinder.findByGroupId(groupId, start, end);
328 }
329 else {
330 return igImageFinder.findByG_U(groupId, userId, start, end);
331 }
332 }
333
334 public int getGroupImagesCount(long groupId) throws SystemException {
335 return igImageFinder.countByGroupId(groupId);
336 }
337
338 public int getGroupImagesCount(long groupId, long userId)
339 throws SystemException {
340
341 if (userId <= 0) {
342 return igImageFinder.countByGroupId(groupId);
343 }
344 else {
345 return igImageFinder.countByG_U(groupId, userId);
346 }
347 }
348
349 public IGImage getImage(long imageId)
350 throws PortalException, SystemException {
351
352 return igImagePersistence.findByPrimaryKey(imageId);
353 }
354
355 public IGImage getImageByCustom1ImageId(long custom1ImageId)
356 throws PortalException, SystemException {
357
358 return igImagePersistence.findByCustom1ImageId(custom1ImageId);
359 }
360
361 public IGImage getImageByCustom2ImageId(long custom2ImageId)
362 throws PortalException, SystemException {
363
364 return igImagePersistence.findByCustom2ImageId(custom2ImageId);
365 }
366
367 public IGImage getImageByFolderIdAndNameWithExtension(
368 long folderId, String nameWithExtension)
369 throws PortalException, SystemException {
370
371 String name = FileUtil.stripExtension(nameWithExtension);
372
373 List<IGImage> images = igImagePersistence.findByF_N(folderId, name);
374
375 if ((images.size() <= 0) && Validator.isNumber(name)) {
376 long imageId = GetterUtil.getLong(name);
377
378 IGImage image = igImagePersistence.fetchByPrimaryKey(imageId);
379
380 if (image != null) {
381 images.add(image);
382 }
383 }
384
385 for (IGImage image : images) {
386 if (nameWithExtension.equals(image.getNameWithExtension())) {
387 return image;
388 }
389 }
390
391 throw new NoSuchImageException();
392 }
393
394 public IGImage getImageByLargeImageId(long largeImageId)
395 throws PortalException, SystemException {
396
397 return igImagePersistence.findByLargeImageId(largeImageId);
398 }
399
400 public IGImage getImageBySmallImageId(long smallImageId)
401 throws PortalException, SystemException {
402
403 return igImagePersistence.findBySmallImageId(smallImageId);
404 }
405
406 public IGImage getImageByUuidAndGroupId(String uuid, long groupId)
407 throws PortalException, SystemException {
408
409 return igImageFinder.findByUuid_G(uuid, groupId);
410 }
411
412 public List<IGImage> getImages(long folderId) throws SystemException {
413 return igImagePersistence.findByFolderId(folderId);
414 }
415
416 public List<IGImage> getImages(long folderId, int start, int end)
417 throws SystemException {
418
419 return igImagePersistence.findByFolderId(folderId, start, end);
420 }
421
422 public List<IGImage> getImages(
423 long folderId, int start, int end, OrderByComparator obc)
424 throws SystemException {
425
426 return igImagePersistence.findByFolderId(folderId, start, end, obc);
427 }
428
429 public int getImagesCount(long folderId) throws SystemException {
430 return igImagePersistence.countByFolderId(folderId);
431 }
432
433 public List<IGImage> getNoAssetImages() throws SystemException {
434 return igImageFinder.findByNoAssets();
435 }
436
437 public IGImage updateImage(
438 long userId, long imageId, long folderId, String name,
439 String description, File file, String contentType,
440 String[] tagsEntries)
441 throws PortalException, SystemException {
442
443 try {
444
445
447 IGImage image = igImagePersistence.findByPrimaryKey(imageId);
448
449 IGFolder folder = getFolder(image, folderId);
450
451 RenderedImage renderedImage = null;
452 byte[] bytes = null;
453
454 if ((file != null) && file.exists()) {
455 renderedImage = ImageProcessorUtil.read(
456 file).getRenderedImage();
457 bytes = FileUtil.getBytes(file);
458
459 validate(bytes);
460 }
461
462 if (Validator.isNotNull(name) && !name.equals(image.getName())) {
463 String nameWithExtension = IGImageImpl.getNameWithExtension(
464 name, image.getImageType());
465
466 validate(folderId, nameWithExtension);
467 }
468 else {
469 name = image.getName();
470 }
471
472 image.setModifiedDate(new Date());
473 image.setFolderId(folder.getFolderId());
474 image.setName(name);
475 image.setDescription(description);
476
477 igImagePersistence.update(image, false);
478
479
481 if (renderedImage != null) {
482 saveImages(
483 image.getLargeImageId(), renderedImage,
484 image.getSmallImageId(), image.getCustom1ImageId(),
485 image.getCustom2ImageId(), file, bytes, contentType);
486 }
487
488
490 updateTagsAsset(userId, image, tagsEntries);
491
492
494 try {
495 Indexer.updateImage(
496 image.getCompanyId(), folder.getGroupId(),
497 folder.getFolderId(), imageId, name, description,
498 image.getModifiedDate(), tagsEntries);
499 }
500 catch (SearchException se) {
501 _log.error("Indexing " + imageId, se);
502 }
503
504 return image;
505 }
506 catch (IOException ioe) {
507 throw new ImageSizeException(ioe);
508 }
509 }
510
511 public void updateTagsAsset(
512 long userId, IGImage image, String[] tagsEntries)
513 throws PortalException, SystemException {
514
515 Image largeImage = imageLocalService.getImage(image.getLargeImageId());
516
517 if (largeImage == null) {
518 return;
519 }
520
521 tagsAssetLocalService.updateAsset(
522 userId, image.getFolder().getGroupId(), IGImage.class.getName(),
523 image.getImageId(), tagsEntries, null, null, null, null,
524 largeImage.getType(), image.getName(), image.getDescription(),
525 null, null, largeImage.getHeight(), largeImage.getWidth(), null,
526 false);
527 }
528
529 protected IGFolder getFolder(IGImage image, long folderId)
530 throws PortalException, SystemException {
531
532 if (image.getFolderId() != folderId) {
533 IGFolder oldFolder = igFolderPersistence.findByPrimaryKey(
534 image.getFolderId());
535
536 IGFolder newFolder = igFolderPersistence.fetchByPrimaryKey(
537 folderId);
538
539 if ((newFolder == null) ||
540 (oldFolder.getGroupId() != newFolder.getGroupId())) {
541
542 folderId = image.getFolderId();
543 }
544 }
545
546 return igFolderPersistence.findByPrimaryKey(folderId);
547 }
548
549 protected void saveImages(
550 long largeImageId, RenderedImage renderedImage, long smallImageId,
551 long custom1ImageId, long custom2ImageId, File file, byte[] bytes,
552 String contentType)
553 throws SystemException {
554
555 try {
556
557
559 imageLocalService.updateImage(largeImageId, bytes);
560
561
563 saveScaledImage(
564 renderedImage, smallImageId, contentType,
565 PropsValues.IG_IMAGE_THUMBNAIL_MAX_DIMENSION);
566
567 if (custom1ImageId > 0) {
568 saveScaledImage(
569 renderedImage, custom1ImageId, contentType,
570 PropsValues.IG_IMAGE_CUSTOM_1_MAX_DIMENSION);
571 }
572
573 if (custom2ImageId > 0) {
574 saveScaledImage(
575 renderedImage, custom2ImageId, contentType,
576 PropsValues.IG_IMAGE_CUSTOM_2_MAX_DIMENSION);
577 }
578 }
579 catch (IOException ioe) {
580 throw new SystemException(ioe);
581 }
582 }
583
584 protected void saveScaledImage(
585 RenderedImage renderedImage, long imageId, String contentType,
586 int dimension)
587 throws IOException, SystemException {
588
589 RenderedImage thumbnail = ImageProcessorUtil.scale(
590 renderedImage, dimension, dimension);
591
592 ByteArrayMaker bam = new ByteArrayMaker();
593
594 if (contentType.indexOf("bmp") != -1) {
595 ImageEncoder encoder = ImageCodec.createImageEncoder(
596 "BMP", bam, null);
597
598 encoder.encode(thumbnail);
599 }
600 else if (contentType.indexOf("gif") != -1) {
601 ImageProcessorUtil.encodeGIF(thumbnail, bam);
602 }
603 else if (contentType.indexOf("jpg") != -1 ||
604 contentType.indexOf("jpeg") != -1) {
605
606 ImageIO.write(thumbnail, "jpeg", bam);
607 }
608 else if (contentType.indexOf("png") != -1) {
609 ImageIO.write(thumbnail, "png", bam);
610 }
611 else if (contentType.indexOf("tif") != -1) {
612 ImageEncoder encoder = ImageCodec.createImageEncoder(
613 "TIFF", bam, null);
614
615 encoder.encode(thumbnail);
616 }
617
618 imageLocalService.updateImage(imageId, bam.toByteArray());
619 }
620
621 protected void validate(byte[] bytes) throws ImageSizeException {
622 if ((PropsValues.IG_IMAGE_MAX_SIZE > 0) &&
623 ((bytes == null) ||
624 (bytes.length > PropsValues.IG_IMAGE_MAX_SIZE))) {
625
626 throw new ImageSizeException();
627 }
628 }
629
630 protected void validate(long folderId, String nameWithExtension)
631 throws PortalException, SystemException {
632
633 if ((nameWithExtension.indexOf("\\\\") != -1) ||
634 (nameWithExtension.indexOf("//") != -1) ||
635 (nameWithExtension.indexOf(":") != -1) ||
636 (nameWithExtension.indexOf("*") != -1) ||
637 (nameWithExtension.indexOf("?") != -1) ||
638 (nameWithExtension.indexOf("\"") != -1) ||
639 (nameWithExtension.indexOf("<") != -1) ||
640 (nameWithExtension.indexOf(">") != -1) ||
641 (nameWithExtension.indexOf("|") != -1) ||
642 (nameWithExtension.indexOf("&") != -1) ||
643 (nameWithExtension.indexOf("[") != -1) ||
644 (nameWithExtension.indexOf("]") != -1) ||
645 (nameWithExtension.indexOf("'") != -1)) {
646
647 throw new ImageNameException();
648 }
649
650 boolean validImageExtension = false;
651
652 String[] imageExtensions =
653 PropsUtil.getArray(PropsKeys.IG_IMAGE_EXTENSIONS);
654
655 for (int i = 0; i < imageExtensions.length; i++) {
656 if (StringPool.STAR.equals(imageExtensions[i]) ||
657 StringUtil.endsWith(nameWithExtension, imageExtensions[i])) {
658
659 validImageExtension = true;
660
661 break;
662 }
663 }
664
665 if (!validImageExtension) {
666 throw new ImageNameException();
667 }
668
669 String name = FileUtil.stripExtension(nameWithExtension);
670 String imageType = FileUtil.getExtension(nameWithExtension);
671
672 List<IGImage> images = igImagePersistence.findByF_N(folderId, name);
673
674 if (imageType.equals("jpeg")) {
675 imageType = ImageProcessor.TYPE_JPEG;
676 }
677 else if (imageType.equals("tif")) {
678 imageType = ImageProcessor.TYPE_TIFF;
679 }
680
681 for (IGImage image : images) {
682 if (imageType.equals(image.getImageType())) {
683 throw new DuplicateImageNameException();
684 }
685 }
686 }
687
688 protected void validate(
689 long folderId, String nameWithExtension, File file, byte[] bytes)
690 throws PortalException, SystemException {
691
692 if (file != null) {
693 String fileName = file.getName();
694 String extension = FileUtil.getExtension(fileName);
695
696 if (Validator.isNull(nameWithExtension)) {
697 nameWithExtension = fileName;
698 }
699 else if (!StringUtil.endsWith(nameWithExtension, extension)) {
700 throw new ImageNameException();
701 }
702 }
703
704 validate(folderId, nameWithExtension);
705 validate(bytes);
706 }
707
708 private static Log _log =
709 LogFactoryUtil.getLog(IGImageLocalServiceImpl.class);
710
711 }