2 * Meviz - Various tools collection to work with multimedia.
3 * Copyright (C) 2012, Svjatoslav Agejenko, svjatoslav@svjatoslav.eu
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of version 2 of the GNU General Public License
7 * as published by the Free Software Foundation.
10 package eu.svjatoslav.meviz.htmlindexer;
13 import java.io.FileNotFoundException;
14 import java.io.IOException;
15 import java.io.UnsupportedEncodingException;
16 import java.util.ArrayList;
17 import java.util.HashSet;
18 import java.util.List;
20 import org.apache.log4j.Logger;
22 import eu.svjatoslav.commons.file.IOHelper;
23 import eu.svjatoslav.commons.network.UrlParamEncoder;
24 import eu.svjatoslav.meviz.htmlindexer.metadata.Dimension;
25 import eu.svjatoslav.meviz.htmlindexer.metadata.DirectoryMetadata;
26 import eu.svjatoslav.meviz.htmlindexer.metadata.MetadadaHelper;
27 import eu.svjatoslav.meviz.htmlindexer.metadata.fileTypes.AbstractFile;
28 import eu.svjatoslav.meviz.htmlindexer.metadata.fileTypes.DirectoryFile;
29 import eu.svjatoslav.meviz.htmlindexer.metadata.fileTypes.GeneralFile;
30 import eu.svjatoslav.meviz.htmlindexer.metadata.fileTypes.Picture;
33 * Main class of HTML indexer.
36 public class FilesystemIndexer extends AbstractIndexer {
38 public static final Logger logger = Logger
39 .getLogger(FilesystemIndexer.class);
41 private final HashSet<String> validMetadataFiles = new HashSet<String>();
43 private final File directoryToIndex;
45 private String thumbnailsPath;
47 private File metadataFile;
49 private DirectoryMetadata metadata;
51 private final List<String> pathElements;
53 private HashSet<Layout> layouts;
55 private final CommandlineHandler commandlineHandler;
57 public FilesystemIndexer(final File directoryToIndex,
58 final CommandlineHandler commandlineHandler,
59 final List<String> pathElements) throws IOException,
62 this.directoryToIndex = directoryToIndex;
63 this.commandlineHandler = commandlineHandler;
64 this.pathElements = pathElements;
66 if (!directoryToIndex.canRead())
69 validMetadataFiles.add(Constants.METADATA_FILE_NAME);
71 initializeThumbnailsDirectory();
72 loadOrCreateMetadata();
78 metadata.removeUnusedMetadataEntries();
80 generateHtmlFromMetadata(layouts);
82 removeUnusedThumbnailFiles();
84 // save directory metadata
86 MetadadaHelper.saveDirectoryMetadata(metadataFile, metadata);
90 public boolean canWriteIndexFile(final File indexFile)
91 throws FileNotFoundException, IOException {
93 if (!indexFile.exists())
96 return Utils.isMevizGeneratedIndexFile(indexFile);
99 public void cleanupUnusedMetadataFiles() {
100 final File thumbnailsDirectory = new File(thumbnailsPath);
102 for (final File file : thumbnailsDirectory.listFiles())
103 if (!validMetadataFiles.contains(file.getName()))
107 public void generateHtmlFromMetadata(final HashSet<Layout> layouts) {
108 // Generate HTML from metadata
109 for (final Layout layout : layouts)
111 final File indexFile = Utils.getLayoutIndexFile(layout,
114 if (canWriteIndexFile(indexFile)) {
116 indexForLayout(layout);
118 IOHelper.overwriteFileIfContentDiffers(indexFile, layout
119 .getHtml(true, true).getBytes());
121 } catch (final Exception e) {
122 logger.error("Error writing index file. ", e);
126 public List<String> getChildPath(final File file) {
128 final List<String> result = new ArrayList<String>();
129 result.addAll(pathElements);
130 result.add(file.getName());
136 public String getDirectoryUrl(final AbstractFile directory,
137 final IndexingContext context) {
138 return directory.fileName + "/index.html";
142 public String getParentDirectoryUrl(final IndexingContext context) {
143 return "../index.html";
147 public String getThumbnailUrl(final Picture picture,
148 final Dimension desiredDimension, final IndexingContext context) {
150 // in case thumbnail size was equal to original, then return original
152 if (picture.getDimensions().equals(desiredDimension))
153 return picture.fileName;
155 final String thumbnailFileName = picture
156 .getRelativeThumbnailFileName(desiredDimension);
158 validMetadataFiles.add(thumbnailFileName);
159 final File thumbnailFile = new File(thumbnailsPath + thumbnailFileName);
161 if (!thumbnailFile.exists()) {
163 final File originalFile = new File(
164 directoryToIndex.getAbsolutePath() + "/" + picture.fileName);
166 // generate new thumbnail
167 Picture.makeThumbnail(originalFile, thumbnailFile,
168 desiredDimension.getAwtDimension());
170 return Constants.THUMBNAILS_DIRECTORY_NAME + "/"
171 + UrlParamEncoder.encode(thumbnailFileName);
174 public void indexForLayout(final Layout layout)
175 throws UnsupportedEncodingException {
177 for (final AbstractFile abstractFile : metadata.getFiles())
178 if (abstractFile instanceof GeneralFile) {
180 if (isOgv(abstractFile.getFileExtension()))
181 layout.enlistOgv(abstractFile);
183 layout.enlistFile(abstractFile);
185 } else if (abstractFile instanceof Picture)
186 layout.enlistImage(abstractFile);
187 else if (abstractFile instanceof DirectoryFile)
188 layout.enlistDirectory(abstractFile);
192 public void initializeLayouts() {
194 layouts = Utils.getLayouts();
196 final String galleryTitle = commandlineHandler.getGalleryTitle();
198 for (final Layout layout : layouts)
199 layout.init(galleryTitle, pathElements, this, new IndexingContext(
203 public void initializeThumbnailsDirectory() {
204 final File thumbnailsDirectory = Utils
205 .getThumbnailsDirectory(directoryToIndex);
207 if (!thumbnailsDirectory.exists())
208 thumbnailsDirectory.mkdirs();
211 public void loadOrCreateMetadata() {
212 metadataFile = new File(thumbnailsPath + Constants.METADATA_FILE_NAME);
214 metadata = MetadadaHelper.initDirectoryMetadata(metadataFile);
217 private void removeUnusedThumbnailFiles() {
219 final File thumbnailsDirectory = new File(thumbnailsPath);
221 for (final File file : thumbnailsDirectory.listFiles())
222 if (!validMetadataFiles.contains(file.getName()))
227 public void updateMetadata() throws IOException, ImageFormatError {
229 final File[] directoryContent = directoryToIndex.listFiles();
231 for (final File file : directoryContent)
232 if (shallFileBeIndexed(file)) {
234 metadata.ensureFileMetainfoIsUpToDate(directoryToIndex, file);
236 if (file.isDirectory())
237 new FilesystemIndexer(file, commandlineHandler,