KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > alfresco > repo > content > filestore > FileContentReader


1 /*
2  * Copyright (C) 2005 Alfresco, Inc.
3  *
4  * Licensed under the Mozilla Public License version 1.1
5  * with a permitted attribution clause. You may obtain a
6  * copy of the License at
7  *
8  * http://www.alfresco.org/legal/license.txt
9  *
10  * Unless required by applicable law or agreed to in writing,
11  * software distributed under the License is distributed on an
12  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
13  * either express or implied. See the License for the specific
14  * language governing permissions and limitations under the
15  * License.
16  */

17 package org.alfresco.repo.content.filestore;
18
19 import java.io.File JavaDoc;
20 import java.io.FileInputStream JavaDoc;
21 import java.io.IOException JavaDoc;
22 import java.io.InputStream JavaDoc;
23 import java.io.RandomAccessFile JavaDoc;
24 import java.nio.channels.Channels JavaDoc;
25 import java.nio.channels.ReadableByteChannel JavaDoc;
26 import java.text.MessageFormat JavaDoc;
27
28 import org.alfresco.repo.content.AbstractContentReader;
29 import org.alfresco.repo.content.MimetypeMap;
30 import org.alfresco.service.cmr.repository.ContentIOException;
31 import org.alfresco.service.cmr.repository.ContentReader;
32 import org.alfresco.service.cmr.repository.ContentWriter;
33 import org.alfresco.util.TempFileProvider;
34 import org.apache.commons.logging.Log;
35 import org.apache.commons.logging.LogFactory;
36
37 /**
38  * Provides direct access to a local file.
39  * <p>
40  * This class does not provide remote access to the file.
41  *
42  * @author Derek Hulley
43  */

44 public class FileContentReader extends AbstractContentReader
45 {
46     /**
47      * message key for missing content. Parameters are
48      * <ul>
49      * <li>{@link org.alfresco.service.cmr.repository.NodeRef NodeRef}</li>
50      * <li>{@link ContentReader ContentReader}</li>
51      * </ul>
52      */

53     public static final String JavaDoc MSG_MISSING_CONTENT = "content.content_missing";
54     
55     private static final Log logger = LogFactory.getLog(FileContentReader.class);
56     
57     private File JavaDoc file;
58     private boolean allowRandomAccess;
59     
60     /**
61      * Checks the existing reader provided and replaces it with a reader onto some
62      * fake content if required. If the existing reader is invalid, an debug message
63      * will be logged under this classname category.
64      * <p>
65      * It is a convenience method that clients can use to cheaply get a reader that
66      * is valid, regardless of whether the initial reader is valid.
67      *
68      * @param existingReader a potentially invalid reader or null
69      * @param msgTemplate the template message that will used to format the final <i>fake</i> content
70      * @param args arguments to put into the <i>fake</i> content
71      * @return Returns a the existing reader or a new reader onto some generated text content
72      */

73     public static ContentReader getSafeContentReader(ContentReader existingReader, String JavaDoc msgTemplate, Object JavaDoc ... args)
74     {
75         ContentReader reader = existingReader;
76         if (existingReader == null || !existingReader.exists())
77         {
78             // the content was never written to the node or the underlying content is missing
79
String JavaDoc fakeContent = MessageFormat.format(msgTemplate, args);
80             
81             // log it
82
if (logger.isDebugEnabled())
83             {
84                 logger.debug(fakeContent);
85             }
86             
87             // fake the content
88
File JavaDoc tempFile = TempFileProvider.createTempFile("getSafeContentReader_", ".txt");
89             ContentWriter writer = new FileContentWriter(tempFile);
90             writer.setMimetype(MimetypeMap.MIMETYPE_TEXT_PLAIN);
91             writer.setEncoding("UTF-8");
92             writer.putContent(fakeContent);
93             // grab the reader from the temp writer
94
reader = writer.getReader();
95         }
96         // done
97
if (logger.isDebugEnabled())
98         {
99             logger.debug("Created safe content reader: \n" +
100                     " existing reader: " + existingReader + "\n" +
101                     " safe reader: " + reader);
102         }
103         return reader;
104     }
105     
106     /**
107      * Constructor that builds a URL based on the absolute path of the file.
108      *
109      * @param file the file for reading. This will most likely be directly
110      * related to the content URL.
111      */

112     public FileContentReader(File JavaDoc file)
113     {
114         this(file, FileContentStore.STORE_PROTOCOL + file.getAbsolutePath());
115     }
116     
117     /**
118      * Constructor that explicitely sets the URL that the reader represents.
119      *
120      * @param file the file for reading. This will most likely be directly
121      * related to the content URL.
122      * @param url the relative url that the reader represents
123      */

124     public FileContentReader(File JavaDoc file, String JavaDoc url)
125     {
126         super(url);
127         
128         this.file = file;
129         allowRandomAccess = true;
130     }
131     
132     /* package */ void setAllowRandomAccess(boolean allow)
133     {
134         this.allowRandomAccess = allow;
135     }
136     
137     /**
138      * @return Returns the file that this reader accesses
139      */

140     public File JavaDoc getFile()
141     {
142         return file;
143     }
144
145     public boolean exists()
146     {
147         return file.exists();
148     }
149
150     /**
151      * @see File#length()
152      */

153     public long getSize()
154     {
155         if (!exists())
156         {
157             return 0L;
158         }
159         else
160         {
161             return file.length();
162         }
163     }
164     
165     /**
166      * @see File#lastModified()
167      */

168     public long getLastModified()
169     {
170         if (!exists())
171         {
172             return 0L;
173         }
174         else
175         {
176             return file.lastModified();
177         }
178     }
179
180     /**
181      * The URL of the write is known from the start and this method contract states
182      * that no consideration needs to be taken w.r.t. the stream state.
183      */

184     @Override JavaDoc
185     protected ContentReader createReader() throws ContentIOException
186     {
187         FileContentReader reader = new FileContentReader(this.file, getContentUrl());
188         reader.setAllowRandomAccess(this.allowRandomAccess);
189         return reader;
190     }
191     
192     @Override JavaDoc
193     protected ReadableByteChannel JavaDoc getDirectReadableChannel() throws ContentIOException
194     {
195         try
196         {
197             // the file must exist
198
if (!file.exists())
199             {
200                 throw new IOException JavaDoc("File does not exist");
201             }
202             // create the channel
203
ReadableByteChannel JavaDoc channel = null;
204             if (allowRandomAccess)
205             {
206                 RandomAccessFile JavaDoc randomAccessFile = new RandomAccessFile JavaDoc(file, "r"); // won't create it
207
channel = randomAccessFile.getChannel();
208             }
209             else
210             {
211                 InputStream JavaDoc is = new FileInputStream JavaDoc(file);
212                 channel = Channels.newChannel(is);
213             }
214             // done
215
if (logger.isDebugEnabled())
216             {
217                 logger.debug("Opened write channel to file: \n" +
218                         " file: " + file + "\n" +
219                         " random-access: " + allowRandomAccess);
220             }
221             return channel;
222         }
223         catch (Throwable JavaDoc e)
224         {
225             throw new ContentIOException("Failed to open file channel: " + this, e);
226         }
227     }
228
229     /**
230      * @return Returns false as this is a reader
231      */

232     public boolean canWrite()
233     {
234         return false; // we only allow reading
235
}
236 }
237
Popular Tags