1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.chemistry.opencmis.client.util;
20
21 import java.io.BufferedInputStream;
22 import java.io.BufferedOutputStream;
23 import java.io.ByteArrayInputStream;
24 import java.io.File;
25 import java.io.FileInputStream;
26 import java.io.FileNotFoundException;
27 import java.io.FileOutputStream;
28 import java.io.IOException;
29 import java.io.InputStream;
30 import java.io.OutputStream;
31 import java.math.BigInteger;
32
33 import org.apache.chemistry.opencmis.commons.data.ContentStream;
34 import org.apache.chemistry.opencmis.commons.data.MutableContentStream;
35 import org.apache.chemistry.opencmis.commons.impl.IOUtils;
36 import org.apache.chemistry.opencmis.commons.impl.MimeTypes;
37 import org.apache.chemistry.opencmis.commons.impl.dataobjects.ContentStreamImpl;
38
39
40
41
42 public final class ContentStreamUtils {
43
44 private static final String OCTETSTREAM = "application/octet-stream";
45
46 private ContentStreamUtils() {
47 }
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64 public static MutableContentStream createContentStream(String filename, long length, String mimetype,
65 InputStream stream) {
66 return createContentStream(filename, length < 0 ? null : BigInteger.valueOf(length), mimetype, stream);
67 }
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83 public static MutableContentStream createContentStream(String filename, BigInteger length, String mimetype,
84 InputStream stream) {
85 return new ContentStreamImpl(checkFilename(filename), length, checkMIMEType(mimetype), stream);
86 }
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101 public static MutableContentStream createByteArrayContentStream(String filename, byte[] contentBytes) {
102 return createByteArrayContentStream(filename, contentBytes, OCTETSTREAM);
103 }
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118 public static MutableContentStream createByteArrayContentStream(String filename, byte[] contentBytes,
119 String mimetype) {
120 if (contentBytes == null) {
121 return createContentStream(filename, null, mimetype, null);
122 }
123
124 return createByteArrayContentStream(filename, contentBytes, 0, contentBytes.length, mimetype);
125 }
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144 public static MutableContentStream createByteArrayContentStream(String filename, byte[] contentBytes, int offset,
145 int length, String mimetype) {
146 if (contentBytes == null) {
147 return createContentStream(filename, null, mimetype, null);
148 }
149
150 if (offset < 0 || offset > contentBytes.length) {
151 throw new IndexOutOfBoundsException("Invalid offset!");
152 } else if (length < 0 || (offset + length) > contentBytes.length || (offset + length) < 0) {
153 throw new IndexOutOfBoundsException("Invalid length!");
154 }
155
156 return createContentStream(filename, length, mimetype, new AutoCloseInputStream(new ByteArrayInputStream(
157 contentBytes, offset, length)));
158 }
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173 public static MutableContentStream createTextContentStream(String filename, String content) {
174 return createTextContentStream(filename, content, "text/plain; charset=UTF-8");
175 }
176
177
178
179
180
181
182
183
184
185
186
187
188
189 public static MutableContentStream createTextContentStream(String filename, String content, String mimetype) {
190 byte[] contentBytes = IOUtils.toUTF8Bytes(content);
191 return createByteArrayContentStream(filename, contentBytes, checkMIMEType(mimetype));
192 }
193
194
195
196
197
198
199
200
201
202
203
204
205 public static MutableContentStream createFileContentStream(File file) throws FileNotFoundException {
206 return createFileContentStream(file.getName(), file, MimeTypes.getMIMEType(file));
207 }
208
209
210
211
212
213
214
215
216
217
218
219
220
221 public static MutableContentStream createFileContentStream(String filename, File file) throws FileNotFoundException {
222 return createFileContentStream(filename, file, MimeTypes.getMIMEType(file));
223 }
224
225
226
227
228
229
230
231
232
233
234
235 public static MutableContentStream createFileContentStream(File file, String mimetype) throws FileNotFoundException {
236 return createFileContentStream(file.getName(), file, mimetype);
237 }
238
239
240
241
242
243
244
245
246
247
248
249
250
251 public static MutableContentStream createFileContentStream(String filename, File file, String mimetype)
252 throws FileNotFoundException {
253 return createContentStream(filename, file.length(), mimetype, new AutoCloseInputStream(new BufferedInputStream(
254 new FileInputStream(file))));
255 }
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271 public static void writeContentStreamToOutputStream(ContentStream contentStream, OutputStream outputStream)
272 throws IOException {
273 if (outputStream == null) {
274 throw new IllegalArgumentException("Output stream is null!");
275 }
276
277 if (contentStream == null || contentStream.getStream() == null) {
278 return;
279 }
280
281 try {
282 IOUtils.copy(contentStream.getStream(), outputStream);
283 } finally {
284 IOUtils.closeQuietly(contentStream);
285 }
286 }
287
288
289
290
291
292
293
294
295
296
297
298
299
300 public static void writeContentStreamToFile(ContentStream contentStream, File file) throws IOException {
301 if (file == null) {
302 throw new IllegalArgumentException("File is null!");
303 }
304
305 OutputStream fileStream = new BufferedOutputStream(new FileOutputStream(file));
306 try {
307 writeContentStreamToOutputStream(contentStream, fileStream);
308 fileStream.flush();
309 } finally {
310 IOUtils.closeQuietly(fileStream);
311 }
312 }
313
314
315 private static String checkFilename(String filename) {
316 if (filename == null || filename.length() == 0) {
317 return "content";
318 }
319
320 return filename;
321 }
322
323 private static String checkMIMEType(String mimetype) {
324 if (mimetype == null) {
325 return OCTETSTREAM;
326 }
327
328 String result = mimetype.trim();
329 if (result.length() < 3) {
330 return OCTETSTREAM;
331 }
332
333 return result;
334 }
335
336
337
338
339
340
341 public static class AutoCloseInputStream extends InputStream {
342
343 protected InputStream stream;
344
345 public AutoCloseInputStream(InputStream in) {
346 stream = in;
347 }
348
349 @Override
350 public int read() throws IOException {
351 if (stream != null) {
352 int b = -1;
353
354 try {
355 b = stream.read();
356 } catch (IOException ioe) {
357 closeQuietly();
358 throw ioe;
359 }
360
361 if (b == -1) {
362 close();
363 }
364
365 return b;
366 } else {
367 throw new IOException("Stream is already closed!");
368 }
369 }
370
371 @Override
372 public int read(byte[] b) throws IOException {
373 if (stream != null) {
374 int l = -1;
375
376 try {
377 l = stream.read(b);
378 } catch (IOException ioe) {
379 closeQuietly();
380 throw ioe;
381 }
382
383 if (l == -1) {
384 close();
385 }
386
387 return l;
388 } else {
389 throw new IOException("Stream is already closed!");
390 }
391 }
392
393 @Override
394 public int read(byte[] b, int off, int len) throws IOException {
395 if (stream != null) {
396 int l = -1;
397
398 try {
399 l = stream.read(b, off, len);
400 } catch (IOException ioe) {
401 closeQuietly();
402 throw ioe;
403 }
404
405 if (l == -1) {
406 close();
407 }
408
409 return l;
410 } else {
411 throw new IOException("Stream is already closed!");
412 }
413 }
414
415 @Override
416 public long skip(long n) throws IOException {
417 if (stream != null) {
418 try {
419 return stream.skip(n);
420 } catch (IOException ioe) {
421 closeQuietly();
422 throw ioe;
423 }
424 } else {
425 throw new IOException("Stream is already closed!");
426 }
427 }
428
429 @Override
430 public int available() throws IOException {
431 if (stream != null) {
432 try {
433 return stream.available();
434 } catch (IOException ioe) {
435 closeQuietly();
436 throw ioe;
437 }
438 } else {
439 throw new IOException("Stream is already closed!");
440 }
441 }
442
443 @Override
444 public void close() throws IOException {
445 if (stream != null) {
446 try {
447 stream.close();
448 } catch (final IOException ioe) {
449 throw ioe;
450 } finally {
451 stream = null;
452 }
453 }
454 }
455
456 public void closeQuietly() {
457 if (stream != null) {
458 try {
459 stream.close();
460 } catch (final IOException ioe) {
461
462 } finally {
463 stream = null;
464 }
465 }
466 }
467
468 @Override
469 public synchronized void mark(int readlimit) {
470 if (stream != null) {
471 stream.mark(readlimit);
472 }
473 }
474
475 @Override
476 public synchronized void reset() throws IOException {
477 if (stream != null) {
478 try {
479 stream.reset();
480 } catch (IOException ioe) {
481 closeQuietly();
482 throw ioe;
483 }
484 } else {
485 throw new IOException("Stream is already closed!");
486 }
487 }
488
489 @Override
490 public boolean markSupported() {
491 if (stream != null) {
492 return stream.markSupported();
493 }
494
495 return false;
496 }
497
498 @Override
499 protected void finalize() throws Throwable {
500 closeQuietly();
501 super.finalize();
502 }
503 }
504 }