Author: jbq
Date: Tue Feb 27 10:19:22 2007
New Revision: 512351
URL: http://svn.apache.org/viewvc?view=rev&rev=512351
Log:
Fix WICKET-327: Download link does not set Content-Type and Content-Length
headers
Adding two methods in WebResponse:
* write(InputStream in)
* detectContentType(RequestCycle requestCycle, String uri)
Added:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadLinkTest.java
(with props)
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.html
(with props)
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.java
(with props)
Modified:
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/markup/html/link/DownloadLink.java
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/WebResponse.java
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/request/WebExternalResourceRequestTarget.java
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/protocol/http/WebRequestCodingStrategyTest.java
Modified:
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/markup/html/link/DownloadLink.java
URL:
http://svn.apache.org/viewvc/incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/markup/html/link/DownloadLink.java?view=diff&rev=512351&r1=512350&r2=512351
==============================================================================
---
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/markup/html/link/DownloadLink.java
(original)
+++
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/markup/html/link/DownloadLink.java
Tue Feb 27 10:19:22 2007
@@ -18,14 +18,10 @@
import java.io.File;
import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.io.InputStream;
import wicket.IRequestTarget;
import wicket.RequestCycle;
import wicket.protocol.http.WebResponse;
-import wicket.util.io.Streams;
import wicket.util.string.Strings;
/**
@@ -118,28 +114,11 @@
try
{
- InputStream is = new
FileInputStream(file);
- try
- {
- Streams.copy(is,
r.getOutputStream());
- }
- catch (IOException e)
- {
- throw new RuntimeException(e);
- }
- finally
- {
- try
- {
- is.close();
- }
- catch (IOException e)
- {
- throw new
RuntimeException(e);
- }
- }
+ r.write(new FileInputStream(file));
+ r.setContentLength(file.length());
+ r.detectContentType(requestCycle,
fileName);
}
- catch (FileNotFoundException e)
+ catch (Exception e)
{
throw new RuntimeException(e);
}
Modified:
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/WebResponse.java
URL:
http://svn.apache.org/viewvc/incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/WebResponse.java?view=diff&rev=512351&r1=512350&r2=512351
==============================================================================
---
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/WebResponse.java
(original)
+++
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/WebResponse.java
Tue Feb 27 10:19:22 2007
@@ -17,17 +17,22 @@
package wicket.protocol.http;
import java.io.IOException;
+import java.io.InputStream;
import java.io.OutputStream;
+import java.net.URLConnection;
import java.util.Locale;
+import javax.servlet.ServletContext;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
+import wicket.RequestCycle;
import wicket.Response;
import wicket.WicketRuntimeException;
+import wicket.util.io.Streams;
import wicket.util.string.AppendingStringBuffer;
import wicket.util.string.Strings;
import wicket.util.time.Time;
@@ -52,7 +57,7 @@
/** The underlying response object. */
private final HttpServletResponse httpServletResponse;
-
+
/** */
private boolean ajax;
@@ -194,9 +199,11 @@
{
httpServletResponse.addHeader("Ajax-Location", url);
- // safari chokes on empty
response. but perhaps this is not the best place?
+ // safari chokes on empty
response. but perhaps this is
+ // not the best place?
httpServletResponse.getWriter().write(" ");
- } else
+ }
+ else
{
httpServletResponse.sendRedirect(url);
}
@@ -368,10 +375,81 @@
/**
* Set that the request which matches this response is an ajax request.
*
- * @param ajax True if the request is an ajax request.
+ * @param ajax
+ * True if the request is an ajax request.
*/
public void setAjax(boolean ajax)
{
this.ajax = ajax;
+ }
+
+ /**
+ * Copies the given input stream to the servlet response
+ * <p>
+ * NOTE Content-Length is not set because it would require to buffer the
+ * whole input stream
+ * </p>
+ *
+ * @param in
+ * input stream to copy, will be closed after copy
+ */
+ public void write(InputStream in)
+ {
+ try
+ {
+ // Copy resource input stream to servlet output stream
+ Streams.copy(in,
getHttpServletResponse().getOutputStream());
+ }
+ catch (Exception e)
+ {
+ throw new WicketRuntimeException(e);
+ }
+ finally
+ {
+ // NOTE: We only close the InputStream. The servlet
+ // container should close the output stream.
+ try
+ {
+ in.close();
+ }
+ catch (IOException e)
+ {
+ throw new WicketRuntimeException(e);
+ }
+ }
+ }
+
+ /**
+ * Sets the Content-Type header with servlet-context-defined
content-types
+ * (application's web.xml or servlet container's configuration), and
fall
+ * back to system or JVM-defined (FileNameMap) content types.
+ *
+ * @param requestCycle
+ * @param uri
+ * Resource name to be analyzed to detect MIME type
+ *
+ * @see ServletContext#getMimeType(String)
+ * @see URLConnection#getFileNameMap()
+ */
+ public void detectContentType(RequestCycle requestCycle, String uri)
+ {
+ // Configure response with content type of resource
+ final ServletContext context =
((WebApplication)requestCycle.getApplication())
+ .getServletContext();
+ // First look for user defined content-type in web.xml
+ String contentType = context.getMimeType(uri);
+
+ // If not found, fall back to
+ // FileResourceStream.getContentType() that looks into
+ // system or JVM content types
+ if (contentType == null)
+ {
+ contentType =
URLConnection.getFileNameMap().getContentTypeFor(uri);
+ }
+
+ if (contentType != null)
+ {
+ setContentType(contentType);
+ }
}
}
Modified:
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/request/WebExternalResourceRequestTarget.java
URL:
http://svn.apache.org/viewvc/incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/request/WebExternalResourceRequestTarget.java?view=diff&rev=512351&r1=512350&r2=512351
==============================================================================
---
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/request/WebExternalResourceRequestTarget.java
(original)
+++
incubator/wicket/branches/wicket-1.x/wicket/src/main/java/wicket/protocol/http/request/WebExternalResourceRequestTarget.java
Tue Feb 27 10:19:22 2007
@@ -31,7 +31,6 @@
import wicket.protocol.http.WebApplication;
import wicket.protocol.http.WebRequestCycle;
import wicket.protocol.http.WebResponse;
-import wicket.util.io.Streams;
/**
* Request target that is not a Wicket resource. For example, such a resource
@@ -84,23 +83,9 @@
final InputStream in = context.getResourceAsStream(url);
if (in != null)
{
- // Set content type
- String contentType = context.getMimeType(url);
- if(contentType != null)
- {
- webResponse.setContentType(contentType);
- }
- try
- {
- // Copy resource input stream to
servlet output stream
- Streams.copy(in,
webResponse.getHttpServletResponse().getOutputStream());
- }
- finally
- {
- // NOTE: We only close the InputStream.
The servlet
- // container should close the output
stream.
- in.close();
- }
+ webResponse.write(in);
+ webResponse.detectContentType(requestCycle,
url);
+ // FIXME do we need to call
webResponse.setContentLength()?
}
else
{
Added:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadLinkTest.java
URL:
http://svn.apache.org/viewvc/incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadLinkTest.java?view=auto&rev=512351
==============================================================================
---
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadLinkTest.java
(added)
+++
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadLinkTest.java
Tue Feb 27 10:19:22 2007
@@ -0,0 +1,73 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package wicket.markup.html.link;
+
+import wicket.WicketTestCase;
+import wicket.protocol.http.MockHttpServletResponse;
+import wicket.protocol.http.MockServletContext;
+
+/**
+ * Tests DownloadLink
+ *
+ * @author <a href="mailto:[EMAIL PROTECTED]">Jean-Baptiste Quenot</a>
+ */
+public class DownloadLinkTest extends WicketTestCase
+{
+ private static final String APPLICATION_X_CUSTOM =
"application/x-custom";
+
+ public DownloadLinkTest(String name)
+ {
+ super(name);
+ }
+
+ public void testTextDownloadLink()
+ {
+ tester.startPage(DownloadPage.class);
+ tester.clickLink(DownloadPage.TEXT_DOWNLOAD_LINK);
+ assertEquals("text/plain", getContentType());
+ assertEquals(0, getContentLength());
+ }
+
+ public void testPdfDownloadLink()
+ {
+ tester.startPage(DownloadPage.class);
+ tester.clickLink(DownloadPage.PDF_DOWNLOAD_LINK);
+ assertEquals("application/pdf", getContentType());
+ assertEquals(DownloadPage.HELLO_WORLD.length(),
getContentLength());
+ }
+
+ public void testCustomTypeDownloadLink()
+ {
+ tester.startPage(DownloadPage.class);
+
((MockServletContext)tester.getApplication().getServletContext()).addMimeType("custom",
+ APPLICATION_X_CUSTOM);
+ tester.clickLink(DownloadPage.CUSTOM_DOWNLOAD_LINK);
+ assertEquals(APPLICATION_X_CUSTOM, getContentType());
+ }
+
+ private String getContentType()
+ {
+ return
((MockHttpServletResponse)tester.getWicketResponse().getHttpServletResponse())
+ .getHeader("Content-Type");
+ }
+
+ private int getContentLength()
+ {
+ return
Integer.parseInt(((MockHttpServletResponse)tester.getWicketResponse()
+
.getHttpServletResponse()).getHeader("Content-Length"));
+ }
+}
Propchange:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadLinkTest.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadLinkTest.java
------------------------------------------------------------------------------
svn:keywords = Id
Added:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.html
URL:
http://svn.apache.org/viewvc/incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.html?view=auto&rev=512351
==============================================================================
---
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.html
(added)
+++
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.html
Tue Feb 27 10:19:22 2007
@@ -0,0 +1,7 @@
+<html>
+ <body bgcolor="white">
+ <span wicket:id="textDownload"></span>
+ <span wicket:id="pdfDownload"></span>
+ <span wicket:id="customDownload"></span>
+ </body>
+</html>
Propchange:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.html
------------------------------------------------------------------------------
svn:eol-style = native
Added:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.java
URL:
http://svn.apache.org/viewvc/incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.java?view=auto&rev=512351
==============================================================================
---
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.java
(added)
+++
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.java
Tue Feb 27 10:19:22 2007
@@ -0,0 +1,51 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package wicket.markup.html.link;
+
+import java.io.File;
+import java.io.FileWriter;
+import java.io.IOException;
+
+import wicket.markup.html.WebPage;
+
+public class DownloadPage extends WebPage
+{
+ public static final String HELLO_WORLD = "Hello, World!";
+ public static final String TEXT_DOWNLOAD_LINK = "textDownload";
+ public static final String PDF_DOWNLOAD_LINK = "pdfDownload";
+ public static final String CUSTOM_DOWNLOAD_LINK = "customDownload";
+
+ /**
+ *
+ */
+ private static final long serialVersionUID = 1L;
+
+ public DownloadPage() throws IOException
+ {
+ File textFile = File.createTempFile("Download", ".txt");
+ add(new DownloadLink(TEXT_DOWNLOAD_LINK, textFile));
+
+ File pdfFile = File.createTempFile("Download", ".pdf");
+ FileWriter writer = new FileWriter(pdfFile);
+ writer.write(HELLO_WORLD);
+ writer.close();
+ add(new DownloadLink(PDF_DOWNLOAD_LINK, pdfFile));
+
+ File customFile = File.createTempFile("Download", ".custom");
+ add(new DownloadLink(CUSTOM_DOWNLOAD_LINK, customFile));
+ }
+}
Propchange:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/markup/html/link/DownloadPage.java
------------------------------------------------------------------------------
svn:keywords = Id
Modified:
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/protocol/http/WebRequestCodingStrategyTest.java
URL:
http://svn.apache.org/viewvc/incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/protocol/http/WebRequestCodingStrategyTest.java?view=diff&rev=512351&r1=512350&r2=512351
==============================================================================
---
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/protocol/http/WebRequestCodingStrategyTest.java
(original)
+++
incubator/wicket/branches/wicket-1.x/wicket/src/test/java/wicket/protocol/http/WebRequestCodingStrategyTest.java
Tue Feb 27 10:19:22 2007
@@ -24,6 +24,8 @@
/**
* Tests for WebRequestCodingStrategy
+ *
+ * @author <a href="mailto:[EMAIL PROTECTED]">Jean-Baptiste Quenot</a>
*/
public class WebRequestCodingStrategyTest extends TestCase
{