2 * Copyright (c) 2000-2009 Liferay, Inc. All rights reserved.
\r
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
\r
5 * of this software and associated documentation files (the "Software"), to deal
\r
6 * in the Software without restriction, including without limitation the rights
\r
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
\r
8 * copies of the Software, and to permit persons to whom the Software is
\r
9 * furnished to do so, subject to the following conditions:
\r
11 * The above copyright notice and this permission notice shall be included in
\r
12 * all copies or substantial portions of the Software.
\r
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
\r
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
\r
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
\r
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
\r
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
\r
19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
\r
23 package com.liferay.portlet.documentlibrary.util;
\r
25 import java.io.BufferedReader;
\r
26 import java.io.ByteArrayInputStream;
\r
27 import java.io.ByteArrayOutputStream;
\r
28 import java.io.File;
\r
29 import java.io.FileInputStream;
\r
30 import java.io.IOException;
\r
31 import java.io.InputStream;
\r
32 import java.io.InputStreamReader;
\r
33 import java.security.MessageDigest;
\r
34 import java.util.ArrayList;
\r
35 import java.util.HashMap;
\r
36 import java.util.List;
\r
37 import java.util.Map;
\r
38 import java.util.regex.Matcher;
\r
39 import java.util.regex.Pattern;
\r
43 import com.artofsolving.jodconverter.DefaultDocumentFormatRegistry;
\r
44 import com.artofsolving.jodconverter.DocumentConverter;
\r
45 import com.artofsolving.jodconverter.DocumentFormat;
\r
46 import com.artofsolving.jodconverter.DocumentFormatRegistry;
\r
47 import com.artofsolving.jodconverter.openoffice.connection.OpenOfficeConnection;
\r
48 import com.artofsolving.jodconverter.openoffice.connection.SocketOpenOfficeConnection;
\r
49 import com.artofsolving.jodconverter.openoffice.converter.OpenOfficeDocumentConverter;
\r
50 import com.artofsolving.jodconverter.openoffice.converter.StreamOpenOfficeDocumentConverter;
\r
51 import com.liferay.portal.kernel.configuration.Filter;
\r
52 import com.liferay.portal.kernel.exception.PortalException;
\r
53 import com.liferay.portal.kernel.exception.SystemException;
\r
54 import com.liferay.portal.kernel.log.Log;
\r
55 import com.liferay.portal.kernel.log.LogFactoryUtil;
\r
56 import com.liferay.portal.kernel.util.ArrayUtil;
\r
57 import com.liferay.portal.kernel.util.Base64;
\r
58 import com.liferay.portal.kernel.util.FileUtil;
\r
59 import com.liferay.portal.kernel.util.MimeTypesOverrideUtil;
\r
60 import com.liferay.portal.kernel.util.PropsKeys;
\r
61 import com.liferay.portal.kernel.util.SortedArrayList;
\r
62 import com.liferay.portal.kernel.util.StringBundler;
\r
63 import com.liferay.portal.kernel.util.StringPool;
\r
64 import com.liferay.portal.kernel.util.SystemProperties;
\r
65 import com.liferay.portal.kernel.util.Validator;
\r
66 import com.liferay.portal.model.CompanyConstants;
\r
67 import com.liferay.portal.service.CompanyLocalServiceUtil;
\r
68 import com.liferay.portal.util.PrefsPropsUtil;
\r
69 import com.liferay.portal.util.PropsUtil;
\r
70 import com.liferay.portal.util.PropsValues;
\r
71 import com.liferay.portlet.documentlibrary.conversion.util.ENTDocumentConversionService;
\r
72 import com.liferay.portlet.documentlibrary.conversion.util.ENTDocumentConversionServiceUtil;
\r
73 import com.liferay.portlet.documentlibrary.store.DLStoreUtil;
\r
74 import com.pentila.entSavoie.utils.ENTMainUtilsLocalServiceUtil;
\r
77 * <a href="DocumentConversionUtil.java.html"><b><i>View Source</i></b></a>
\r
79 * @author Bruno Farache
\r
82 public class ENTDocumentConversionUtil implements ENTDocumentConversionService {
\r
84 static Map<String, String> convertState = new HashMap<String, String>();
\r
85 static Map<String, Process> convertProcess = new HashMap<String, Process>();
\r
87 public File convert(
\r
88 String id, InputStream is, String sourceExtension,
\r
89 String targetExtension)
\r
90 throws IOException, SystemException {
\r
91 Map<String, String> parameters = new HashMap<String, String>();
\r
92 return this.convert(id, is, sourceExtension, targetExtension, parameters);
\r
95 public File convert(
\r
96 String id, InputStream is, String sourceExtension,
\r
97 String targetExtension, Map<String, String> parameters)
\r
98 throws IOException, SystemException {
\r
99 return _instance._convert(id, is, sourceExtension, targetExtension, parameters);
\r
102 public void disconnect() {
\r
103 _instance._disconnect();
\r
106 public static String[] getConversions(String extension) {
\r
107 return _instance._getConversions(extension);
\r
110 public static boolean isComparableVersion(String extension) {
\r
111 boolean enabled = false;
\r
113 String dotExtension = StringPool.PERIOD + extension;
\r
115 for (int i = 0; i < _COMPARABLE_FILE_EXTENSIONS.length; i++) {
\r
116 if (StringPool.STAR.equals(_COMPARABLE_FILE_EXTENSIONS[i]) ||
\r
117 dotExtension.equals(_COMPARABLE_FILE_EXTENSIONS[i])) {
\r
128 if (extension.equals("css") || extension.equals("js") ||
\r
129 extension.equals("htm") || extension.equals("html") ||
\r
130 extension.equals("txt") || extension.equals("xml")) {
\r
136 if (isEnabled() && isConvertBeforeCompare(extension)) {
\r
140 catch (Exception e) {
\r
141 if (_log.isErrorEnabled()) {
\r
149 public static boolean isConvertBeforeCompare(String extension) {
\r
150 if (extension.equals("txt")) {
\r
154 String[] conversions = getConversions(extension);
\r
156 for (int i = 0; i < conversions.length; i++) {
\r
157 if (conversions[i].equals("txt")) {
\r
165 public static boolean isEnabled() {
\r
167 return PrefsPropsUtil.getBoolean(
\r
168 PropsKeys.OPENOFFICE_SERVER_ENABLED,
\r
169 PropsValues.OPENOFFICE_SERVER_ENABLED);
\r
171 catch (Exception e) {
\r
178 * Return target file as inputStream
\r
181 * @param targetExtension
\r
184 * @throws PortalException
\r
185 * @throws SystemException
\r
186 * @throws IOException
\r
188 public Map<String, Object> getFileAsInputStream(String path, long companyId, String targetExtension, String fileName) throws PortalException, SystemException, IOException {
\r
189 Map<String, Object> result = new HashMap<String, Object>();
\r
191 // Dans cette methode is n'est pas ferné car on doit le faire dans la methode qui appelle, generalement getFile par un strut
\r
192 InputStream is = null;
\r
193 InputStream convertedIS = null;
\r
194 InputStream isToConvert = null;
\r
197 int contentLength = (int) DLStoreUtil.getFileSize(companyId, CompanyConstants.SYSTEM, path);
\r
199 if (Validator.isNotNull(targetExtension)) {
\r
200 InputStream isForId = DLStoreUtil.getFileAsStream(
\r
201 companyId, CompanyConstants.SYSTEM, path);
\r
202 String idSecure = ENTDocumentConversionServiceUtil.getFileChecksum(isForId);
\r
205 isToConvert = DLStoreUtil.getFileAsStream(
\r
206 companyId, CompanyConstants.SYSTEM, path);
\r
208 String sourceExtension = FileUtil.getExtension(fileName);
\r
210 File file = ENTDocumentConversionServiceUtil.convert(
\r
211 idSecure, isToConvert, sourceExtension, targetExtension);
\r
212 convertedIS = new FileInputStream(file);
\r
213 contentLength = (int) file.length();
\r
215 StringBuilder sb = new StringBuilder();
\r
216 sb.append(fileName);
\r
217 sb.append(StringPool.PERIOD);
\r
218 sb.append(targetExtension);
\r
219 fileName = sb.toString();
\r
223 } catch (Exception e){
\r
224 File f = new File(ENTMainUtilsLocalServiceUtil.getFileErrorFlv(companyId));
\r
225 fileName = "error.txt";
\r
226 is = new FileInputStream(f);
\r
227 contentLength = (int) f.length();
\r
230 isToConvert.close();
\r
234 is = DLStoreUtil.getFileAsStream(
\r
235 companyId, CompanyConstants.SYSTEM, path);
\r
238 String contentType = MimeTypesOverrideUtil.getContentType(fileName);
\r
241 result.put("contentType", contentType);
\r
242 result.put("contentLength", contentLength);
\r
243 result.put("fileName", fileName);
\r
244 result.put("stream", is);
\r
248 catch(Exception exc) {
\r
249 if (isToConvert!=null) {
\r
250 isToConvert.close();
\r
255 f = new File(ENTMainUtilsLocalServiceUtil.getFileErrorFlv(companyId));
\r
256 fileName = "error.txt";
\r
257 is = new FileInputStream(f);
\r
259 result.put("contentType", MimeTypesOverrideUtil.getContentType(fileName));
\r
260 result.put("contentLength", (int) f.length());
\r
261 result.put("fileName", fileName);
\r
262 result.put("stream", is);
\r
270 public String getFileChecksum(InputStream is) {
\r
274 MessageDigest md = MessageDigest.getInstance("MD5");
\r
275 byte[] dataBytes = new byte[1024];
\r
279 while ((nread = is.read(dataBytes)) != -1) {
\r
280 md.update(dataBytes, 0, nread);
\r
283 byte[] mdbytes = md.digest();
\r
285 //convert the byte to hex format
\r
286 StringBuffer sb = new StringBuffer("");
\r
287 for (int i = 0; i < mdbytes.length; i++) {
\r
288 sb.append(Integer.toString((mdbytes[i] & 0xFF), 16).substring(1));
\r
291 return sb.toString();
\r
292 } catch (Exception e) {
\r
299 public String getTempFileId(String id, double version) {
\r
300 StringBuilder sb = new StringBuilder();
\r
303 sb.append(StringPool.PERIOD);
\r
304 sb.append(version);
\r
306 return sb.toString();
\r
309 private ENTDocumentConversionUtil() {
\r
310 _conversionsMap.put("svg", _DRAWING_CONVERSIONS);
\r
311 _conversionsMap.put("swf", _DRAWING_CONVERSIONS);
\r
313 _conversionsMap.put("odp", _PRESENTATION_CONVERSIONS);
\r
314 _conversionsMap.put("ppt", _PRESENTATION_CONVERSIONS);
\r
315 _conversionsMap.put("sxi", _PRESENTATION_CONVERSIONS);
\r
316 _conversionsMap.put("pptx", _PRESENTATION_CONVERSIONS);
\r
318 _conversionsMap.put("csv", _SPREADSHEET_CONVERSIONS);
\r
319 _conversionsMap.put("ods", _SPREADSHEET_CONVERSIONS);
\r
320 _conversionsMap.put("sxc", _SPREADSHEET_CONVERSIONS);
\r
321 _conversionsMap.put("tsv", _SPREADSHEET_CONVERSIONS);
\r
322 _conversionsMap.put("xls", _SPREADSHEET_CONVERSIONS);
\r
323 _conversionsMap.put("xlsx", _SPREADSHEET_CONVERSIONS);
\r
325 _conversionsMap.put("doc", _TEXT_CONVERSIONS);
\r
326 _conversionsMap.put("htm", _TEXT_CONVERSIONS);
\r
327 _conversionsMap.put("html", _TEXT_CONVERSIONS);
\r
328 _conversionsMap.put("odt", _TEXT_CONVERSIONS);
\r
329 _conversionsMap.put("rtf", _TEXT_CONVERSIONS);
\r
330 _conversionsMap.put("sxw", _TEXT_CONVERSIONS);
\r
331 _conversionsMap.put("txt", _TEXT_CONVERSIONS);
\r
332 _conversionsMap.put("wpd", _TEXT_CONVERSIONS);
\r
333 _conversionsMap.put("docx", _TEXT_CONVERSIONS);
\r
337 * Get conversion process state from file key
\r
341 public String getConvertState(String key){
\r
343 if(convertState.containsKey(key)){
\r
345 if(convertState.containsKey(key+"duration")) {
\r
346 duration = Integer.parseInt(convertState.get(key+"duration"));
\r
348 String state = convertState.get(key);
\r
350 if (state.contains("time")) {
\r
351 int currentTime = 0;
\r
352 //time=00:00:53.77 We take the hour, minute and seconds values
\r
353 Pattern pattern = Pattern.compile("time=(.*?)[.]");
\r
354 Matcher matcher = pattern.matcher(state);
\r
355 if (matcher.find())
\r
357 // Get value in seconds
\r
358 String currentTimeStr = matcher.group(1);
\r
360 String[] timeValues = currentTimeStr.split(":");
\r
361 if (timeValues.length == 3) {
\r
362 currentTime = Integer.parseInt(timeValues[0]) * 3600 + Integer.parseInt(timeValues[1]) * 60 + Integer.parseInt(timeValues[2]);
\r
365 if (currentTime != 0) {
\r
366 state = String.valueOf(currentTime*100/duration);
\r
369 if(state.equals("done") || state.equals("error")){
\r
370 convertState.remove(key);
\r
378 * Stop conversion process with the given key
\r
381 public void killConvertProcess(String key){
\r
382 if(convertProcess.containsKey(key)){
\r
383 convertProcess.get(key).destroy();
\r
384 convertProcess.remove(key);
\r
389 * Convert the source file in input stream to a new file with the targetExtension type
\r
392 * @param sourceExtension
\r
393 * @param targetExtension
\r
394 * @param parameters
\r
396 * @throws IOException
\r
397 * @throws SystemException
\r
399 private File _convert(
\r
400 String id, InputStream is, String sourceExtension,
\r
401 String targetExtension, Map<String, String> parameters)
\r
402 throws IOException, SystemException {
\r
404 _log.warn("BEGIN CONVERSION METHOD : Convert from " + sourceExtension + " to " + targetExtension);
\r
409 if (!PrefsPropsUtil.getBoolean(
\r
410 PropsKeys.OPENOFFICE_SERVER_ENABLED,
\r
411 PropsValues.OPENOFFICE_SERVER_ENABLED)) {
\r
415 String fileName = getFileName(id, targetExtension);
\r
416 File fileResult = new File(fileName);
\r
417 boolean forceConversion = !parameters.isEmpty();
\r
419 // If the file is in cache then don't convert it again
\r
420 if (fileResult.exists() && !forceConversion) {
\r
421 _log.warn("File already converted, directly return file in cache");
\r
422 convertState.put(id, "done");
\r
426 if (targetExtension.equals("mp4") || targetExtension.equals("mp3")) {
\r
427 // Start media conversion
\r
428 fileResult = startMediaConversion(fileResult, is, id, sourceExtension, targetExtension, fileName, parameters);
\r
430 else if (targetExtension.equals("pdf")) {
\r
431 // Run OpenOffice conversion
\r
432 return runOpenOfficeConversion(fileResult, is, sourceExtension, targetExtension);
\r
435 // Process has ended without being killed
\r
436 if(convertProcess.containsKey(id)){
\r
437 convertProcess.remove(id);
\r
439 // Check if the conversion has ended correctly (the new file is created)
\r
440 if(fileResult.exists()){
\r
441 _log.warn("Conversion process successfully done");
\r
442 convertState.put(id, "done");
\r
445 _log.error("Conversion process failed");
\r
446 convertState.put(id, "error");
\r
456 * Build complete temp filename from id and extension
\r
457 * @param id ID from the file
\r
458 * @param extension file type
\r
459 * @return the temp file name
\r
461 private String getFileName(String id, String extension) {
\r
462 StringBuilder sb = new StringBuilder();
\r
463 sb.append(SystemProperties.get(SystemProperties.TMP_DIR));
\r
464 sb.append("/liferay/document_conversion/");
\r
466 sb.append(StringPool.PERIOD);
\r
467 sb.append(extension);
\r
468 return sb.toString();
\r
472 * Find infos concerning video or audio file before conversion
\r
473 * @param filePath the source file path
\r
475 private void getMediaFileInfos(String filePath, String id) {
\r
476 String [] cmdProbe = new String("ffprobe " + filePath).split(" ");
\r
478 final Process p = Runtime.getRuntime().exec(cmdProbe);
\r
479 convertProcess.put(id+"getInfos", p);
\r
481 public void run() {
\r
483 BufferedReader reader = new BufferedReader(new InputStreamReader(p.getErrorStream()));
\r
486 while((line = reader.readLine()) != null) {
\r
487 if (line.contains("Duration")) {
\r
488 //Duration: 01:38:16.28, We take the hour, minute and seconds values
\r
489 Pattern pattern = Pattern.compile("Duration: (.*?)[.]");
\r
490 Matcher matcher = pattern.matcher(line);
\r
491 if (matcher.find())
\r
493 // Get value in seconds
\r
494 String durationStr = matcher.group(1);
\r
496 String[] timeValues = durationStr.split(":");
\r
497 if (timeValues.length == 3) {
\r
498 mediaDuration = Integer.parseInt(timeValues[0]) * 3600 + Integer.parseInt(timeValues[1]) * 60 + Integer.parseInt(timeValues[2]);
\r
502 if (line.contains("Video: h264") && line.contains("kb/s")) {
\r
509 } catch(IOException ioe) {
\r
515 }catch(Exception e) {
\r
522 * Run document conversion to PDF
\r
523 * @param fileResult
\r
525 * @param sourceExtension
\r
526 * @param targetExtension
\r
529 private File runOpenOfficeConversion(File fileResult, InputStream is, String sourceExtension, String targetExtension) {
\r
530 // conversion OPENOFFICE
\r
531 _log.debug("OpenOffice conversion");
\r
532 DocumentFormatRegistry registry =
\r
533 new DefaultDocumentFormatRegistry();
\r
535 DocumentConverter converter;
\r
537 converter = _getConverter(registry);
\r
539 catch(SystemException e) {
\r
541 return new File(fileResult.getPath());
\r
544 if (sourceExtension.equals("docx")) {
\r
545 sourceExtension = "doc";
\r
547 if (sourceExtension.equals("xlsx")) {
\r
548 sourceExtension = "xls";
\r
550 if (sourceExtension.equals("pptx")) {
\r
551 sourceExtension = "ppt";
\r
555 DocumentFormat inputFormat = registry.getFormatByFileExtension(
\r
558 ByteArrayOutputStream baos = new ByteArrayOutputStream();
\r
560 DocumentFormat outputFormat = registry.getFormatByFileExtension(
\r
563 converter.convert(is, inputFormat, baos, outputFormat);
\r
564 FileUtil.write(fileResult, baos.toByteArray());
\r
567 catch(IOException e) {
\r
569 return new File(fileResult.getPath());
\r
572 // retour direct apres conversion office
\r
577 * Launch media conversion which will init the needed parameters
\r
578 * @param fileResult
\r
581 * @param sourceExtension
\r
582 * @param targetExtension
\r
584 * @param parameters
\r
587 private File startMediaConversion(File fileResult, InputStream is, String id, String sourceExtension,
\r
588 String targetExtension, String fileName, Map<String, String> parameters) {
\r
589 String command = "";
\r
590 String extraConversionOption = "";
\r
592 String fileSourceName = getFileName(id, sourceExtension);
\r
593 File fileSourceTmp = new File(fileSourceName);
\r
595 // Write temp source file
\r
596 ByteArrayOutputStream buffer = new ByteArrayOutputStream();
\r
598 byte[] data = new byte[16384];
\r
601 while ((nRead = is.read(data, 0, data.length)) != -1) {
\r
602 buffer.write(data, 0, nRead);
\r
605 FileUtil.write(fileSourceTmp, buffer.toByteArray());
\r
607 catch (IOException e) {
\r
609 return new File(fileResult.getPath());
\r
613 getMediaFileInfos(fileSourceTmp.getPath(), id);
\r
615 if(targetExtension.equals("mp3")){
\r
616 command = "ffmpeg -i " + fileSourceTmp.getPath() + " -movflags +faststart " + fileName;
\r
618 else if(targetExtension.equals("mp4")) {
\r
619 /* If we have more args -> need a command update
\r
620 String sampleRate = parameters.containsKey("sampleRate") ? parameters.get("sampleRate") : "22050";
\r
621 String avSync = parameters.containsKey("avSync") ? parameters.get("avSync") : "-mc 0";
\r
622 String frameRate = parameters.containsKey("frameRate") ? parameters.get("frameRate") : ""; // frameRate doit contenir "-ofps 25" par exemple
\r
623 String bitrateAudio = parameters.containsKey("bitrateAudio") ? parameters.get("bitrateAudio") : "56";
\r
624 String bitrateVideo = parameters.containsKey("bitrateVideo") ? parameters.get("bitrateVideo") : "250"; // frameRate doit contenir "-ofps 25" par exemple
\r
626 String videoSize = parameters.containsKey("videoSize") ? parameters.get("videoSize") : "360x240";
\r
627 String[] size = videoSize.split("x");
\r
628 String videoWidth = size[0];
\r
629 String videoHeight = size[1];
\r
630 String videoScale = "-vf scale=";
\r
631 boolean keepAspect = Boolean.getBoolean(parameters.containsKey("keepAspect") ? parameters.get("keepAspect") : "true");
\r
633 videoScale += videoWidth + ":-2,expand=:" + videoHeight + ":::,crop=" + videoWidth + ":" + videoHeight + ",harddup";
\r
636 videoScale += videoWidth + ":" + videoHeight + ",harddup";
\r
640 //-movflags +faststart thanks to this option the video will start before file is entirely loaded
\r
642 //If we can detect if video encoding is h264 use copy only to optimize (using ffprobe ?) :
\r
643 command = "ffmpeg -i " + fileSourceTmp.getPath() + " -vcodec copy -acodec copy -movflags +faststart " + fileName;
\r
646 command = "ffmpeg -i " + fileSourceTmp.getPath() + " -c:v libx264 -preset ultrafast -c:a aac -movflags +faststart " + fileName;
\r
650 //_log.warn("Command used : " + command);
\r
651 fileResult = runMediaConversion(command, fileResult, fileName, id);
\r
653 // Delete the temp source file created
\r
654 if (FileUtil.exists(fileSourceTmp)) {
\r
655 FileUtil.delete(fileSourceTmp);
\r
662 * Run media conversion process that's describe in command parameter.
\r
663 * Return the converted file
\r
665 * @param fileResult
\r
670 private File runMediaConversion(String command, File fileResult, String fileName, String id) {
\r
671 _log.warn("Media conversion");
\r
672 final String secureId = id;
\r
673 String [] cmd = command.split(" ");
\r
676 final Process p = Runtime.getRuntime().exec(cmd);
\r
677 convertProcess.put(secureId, p);
\r
678 convertState.put(secureId+"duration", String.valueOf(mediaDuration));
\r
679 // Write convert process state informations
\r
681 public void run() {
\r
683 BufferedReader reader = new BufferedReader(new InputStreamReader(p.getErrorStream()));
\r
686 while((line = reader.readLine()) != null) {
\r
687 convertState.put(secureId, line);
\r
693 } catch(IOException ioe) {
\r
698 // Waiting for the process to end
\r
700 fileResult = new File(fileName);
\r
702 }catch(Exception e) {
\r
708 private void _disconnect() {
\r
709 if (_connection != null) {
\r
710 _connection.disconnect();
\r
714 private String _fixExtension(String extension) {
\r
715 if (extension.equals("htm")) {
\r
716 extension = "html";
\r
722 private String[] _getConversions(String extension) {
\r
723 extension = _fixExtension(extension);
\r
725 String[] conversions = _conversionsMap.get(extension);
\r
727 if (conversions == null) {
\r
728 conversions = _DEFAULT_CONVERSIONS;
\r
731 if (ArrayUtil.contains(conversions, extension)) {
\r
732 List<String> conversionsList = new ArrayList<String>();
\r
734 for (int i = 0; i < conversions.length; i++) {
\r
735 String conversion = conversions[i];
\r
737 if (!conversion.equals(extension)) {
\r
738 conversionsList.add(conversion);
\r
742 conversions = conversionsList.toArray(
\r
743 new String[conversionsList.size()]);
\r
747 return conversions;
\r
750 private DocumentConverter _getConverter(DocumentFormatRegistry registry)
\r
751 throws SystemException {
\r
753 if ((_connection == null) || (_converter == null)) {
\r
754 String host = PrefsPropsUtil.getString(
\r
755 PropsKeys.OPENOFFICE_SERVER_HOST);
\r
756 int port = PrefsPropsUtil.getInteger(
\r
757 PropsKeys.OPENOFFICE_SERVER_PORT,
\r
758 PropsValues.OPENOFFICE_SERVER_PORT);
\r
759 //_log.warn("host : " + host + " - port : " + port);
\r
761 if (_isRemoteOpenOfficeHost(host)) {
\r
762 _connection = new SocketOpenOfficeConnection(host, port);
\r
763 _converter = new StreamOpenOfficeDocumentConverter(_connection);
\r
766 _connection = new SocketOpenOfficeConnection(port);
\r
767 _converter = new OpenOfficeDocumentConverter(_connection);
\r
774 private boolean _isRemoteOpenOfficeHost(String host) {
\r
775 if (Validator.isNotNull(host) && !host.equals(_LOCALHOST_IP) &&
\r
776 !host.startsWith(_LOCALHOST)) {
\r
785 private void _populateConversionsMap(String documentFamily) {
\r
786 Filter filter = new Filter(documentFamily);
\r
788 DocumentFormatRegistry documentFormatRegistry =
\r
789 new DefaultDocumentFormatRegistry();
\r
791 String[] sourceExtensions = PropsUtil.getArray(
\r
792 PropsKeys.OPENOFFICE_CONVERSION_SOURCE_EXTENSIONS, filter);
\r
793 String[] targetExtensions = PropsUtil.getArray(
\r
794 PropsKeys.OPENOFFICE_CONVERSION_TARGET_EXTENSIONS, filter);
\r
796 for (String sourceExtension : sourceExtensions) {
\r
797 List<String> conversions = new SortedArrayList<String>();
\r
799 DocumentFormat sourceDocumentFormat =
\r
800 documentFormatRegistry.getFormatByFileExtension(
\r
803 if (sourceDocumentFormat == null) {
\r
804 if (_log.isWarnEnabled()) {
\r
805 _log.warn("Invalid source extension " + sourceExtension);
\r
811 for (String targetExtension : targetExtensions) {
\r
812 DocumentFormat targetDocumentFormat =
\r
813 documentFormatRegistry.getFormatByFileExtension(
\r
816 if (targetDocumentFormat == null) {
\r
817 if (_log.isWarnEnabled()) {
\r
819 "Invalid target extension " + targetDocumentFormat);
\r
825 if (sourceDocumentFormat.isExportableTo(targetDocumentFormat)) {
\r
826 conversions.add(targetExtension);
\r
830 if (conversions.isEmpty()) {
\r
831 if (_log.isInfoEnabled()) {
\r
833 "There are no conversions supported from " +
\r
838 if (_log.isInfoEnabled()) {
\r
840 "Conversions supported from " + sourceExtension +
\r
841 " to " + conversions);
\r
844 _conversionsMap.put(
\r
846 conversions.toArray(new String[conversions.size()]));
\r
851 private void _validateExtension(String extension) throws SystemException {
\r
852 if (extension.contains(StringPool.SLASH) ||
\r
853 extension.contains(StringPool.BACK_SLASH) ||
\r
854 extension.contains(File.pathSeparator)) {
\r
856 throw new SystemException("Invalid extension: " + extension);
\r
860 private static final String[] _DEFAULT_CONVERSIONS = new String[0];
\r
862 private static final String[] _DRAWING_CONVERSIONS = new String[] {"odg"};
\r
864 private static final String[] _COMPARABLE_FILE_EXTENSIONS =
\r
865 PropsValues.DL_COMPARABLE_FILE_EXTENSIONS;
\r
867 private static final String _LOCALHOST = "localhost";
\r
869 private static final String _LOCALHOST_IP = "127.0.0.1";
\r
871 private static final String[] _PRESENTATION_CONVERSIONS = new String[] {
\r
872 "odp", "pdf", "ppt", "sxi","pptx"
\r
875 private static final String[] _SPREADSHEET_CONVERSIONS = new String[] {
\r
876 "csv", "ods", "pdf", "sxc", "tsv", "xls","xlsx"
\r
879 private static final String[] _TEXT_CONVERSIONS = new String[] {
\r
880 "doc", "odt", "pdf", "rtf", "sxw", "txt","docx"
\r
883 private static Log _log = LogFactoryUtil.getLog(
\r
884 ENTDocumentConversionUtil.class);
\r
886 private static ENTDocumentConversionUtil _instance =
\r
887 new ENTDocumentConversionUtil();
\r
889 private Map<String, String[]> _conversionsMap =
\r
890 new HashMap<String, String[]>();
\r
891 private OpenOfficeConnection _connection;
\r
892 private DocumentConverter _converter;
\r
894 // If video has the right encoding we can handle faster conversion
\r
895 private boolean isH264 = false;
\r
897 // Media duration on seconds (Use for the progress bar)
\r
898 private int mediaDuration = 0;
\r