1 package org.apache.turbine.services.xmlrpc.util;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 import java.io.BufferedReader;
20 import java.io.File;
21 import java.io.FileInputStream;
22 import java.io.FileWriter;
23 import java.io.IOException;
24 import java.io.InputStreamReader;
25 import java.io.StringWriter;
26
27 import javax.mail.internet.MimeUtility;
28
29 import org.apache.commons.lang.StringUtils;
30
31 import org.apache.commons.logging.Log;
32 import org.apache.commons.logging.LogFactory;
33
34 import org.apache.turbine.Turbine;
35
36 import org.apache.turbine.services.servlet.TurbineServlet;
37
38 /***
39 * A Handler for use with the XML-RPC service that will deal
40 * with clients sending file to the server (Turbine application)
41 * and clients getting files from the server (Turbine application).
42 *
43 * 1) In the first case where the client sends a file to the server,
44 * the client has encoded the file contents and passes those
45 * encoded file contents on to the server:
46 *
47 * Client --------> encoded file contents -------------> Server
48 *
49 * The server must then decode the file contents and write the
50 * decoded file contents to disk.
51 *
52 * 2) In the second case where the client gets a file from the
53 * the server, the server has encoded the file contents and
54 * passes those encoded file contents on to the client:
55 *
56 * Client <------- encoded file contents <------------- Server
57 *
58 * The client must then decode the file contents and write the
59 * decoded file contents to disk.
60 *
61 * @author <a href="mailto:jvanzyl@periapt.com">Jason van Zyl</a>
62 * @author <a href="mailto:jon@latchkey.com">Jon S. Stevens</a>
63 * @author <a href="mailto:hps@intermeta.de">Henning P. Schmiedehausen</a>
64 * @version $Id: FileHandler.java 264148 2005-08-29 14:21:04Z henning $
65 * @deprecated This is not scope of the Service itself but of an
66 * application which uses the service. This class shouldn't
67 * be part of Turbine but of an addon application.
68 */
69 public class FileHandler
70 {
71 /*** Logging */
72 private static Log log = LogFactory.getLog(FileHandler.class);
73
74 /***
75 * Default Constructor
76 */
77 public FileHandler()
78 {
79 }
80
81 /***
82 * The client has indicated that it would like
83 * to send a file to the server and have it
84 * stored in a certain location on the server.
85 *
86 * So a client Turbine application might use the
87 * following bit of code to send a file to a server
88 * Turbine application:
89 *
90 * TurbineXmlRpc.executeRpc("file.send", params)
91 *
92 * Where:
93 *
94 * params.get(0) = contents of the file as a string.
95 * params.get(1) = the name the file should have when it lands.
96 * params.get(2) = property describing where the file should land.
97 *
98 * @param fileContents The contents of the file to store. It
99 * is assumed that any xml content is properly encoded!
100 *
101 * @param fileName Name to give the file created to store
102 * the contents.
103 *
104 * @param targetLocationProperty storage location of this file
105 * is controlled by this property that is specified in
106 * the TR.props file or an included properties file.
107 */
108 public boolean send(String fileContents,
109 String targetLocationProperty,
110 String fileName)
111 {
112
113
114
115
116
117
118
119 return writeFileContents(fileContents, targetLocationProperty,
120 fileName);
121 }
122
123 /***
124 * The client has indicated that it would like
125 * to get a file from the server.
126 *
127 * So a client Turbine application might use the
128 * following bit of code to get a file from a server
129 * Turbine application:
130 *
131 * TurbineXmlRpc.executeRpc("file.get", params)
132 *
133 * Where:
134 *
135 * params.get(0) = the name the file should have when it lands.
136 * params.get(1) = property describing where the file should land.
137 *
138 * @param fileName Name to give the file created to store
139 * the contents.
140 *
141 * @param targetLocationProperty storage location of this file
142 * is controlled by this property that is specified in
143 * the TR.props file or an included properties file.
144 *
145 * @return the file contents encoded with base64.
146 */
147 public String get(String targetLocationProperty,
148 String fileName)
149 {
150
151
152
153
154
155 return readFileContents(targetLocationProperty, fileName);
156 }
157
158 /***
159 * Return the content of file encoded for transfer
160 *
161 * @param targetLocationProperty path to file to encode.
162 * @param fileName file to encode
163 * @return String encoded contents of the requested file.
164 */
165 public static String readFileContents(String targetLocationProperty,
166 String fileName)
167 {
168 String location =
169 Turbine.getConfiguration().getString(targetLocationProperty);
170
171 if (StringUtils.isEmpty(location))
172 {
173 log.error("Could not load Property for location "
174 + targetLocationProperty);
175 return null;
176 }
177
178 File tmpF = new File(".");
179
180 StringBuffer sb = new StringBuffer();
181 sb.append(location);
182 sb.append(File.separator);
183 sb.append(fileName);
184
185 String file = TurbineServlet.getRealPath(sb.toString());
186
187 StringWriter sw = null;
188 BufferedReader reader = null;
189 try
190 {
191
192
193
194
195
196 sw = new StringWriter();
197
198 reader = new BufferedReader(
199 new InputStreamReader(
200 new FileInputStream(file)));
201
202 char buf[] = new char[1024];
203 int len = 0;
204
205 while ((len = reader.read(buf, 0, 1024)) != -1)
206 {
207 sw.write(buf, 0, len);
208 }
209
210 return MimeUtility.encodeText(sw.toString(), "UTF-8", "B");
211 }
212 catch (IOException ioe)
213 {
214 log.error("[FileHandler] Unable to encode the contents " +
215 "of the request file.", ioe);
216
217 return null;
218 }
219 finally
220 {
221 try
222 {
223 if (sw != null)
224 {
225 sw.close();
226 }
227 if (reader != null)
228 {
229 reader.close();
230 }
231 }
232 catch (Exception e)
233 {
234 }
235 }
236 }
237
238 public static boolean writeFileContents(String fileContents,
239 String targetLocationProperty,
240 String fileName)
241 {
242 String location =
243 Turbine.getConfiguration().getString(targetLocationProperty);
244
245 if (StringUtils.isEmpty(location))
246 {
247 log.error("Could not load Property for location "
248 + targetLocationProperty);
249 return false;
250 }
251
252
253
254
255
256
257
258 File targetLocation = new File(
259 TurbineServlet.getRealPath(location));
260
261 if (!targetLocation.exists())
262 {
263
264
265
266
267
268 if (!targetLocation.mkdirs())
269 {
270 log.error("[FileHandler] Could not create target location: " +
271 targetLocation + ". Cannot transfer file from client.");
272
273 return false;
274 }
275 else
276 {
277 log.info("[FileHandler] Creating target location:" +
278 targetLocation +
279 " in order to complete file transfer from client.");
280 }
281 }
282
283 FileWriter fileWriter = null;
284 try
285 {
286
287
288
289
290 fileWriter = new FileWriter(
291 targetLocation + "/" + fileName);
292
293
294
295
296
297
298 fileWriter.write(MimeUtility.decodeText(fileContents));
299
300 return true;
301 }
302 catch (IOException ioe)
303 {
304 log.error("[FileHandler] Could not write the decoded file " +
305 "contents to disk for the following reason.", ioe);
306
307 return false;
308 }
309 finally
310 {
311 try
312 {
313 if (fileWriter != null)
314 {
315 fileWriter.close();
316 }
317 }
318 catch (Exception e)
319 {
320 }
321 }
322 }
323
324 /***
325 * Method to allow a client to remove a file from
326 * the server
327 *
328 * @param sourceLocationProperty
329 * @param sourceFileName
330 */
331 public static void remove(String sourceLocationProperty,
332 String sourceFileName)
333 {
334 String location =
335 Turbine.getConfiguration().getString(sourceLocationProperty);
336
337 if (StringUtils.isEmpty(location))
338 {
339 log.error("Could not load Property for location "
340 + sourceLocationProperty);
341 return;
342 }
343
344
345
346
347
348
349 File sourceFile =
350 new File(TurbineServlet.getRealPath(sourceLocationProperty
351 + "/" + sourceFileName));
352
353 if (sourceFile.exists())
354 {
355 sourceFile.delete();
356 }
357 }
358 }