001
014
015 package com.liferay.util.servlet;
016
017 import com.liferay.portal.kernel.io.unsync.UnsyncByteArrayOutputStream;
018 import com.liferay.portal.kernel.log.Log;
019 import com.liferay.portal.kernel.log.LogFactoryUtil;
020 import com.liferay.portal.kernel.nio.charset.CharsetEncoderUtil;
021 import com.liferay.portal.kernel.servlet.BrowserSnifferUtil;
022 import com.liferay.portal.kernel.servlet.ByteBufferServletResponse;
023 import com.liferay.portal.kernel.servlet.HttpHeaders;
024 import com.liferay.portal.kernel.servlet.StringServletResponse;
025 import com.liferay.portal.kernel.util.ArrayUtil;
026 import com.liferay.portal.kernel.util.FileUtil;
027 import com.liferay.portal.kernel.util.GetterUtil;
028 import com.liferay.portal.kernel.util.HttpUtil;
029 import com.liferay.portal.kernel.util.PropsUtil;
030 import com.liferay.portal.kernel.util.StreamUtil;
031 import com.liferay.portal.kernel.util.StringPool;
032 import com.liferay.portal.kernel.util.StringUtil;
033 import com.liferay.portal.kernel.util.Validator;
034
035 import java.io.File;
036 import java.io.FileInputStream;
037 import java.io.IOException;
038 import java.io.InputStream;
039
040 import java.net.SocketException;
041
042 import java.nio.ByteBuffer;
043 import java.nio.channels.Channels;
044 import java.nio.channels.FileChannel;
045
046 import javax.servlet.ServletOutputStream;
047 import javax.servlet.http.HttpServletRequest;
048 import javax.servlet.http.HttpServletResponse;
049
050
054 public class ServletResponseUtil {
055
056 public static void sendFile(
057 HttpServletRequest request, HttpServletResponse response,
058 String fileName, byte[] bytes)
059 throws IOException {
060
061 sendFile(request, response, fileName, bytes, null);
062 }
063
064 public static void sendFile(
065 HttpServletRequest request, HttpServletResponse response,
066 String fileName, byte[] bytes, String contentType)
067 throws IOException {
068
069 setHeaders(request, response, fileName, contentType);
070
071 write(response, bytes);
072 }
073
074 public static void sendFile(
075 HttpServletRequest request, HttpServletResponse response,
076 String fileName, InputStream is)
077 throws IOException {
078
079 sendFile(request, response, fileName, is, null);
080 }
081
082 public static void sendFile(
083 HttpServletRequest request, HttpServletResponse response,
084 String fileName, InputStream is, int contentLength,
085 String contentType)
086 throws IOException {
087
088 setHeaders(request, response, fileName, contentType);
089
090 write(response, is, contentLength);
091 }
092
093 public static void sendFile(
094 HttpServletRequest request, HttpServletResponse response,
095 String fileName, InputStream is, String contentType)
096 throws IOException {
097
098 sendFile(request, response, fileName, is, 0, contentType);
099 }
100
101
104 public static void sendFile(
105 HttpServletResponse response, String fileName, byte[] bytes)
106 throws IOException {
107
108 sendFile(null, response, fileName, bytes);
109 }
110
111
114 public static void sendFile(
115 HttpServletResponse response, String fileName, byte[] bytes,
116 String contentType)
117 throws IOException {
118
119 sendFile(null, response, fileName, bytes, contentType);
120 }
121
122
125 public static void sendFile(
126 HttpServletResponse response, String fileName, InputStream is)
127 throws IOException {
128
129 sendFile(null, response, fileName, is);
130 }
131
132
135 public static void sendFile(
136 HttpServletResponse response, String fileName, InputStream is,
137 int contentLength, String contentType)
138 throws IOException {
139
140 sendFile(null, response, fileName, is, contentLength, contentType);
141 }
142
143
146 public static void sendFile(
147 HttpServletResponse response, String fileName, InputStream is,
148 String contentType)
149 throws IOException {
150
151 sendFile(null, response, fileName, is, contentType);
152 }
153
154 public static void write(HttpServletResponse response, byte[] bytes)
155 throws IOException {
156
157 write(response, bytes, 0, 0);
158 }
159
160 public static void write(
161 HttpServletResponse response, byte[] bytes, int offset,
162 int contentLength)
163 throws IOException {
164
165 try {
166
167
168
169 if (!response.isCommitted()) {
170
171
172
173 if (contentLength == 0) {
174 contentLength = bytes.length;
175 }
176
177 response.setContentLength(contentLength);
178
179 if (response instanceof ByteBufferServletResponse) {
180 ByteBufferServletResponse byteBufferResponse =
181 (ByteBufferServletResponse)response;
182
183 byteBufferResponse.setByteBuffer(
184 ByteBuffer.wrap(bytes, offset, contentLength));
185 }
186 else {
187 ServletOutputStream servletOutputStream =
188 response.getOutputStream();
189
190 servletOutputStream.write(bytes, offset, contentLength);
191 }
192 }
193 }
194 catch (IOException ioe) {
195 if (ioe instanceof SocketException ||
196 ioe.getClass().getName().equals(_CLIENT_ABORT_EXCEPTION)) {
197
198 if (_log.isWarnEnabled()) {
199 _log.warn(ioe);
200 }
201 }
202 else {
203 throw ioe;
204 }
205 }
206 }
207
208 public static void write(HttpServletResponse response, byte[][] bytesArray)
209 throws IOException {
210
211 try {
212
213
214
215 if (!response.isCommitted()) {
216 int contentLength = 0;
217
218 for (byte[] bytes : bytesArray) {
219 contentLength += bytes.length;
220 }
221
222 response.setContentLength(contentLength);
223
224 ServletOutputStream servletOutputStream =
225 response.getOutputStream();
226
227 for (byte[] bytes : bytesArray) {
228 servletOutputStream.write(bytes);
229 }
230 }
231 }
232 catch (IOException ioe) {
233 if (ioe instanceof SocketException ||
234 ioe.getClass().getName().equals(_CLIENT_ABORT_EXCEPTION)) {
235
236 if (_log.isWarnEnabled()) {
237 _log.warn(ioe);
238 }
239 }
240 else {
241 throw ioe;
242 }
243 }
244 }
245
246 public static void write(
247 HttpServletResponse response, ByteBuffer byteBuffer)
248 throws IOException {
249
250 if (response instanceof ByteBufferServletResponse) {
251 ByteBufferServletResponse byteBufferResponse =
252 (ByteBufferServletResponse)response;
253
254 byteBufferResponse.setByteBuffer(byteBuffer);
255 }
256 else {
257 write(
258 response, byteBuffer.array(), byteBuffer.position(),
259 byteBuffer.limit());
260 }
261 }
262
263 public static void write(HttpServletResponse response, File file)
264 throws IOException {
265
266 if (response instanceof ByteBufferServletResponse) {
267 ByteBufferServletResponse byteBufferResponse =
268 (ByteBufferServletResponse)response;
269
270 ByteBuffer byteBuffer = ByteBuffer.wrap(FileUtil.getBytes(file));
271
272 byteBufferResponse.setByteBuffer(byteBuffer);
273 }
274 else if (response instanceof StringServletResponse) {
275 StringServletResponse stringResponse =
276 (StringServletResponse)response;
277
278 String s = FileUtil.read(file);
279
280 stringResponse.setString(s);
281 }
282 else {
283 FileInputStream fileInputStream = new FileInputStream(file);
284
285 FileChannel fileChannel = fileInputStream.getChannel();
286
287 try {
288 int contentLength = (int)fileChannel.size();
289
290 response.setContentLength(contentLength);
291
292 fileChannel.transferTo(
293 0, contentLength,
294 Channels.newChannel(response.getOutputStream()));
295 }
296 finally {
297 fileChannel.close();
298 }
299 }
300 }
301
302 public static void write(HttpServletResponse response, InputStream is)
303 throws IOException {
304
305 write(response, is, 0);
306 }
307
308 public static void write(
309 HttpServletResponse response, InputStream is, int contentLength)
310 throws IOException {
311
312 if (response.isCommitted()) {
313 return;
314 }
315
316 if (contentLength > 0) {
317 response.setContentLength(contentLength);
318 }
319
320 StreamUtil.transfer(is, response.getOutputStream());
321 }
322
323 public static void write(HttpServletResponse response, String s)
324 throws IOException {
325
326 if (response instanceof StringServletResponse) {
327 StringServletResponse stringResponse =
328 (StringServletResponse)response;
329
330 stringResponse.setString(s);
331 }
332 else {
333 ByteBuffer byteBuffer = CharsetEncoderUtil.encode(
334 StringPool.UTF8, s);
335
336 write(response, byteBuffer);
337 }
338 }
339
340 public static void write(
341 HttpServletResponse response, StringServletResponse stringResponse)
342 throws IOException {
343
344 if (stringResponse.isCalledGetOutputStream()) {
345 UnsyncByteArrayOutputStream unsyncByteArrayOutputStream =
346 stringResponse.getUnsyncByteArrayOutputStream();
347
348 ByteBuffer byteBuffer =
349 unsyncByteArrayOutputStream.unsafeGetByteBuffer();
350
351 write(response, byteBuffer);
352 }
353 else {
354 write(response, stringResponse.getString());
355 }
356 }
357
358 protected static void setHeaders(
359 HttpServletRequest request, HttpServletResponse response,
360 String fileName, String contentType) {
361
362 if (_log.isDebugEnabled()) {
363 _log.debug("Sending file of type " + contentType);
364 }
365
366
367
368 if (Validator.isNotNull(contentType)) {
369 response.setContentType(contentType);
370 }
371
372 response.setHeader(
373 HttpHeaders.CACHE_CONTROL, HttpHeaders.CACHE_CONTROL_PUBLIC_VALUE);
374 response.setHeader(HttpHeaders.PRAGMA, HttpHeaders.PRAGMA_PUBLIC_VALUE);
375
376 if (Validator.isNotNull(fileName)) {
377 String contentDisposition =
378 "attachment; filename=\"" + fileName + "\"";
379
380
381
382
383 boolean ascii = true;
384
385 for (int i = 0; i < fileName.length(); i++) {
386 if (!Validator.isAscii(fileName.charAt(i))) {
387 ascii = false;
388
389 break;
390 }
391 }
392
393 try {
394 if (!ascii) {
395 String encodedFileName = HttpUtil.encodeURL(fileName, true);
396
397 if (BrowserSnifferUtil.isIe(request)) {
398 contentDisposition =
399 "attachment; filename=\"" + encodedFileName + "\"";
400 }
401 else {
402 contentDisposition =
403 "attachment; filename*=UTF-8''" + encodedFileName;
404 }
405 }
406 }
407 catch (Exception e) {
408 if (_log.isWarnEnabled()) {
409 _log.warn(e);
410 }
411 }
412
413 String extension = GetterUtil.getString(
414 FileUtil.getExtension(fileName)).toLowerCase();
415
416 String[] mimeTypesContentDispositionInline = null;
417
418 try {
419 mimeTypesContentDispositionInline = PropsUtil.getArray(
420 "mime.types.content.disposition.inline");
421 }
422 catch (Exception e) {
423 mimeTypesContentDispositionInline = new String[0];
424 }
425
426 if (ArrayUtil.contains(
427 mimeTypesContentDispositionInline, extension)) {
428
429 contentDisposition = StringUtil.replace(
430 contentDisposition, "attachment; ", "inline; ");
431 }
432
433 response.setHeader(
434 HttpHeaders.CONTENT_DISPOSITION, contentDisposition);
435 }
436 }
437
438 private static final String _CLIENT_ABORT_EXCEPTION =
439 "org.apache.catalina.connector.ClientAbortException";
440
441 private static Log _log = LogFactoryUtil.getLog(ServletResponseUtil.class);
442
443 }