001    /**
002     * Copyright (c) 2000-2013 Liferay, Inc. All rights reserved.
003     *
004     * The contents of this file are subject to the terms of the Liferay Enterprise
005     * Subscription License ("License"). You may not use this file except in
006     * compliance with the License. You can obtain a copy of the License by
007     * contacting Liferay, Inc. See the License for the specific language governing
008     * permissions and limitations under the License, including but not limited to
009     * distribution rights of the Software.
010     *
011     *
012     *
013     */
014    
015    package com.liferay.portlet.documentlibrary.store;
016    
017    import com.liferay.portal.kernel.exception.PortalException;
018    import com.liferay.portal.kernel.exception.SystemException;
019    import com.liferay.portal.kernel.io.unsync.UnsyncByteArrayInputStream;
020    import com.liferay.portal.kernel.log.Log;
021    import com.liferay.portal.kernel.log.LogFactoryUtil;
022    import com.liferay.portal.kernel.transaction.Propagation;
023    import com.liferay.portal.kernel.transaction.Transactional;
024    import com.liferay.portal.kernel.util.FileUtil;
025    import com.liferay.portal.kernel.util.StringBundler;
026    import com.liferay.portlet.documentlibrary.DuplicateFileException;
027    import com.liferay.portlet.documentlibrary.model.DLContent;
028    import com.liferay.portlet.documentlibrary.service.DLContentLocalServiceUtil;
029    
030    import java.io.ByteArrayInputStream;
031    import java.io.File;
032    import java.io.FileInputStream;
033    import java.io.FileNotFoundException;
034    import java.io.IOException;
035    import java.io.InputStream;
036    
037    import java.nio.channels.FileChannel;
038    
039    import java.sql.Blob;
040    import java.sql.SQLException;
041    
042    import java.util.List;
043    
044    /**
045     * @author Shuyang Zhou
046     * @author Tina Tian
047     */
048    public class DBStore extends BaseStore {
049    
050            @Override
051            public void addDirectory(
052                    long companyId, long repositoryId, String dirName) {
053            }
054    
055            @Override
056            public void addFile(
057                            long companyId, long repositoryId, String fileName, byte[] bytes)
058                    throws PortalException, SystemException {
059    
060                    updateFile(
061                            companyId, repositoryId, fileName, Store.VERSION_DEFAULT, bytes);
062            }
063    
064            @Override
065            public void addFile(
066                            long companyId, long repositoryId, String fileName, File file)
067                    throws PortalException, SystemException {
068    
069                    updateFile(
070                            companyId, repositoryId, fileName, Store.VERSION_DEFAULT, file);
071            }
072    
073            @Override
074            public void addFile(
075                            long companyId, long repositoryId, String fileName,
076                            InputStream inputStream)
077                    throws PortalException, SystemException {
078    
079                    updateFile(
080                            companyId, repositoryId, fileName, Store.VERSION_DEFAULT,
081                            inputStream);
082            }
083    
084            @Override
085            public void checkRoot(long companyId) {
086            }
087    
088            @Override
089            public void deleteDirectory(
090                            long companyId, long repositoryId, String dirName)
091                    throws SystemException {
092    
093                    DLContentLocalServiceUtil.deleteContentsByDirectory(
094                            companyId, repositoryId, dirName);
095            }
096    
097            @Override
098            public void deleteFile(long companyId, long repositoryId, String fileName)
099                    throws SystemException {
100    
101                    DLContentLocalServiceUtil.deleteContents(
102                            companyId, repositoryId, fileName);
103            }
104    
105            @Override
106            public void deleteFile(
107                            long companyId, long repositoryId, String fileName,
108                            String versionLabel)
109                    throws PortalException, SystemException {
110    
111                    DLContentLocalServiceUtil.deleteContent(
112                            companyId, repositoryId, fileName, versionLabel);
113            }
114    
115            @Override
116            @Transactional(propagation = Propagation.REQUIRED)
117            public InputStream getFileAsStream(
118                            long companyId, long repositoryId, String fileName)
119                    throws PortalException, SystemException {
120    
121                    DLContent dlContent = DLContentLocalServiceUtil.getContent(
122                            companyId, repositoryId, fileName);
123    
124                    dlContent.resetOriginalValues();
125    
126                    Blob blobData = dlContent.getData();
127    
128                    if (blobData == null) {
129                            if (_log.isWarnEnabled()) {
130                                    StringBundler sb = new StringBundler(9);
131    
132                                    sb.append("No blob data found for file {companyId=");
133                                    sb.append(companyId);
134                                    sb.append(", repositoryId=");
135                                    sb.append(repositoryId);
136                                    sb.append(", fileName=");
137                                    sb.append(fileName);
138                                    sb.append("}");
139    
140                                    _log.warn(sb.toString());
141                            }
142    
143                            return null;
144                    }
145    
146                    try {
147                            return blobData.getBinaryStream();
148                    }
149                    catch (SQLException sqle) {
150                            StringBundler sb = new StringBundler(7);
151    
152                            sb.append("Unable to load data binary stream for file {companyId=");
153                            sb.append(companyId);
154                            sb.append(", repositoryId=");
155                            sb.append(repositoryId);
156                            sb.append(", fileName=");
157                            sb.append(fileName);
158                            sb.append("}");
159    
160                            throw new SystemException(sb.toString(), sqle);
161                    }
162            }
163    
164            @Override
165            @Transactional(propagation = Propagation.REQUIRED)
166            public InputStream getFileAsStream(
167                            long companyId, long repositoryId, String fileName,
168                            String versionLabel)
169                    throws PortalException, SystemException {
170    
171                    DLContent dlContent = DLContentLocalServiceUtil.getContent(
172                            companyId, repositoryId, fileName, versionLabel);
173    
174                    Blob blobData = dlContent.getData();
175    
176                    if (blobData == null) {
177                            if (_log.isWarnEnabled()) {
178                                    StringBundler sb = new StringBundler(9);
179    
180                                    sb.append("No blob data found for file {companyId=");
181                                    sb.append(companyId);
182                                    sb.append(", repositoryId=");
183                                    sb.append(repositoryId);
184                                    sb.append(", fileName=");
185                                    sb.append(fileName);
186                                    sb.append(", versionLabel=");
187                                    sb.append(versionLabel);
188                                    sb.append("}");
189    
190                                    _log.warn(sb.toString());
191                            }
192    
193                            return null;
194                    }
195    
196                    try {
197                            return blobData.getBinaryStream();
198                    }
199                    catch (SQLException sqle) {
200                            StringBundler sb = new StringBundler(9);
201    
202                            sb.append("Unable to load data binary stream for file {companyId=");
203                            sb.append(companyId);
204                            sb.append(", repositoryId=");
205                            sb.append(repositoryId);
206                            sb.append(", fileName=");
207                            sb.append(fileName);
208                            sb.append(", versionLabel=");
209                            sb.append(versionLabel);
210                            sb.append("}");
211    
212                            throw new SystemException(sb.toString(), sqle);
213                    }
214            }
215    
216            @Override
217            public String[] getFileNames(long companyId, long repositoryId)
218                    throws SystemException {
219    
220                    List<DLContent> dlContents = DLContentLocalServiceUtil.getContents(
221                            companyId, repositoryId);
222    
223                    String[] fileNames = new String[dlContents.size()];
224    
225                    for (int i = 0; i < dlContents.size(); i++) {
226                            DLContent dlContent = dlContents.get(i);
227    
228                            fileNames[i] = dlContent.getPath();
229                    }
230    
231                    return fileNames;
232            }
233    
234            @Override
235            public String[] getFileNames(
236                            long companyId, long repositoryId, String dirName)
237                    throws SystemException {
238    
239                    List<DLContent> dlContents =
240                            DLContentLocalServiceUtil.getContentsByDirectory(
241                                    companyId, repositoryId, dirName);
242    
243                    String[] fileNames = new String[dlContents.size()];
244    
245                    for (int i = 0; i < dlContents.size(); i++) {
246                            DLContent dlContent = dlContents.get(i);
247    
248                            fileNames[i] = dlContent.getPath();
249                    }
250    
251                    return fileNames;
252            }
253    
254            @Override
255            public long getFileSize(long companyId, long repositoryId, String fileName)
256                    throws PortalException, SystemException {
257    
258                    DLContent dlContent = DLContentLocalServiceUtil.getContent(
259                            companyId, repositoryId, fileName);
260    
261                    return dlContent.getSize();
262            }
263    
264            @Override
265            public boolean hasDirectory(
266                    long companyId, long repositoryId, String dirName) {
267    
268                    return true;
269            }
270    
271            @Override
272            public boolean hasFile(
273                            long companyId, long repositoryId, String fileName,
274                            String versionLabel)
275                    throws SystemException {
276    
277                    return DLContentLocalServiceUtil.hasContent(
278                            companyId, repositoryId, fileName, versionLabel);
279            }
280    
281            @Override
282            public void move(String srcDir, String destDir) {
283            }
284    
285            @Override
286            public void updateFile(
287                            long companyId, long repositoryId, long newRepositoryId,
288                            String fileName)
289                    throws PortalException, SystemException {
290    
291                    if (repositoryId == newRepositoryId) {
292                            throw new DuplicateFileException(
293                                    String.format(
294                                            "{companyId=%s, fileName=%s, repositoryId=%s}", companyId,
295                                            fileName, repositoryId));
296                    }
297    
298                    DLContentLocalServiceUtil.updateDLContent(
299                            companyId, repositoryId, newRepositoryId, fileName, fileName);
300            }
301    
302            @Override
303            public void updateFile(
304                            long companyId, long repositoryId, String fileName,
305                            String newFileName)
306                    throws PortalException, SystemException {
307    
308                    if (fileName.equals(newFileName)) {
309                            throw new DuplicateFileException(
310                                    String.format(
311                                            "{companyId=%s, fileName=%s, repositoryId=%s}", companyId,
312                                            fileName, repositoryId));
313                    }
314    
315                    DLContentLocalServiceUtil.updateDLContent(
316                            companyId, repositoryId, repositoryId, fileName, newFileName);
317            }
318    
319            @Override
320            public void updateFile(
321                            long companyId, long repositoryId, String fileName,
322                            String versionLabel, byte[] bytes)
323                    throws PortalException, SystemException {
324    
325                    if (DLContentLocalServiceUtil.hasContent(
326                                    companyId, repositoryId, fileName, versionLabel)) {
327    
328                            throw new DuplicateFileException(fileName);
329                    }
330    
331                    DLContentLocalServiceUtil.addContent(
332                            companyId, repositoryId, fileName, versionLabel, bytes);
333            }
334    
335            @Override
336            public void updateFile(
337                            long companyId, long repositoryId, String fileName,
338                            String versionLabel, File file)
339                    throws PortalException, SystemException {
340    
341                    if (DLContentLocalServiceUtil.hasContent(
342                                    companyId, repositoryId, fileName, versionLabel)) {
343    
344                            throw new DuplicateFileException(fileName);
345                    }
346    
347                    InputStream inputStream = null;
348    
349                    try {
350                            inputStream = new FileInputStream(file);
351                    }
352                    catch (FileNotFoundException fnfe) {
353                            throw new SystemException(fnfe);
354                    }
355    
356                    DLContentLocalServiceUtil.addContent(
357                            companyId, repositoryId, fileName, versionLabel, inputStream,
358                            file.length());
359            }
360    
361            @Override
362            public void updateFile(
363                            long companyId, long repositoryId, String fileName,
364                            String versionLabel, InputStream inputStream)
365                    throws PortalException, SystemException {
366    
367                    if (DLContentLocalServiceUtil.hasContent(
368                                    companyId, repositoryId, fileName, versionLabel)) {
369    
370                            throw new DuplicateFileException(fileName);
371                    }
372    
373                    long length = -1;
374    
375                    if (inputStream instanceof ByteArrayInputStream) {
376                            ByteArrayInputStream byteArrayInputStream =
377                                    (ByteArrayInputStream)inputStream;
378    
379                            length = byteArrayInputStream.available();
380                    }
381                    else if (inputStream instanceof FileInputStream) {
382                            FileInputStream fileInputStream = (FileInputStream)inputStream;
383    
384                            FileChannel fileChannel = fileInputStream.getChannel();
385    
386                            try {
387                                    length = fileChannel.size();
388                            }
389                            catch (IOException ioe) {
390                                    if (_log.isWarnEnabled()) {
391                                            _log.warn(
392                                                    "Unable to detect file size from file channel", ioe);
393                                    }
394                            }
395                    }
396                    else if (inputStream instanceof UnsyncByteArrayInputStream) {
397                            UnsyncByteArrayInputStream unsyncByteArrayInputStream =
398                                    (UnsyncByteArrayInputStream)inputStream;
399    
400                            length = unsyncByteArrayInputStream.available();
401                    }
402    
403                    if (length >= 0) {
404                            DLContentLocalServiceUtil.addContent(
405                                    companyId, repositoryId, fileName, versionLabel, inputStream,
406                                    length);
407                    }
408                    else {
409                            if (_log.isWarnEnabled()) {
410                                    _log.warn(
411                                            "Unable to detect length from input stream. Reading " +
412                                                    "entire input stream into memory as a last resort.");
413                            }
414    
415                            byte[] bytes = null;
416    
417                            try {
418                                    bytes = FileUtil.getBytes(inputStream);
419                            }
420                            catch (IOException ioe) {
421                                    throw new SystemException(ioe);
422                            }
423    
424                            DLContentLocalServiceUtil.addContent(
425                                    companyId, repositoryId, fileName, versionLabel, bytes);
426                    }
427            }
428    
429            private static Log _log = LogFactoryUtil.getLog(DBStore.class);
430    
431    }