Details
Description
Adobe Acrobat provides "Fast Web View" property for a PDF document. This allows the Acrobat plug-in for web browsers, to quickly download the desired page and then download the remaining by making multiple HTTP fetches. This is very useful for displaying large PDF documents.
The current version of jetty (specifically DefaultServlet.java) downloads the entire PDF file before displaying the document, even if the "Fast Web View" property is enabled. However, Apache Web Server, handles this correctly.
Since this was a major requirement for my project. I ended up writing my own Filter to deal with this issue. Filter is a less invasive way to deal with this issue. A more invasive way is to modify the code in DefaultServlet.java to deal with it.
I have attached the source code for the PDFFilter.java
Notice, I am not checking for content type PDF in the filter. I would assume that it will be handled in web.xml:
<display-name>Test WebApp</display-name>
<filter>
<filter-name>PDFFilter</filter-name>
<filter-class>org.mortbay.jetty.filters.PDFFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>PDFFilter</filter-name>
<url-pattern>/pdf/*</url-pattern>
</filter-mapping>
Attachments
-
$i18n.getText("admin.common.words.hide")
- bad.zip
- 29/Jan/10 6:02 PM
- 382 kB
- Richard Beck
-
- bad/bad.pcap 561 kB
- bad/p1.txt 4 kB
- bad/p2.txt 4 kB
- bad/request.log 0.1 kB
- bad/webdefault.xml.values.txt 0.0 kB
-
$i18n.getText("admin.common.words.hide")
- config.zip
- 09/Feb/10 8:17 AM
- 34 kB
- Richard Beck
-
- webdefault.xml 24 kB
- jetty.xml 10 kB
-
$i18n.getText("admin.common.words.hide")
- fixed.zip
- 17/Feb/10 1:49 PM
- 3.54 MB
- Richard Beck
-
- fixed.pcap 4.92 MB
-
$i18n.getText("admin.common.words.hide")
- good.zip
- 29/Jan/10 6:02 PM
- 3.52 MB
- Richard Beck
-
- good/good.pcap 4.85 MB
- good/p1.txt 4 kB
- good/p2.txt 4 kB
- good/p3.txt 4 kB
- good/p4.txt 4 kB
- good/p5.txt 4 kB
- good/p6.txt 4 kB
- good/p7.txt 203 kB
- good/request.log 0.3 kB
- good/webdefault.xml.values.txt 0.0 kB
-
- PDFFilter.java
- 15/Apr/09 11:33 AM
- 2 kB
- Cyber Jetty
Activity
Now, I know there is code in place in DefaultServlet to handle byte ranges but it does not work for PDF documents with fast web view property enabled. Take a look at the headers below. When I try to view a PDF document without the plug-in, the entire document is downloaded in one fetch. However, if I use the plug-in, then the Acrobat plug-in makes multiple byte-range fetches and as a consequence, the document becomes viewable immediately.
As far as, I could understand the behavior of Acrobat plug-in, when an initial request comes in for a PDF document, it doesn't send a byte range request. It expects a response from the webserver. The response can be either an entire document or a header ACCEPT-RANGES = bytes. Once it sees that, the acrobat plug-in then makes byte range requests in subsequent fetches.
Now I think DefaultServlet handles this correctly and that is why I think that PDF documents should handled via a Filter. However, if you think that DefaultServlet should handle this case, that is fine with me too.
In the PDF Filter I have added the "HTTP Header Connection: Close" so the connections close after every partial content request is fulfilled. Otherwise, the Acrobat plug-in keeps these connections open until a connection timeout happens.
(HTTP Headers without the plug-in![]()
URL
====
http://localhost:8080/pdf/J_VOL001_N03.pdf
Request Headers
===============
Host: localhost:8080
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.0.8) Gecko/2009032609 Firefox/3.0.8
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Cookie: JSESSIONID=7olh60cwmke0
Response Headers
================
Content-Type: application/pdf
Content-Length: 2270915
Last-Modified: Tue, 17 Feb 2009 04:56:31 GMT
Server: Jetty(6.1.14)
(HTTP Headers with the plug-in![]()
1) Initial request
----------------------
URL
====
http://localhost:8080/pdf/J_VOL001_N03.pdf
Request Headers
===============
Host: localhost:8080
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.0.8) Gecko/2009032609 Firefox/3.0.8
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Cookie: JSESSIONID=1jrmnop7xu8xg
Response Headers
================
Content-Type: application/pdf
Accept-Ranges: bytes
Content-Length: 2270915
Last-Modified: Tue, 17 Feb 2009 04:56:31 GMT
Server: Jetty(6.1.14)
Response Status
===============
200 OK
2) Second byte range fetch.
-------------------------------------
URL
===
http://localhost:8080/pdf/J_VOL001_N03.pdf
Request Headers
===============
Host: localhost:8080
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.0.8) Gecko/2009032609 Firefox/3.0.8
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=16384-264758,16384-16385
Cookie: JSESSIONID=1jrmnop7xu8xg
Response Headers
================
Accept-Ranges: bytes
Content-Type: multipart/byteranges; boundary=jetty22693155ftllw33i
Last-Modified: Tue, 17 Feb 2009 04:56:31 GMT
Connection: close
Server: Jetty(6.1.14)
Response Status
===============
206 (Partial Content)
NOTE: There were 3-4 more subsequent partial content requests before the entire document was downloaded.
By "plugin" do you mean your filter?
What I don't understand is why there is no Accept-Ranges: bytes header
in the response for http://localhost:8080/pdf/J_VOL001_N03.pdf
If that is served by Jetty's default servlet, then the accept ranges header
should be set?
How is that initial request being served?
Ah - I see a problem where the Accept-ranges header is not being set for some cached content.
working on a fix.
I've committed a fix that makes sure the accept-ranges header is set for all content sent by the default servlet (cached and gzipped).
Hi,
Although the "accept-ranges" triggers multiple requests for partial contents from the Adobe Acrobat plugin. However, each connection to fetch partial content remains open even if the partial content has been retreived. I wonder, if each connection time outs. As a consequence, the PDF download performance seems to be sluggish.
To solve this problem, in my PDFFilter, which I had attached with this issue earlier, I am setting the HttpHeaders.CONNECTION to CLOSE once the partial content download is finished, which solves the above problem.
Best way to debug is to test it using Firefox and firebug. You will notice that connection for partial contents closes after sometime.
can you attach a pdf that you are seeing this issue with. Also can you tell me the version of the plugin that you're using.
I am using Adobe Acrobat Plugin 9. Unfortunately, I cannot upload the PDF document in question due to privacy issues. However, I tested it on many pdf documents especially if the document is large in the order of 7-8 MB and I faced the same issue.
I'm seeing similar behavior. I'm downloading a fairly large PDF (5-10MB). If I have acceptRanges=true for DefaultServlet, the Acrobat Reader (version 9.2) attempts to download the file in byte ranges. This downloads maybe approximately a tenth of document in Firefox 3.5 (closer to 1/5 in IE 8), then the CPU usage goes very high and both the browser and the Acrobat plugin become unresponsive.
If I turn acceptRanges to false, the entire document downloads in seconds (in one full HTTP response).
acceptRanges = false
====================================
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Cookie: JSESSIONID=19tq1e5grnjw
HTTP/1.x 200 OK
Content-Type: application/pdf
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Content-Length: 12159738
Server: Jetty(6.1.21)
----------------------------------------------------------
acceptRanges = true
=================================
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 200 OK
Content-Type: application/pdf
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Content-Length: 12159738
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=16384-186401,16384-16385
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty8609603g0vfg6t0
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=12155588-12159683,12155588-12155589
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty10815424g0vfg6tf
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=12159684-12159737,12159684-12159685
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty309427g0vfg6v6
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=11677269-11681364,11677269-11677270
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty23559693g0vfg6ww
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=11681365-11685252,11681365-11681366
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty12645594g0vfg6yn
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=11666576-11667669,12154706-12155587
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty25471206g0vfg719
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=11685253-11693719,11795666-11807959,9518904-9521160,9518633-9518903,9518356-9518632
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty7124377g0vfhh43
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=9598369-9600227,9521161-9565268,9565269-9598368,9600228-9622466,186402-188174
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty10659671g0vfhh5e
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=11807960-11812039,9629852-9655663,188175-188585,9622467-9622547,11812040-11820199
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty29421438g0vfhh5u
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=9697661-9698767,9697577-9697660,9697493-9697576,9697409-9697492,9697325-9697408
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty16254627g0vfhh7k
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=9697241-9697324,9697157-9697240,9697073-9697156,9696989-9697072,9696905-9696988
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty17501040g0vfhh9q
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
----------------------------------------------------------
http://localhost/help/UserManual.pdf
GET /help/UserManual.pdf HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Range: bytes=9696821-9696904,9696737-9696820,9696653-9696736,9696569-9696652,9696485-9696568
Cookie: JSESSIONID=1p7q4urppa6tp
HTTP/1.x 206 Partial Content
Content-Type: multipart/byteranges; boundary=jetty13488960g0vfhhbx
Last-Modified: Fri, 16 Oct 2009 19:48:04 GMT
Accept-Ranges: bytes
Server: Jetty(6.1.21)
I'm seeing the above behavior whether or not "Fast Web View" is actually enabled in the PDF file itself.
Ory,
thanks for the excellent detail.
Any chance of getting a copy of the actual PDF you were trying to serve?
It might be to large to attach here, so maybe email it to my gregw@mortbay.com
The interesting thing is that we have neither chunked content nor a content-length, so
that might be putting the plugin into a spin. I'm pretty sure it should have one or the other... probably content length as we should be able to work that out exactly.
looking into this before the next release.
In rfc2616 4.4 Message length, it says:
4.If the message uses the media type "multipart/byteranges", and the
ransfer-length is not otherwise specified, then this self-
elimiting media type defines the transfer-length. This media type
UST NOT be used unless the sender knows that the recipient can arse
it; the presence in a request of a Range header with ultiple byte-
range specifiers from a 1.1 client implies that the lient can parse
multipart/byteranges responses.
A range header might be forwarded by a 1.0 proxy that does not
understand multipart/byteranges; in this case the server MUST
delimit the message using methods defined in items 1,3 or 5 of
this section.
So do you have a proxy involved?
Ory et al,
I've committed to jetty-6 and jetty-7 a fix that always sends a content-length with a range response. I'm hoping this will stop the acroread plugin going crazy.
Can you check and try http://svn.codehaus.org/jetty/jetty/branches/jetty-6.1
cheers
Unfortunately I can't include the particular PDF because it has some proprietary information in it. I had tried a few PDFs in the 5-10MB range. I'll see if the snapshot build you pointed to works next.
This addresses the issue I saw. The large PDFs download correctly now.
I have experienced similar problems to those mentioned here as well as on other threads. We have always had to set the acceptRanges value to false in order to load large PDF files with Jetty. When I saw that this issue was fixed I was hoping it would fix a similar issue we were having with version 6.1.20. As it turned out our problem was due to incorrectly (not) referencing the webdefault.xml file from within our context.xml file. So, long story short I was able to get 6.1.20 to work but only if acceptRanges was false.
Since the real fix for acceptRanges was introduced in 6.1.22 I downloaded that version, but it still did not work. This is what I noticed:
1) If acceptRanges is false everything works.
2) If acceptRanges is true and the Jetty server is on the same machine as the browser everything works.
3) If acceptRanges is true and the Jetty server is on another machine the PDF never loads - it doesn't matter whether "Allow fast web view" is on or off.
The browser status bar indicates Downloaded (1.74 MB of 4.43 MB) : <URL of PDF> but it stops loading and eventually (several minutes later) Adobe displays a message "The file is damaged and could not be repaired". Different versions of Adobe display different error message. The above message is displayed from Adobe 9.3. Version 8.x returned a message indicating some I/O error had occurred.
I then changed the value for maxCachedFileSize from the default of 10000000 (10 MB) to 1000000 (1 MB) and the files downloaded correctly with acceptRanges set to true. The particular file I was trying to load was approximately 4.6 MB and as long as the value for maxCachedFileSize was less than the actual file size everything worked correctly.
Hopefully I have not set up anything incorrectly, but I just wanted to share these observations in case it helps someone else.
Richard,
I've reopened this issue... although it does sound like it could be a slightly different issue - as the clue about the cache size is very curious!
What we need to make progress is to see a tcpdump (or wireshark or similar) trace of the network traffic while
you attempt a download in case 3) of your comment
regards
I am attaching the Wireshark trace of the good and bad attempts to download the PDF. The only difference being the value of maxCachedFileSize. Good = 1000000, bad = 10000000
thanks - I'll look at these as soon as possible... probably mid week.
Richard,
Greg asked me to recreate the problem you are experiencing, so I had set up a test environment with Jetty 6.1.22 to download a 5.9MB PDF file using Firefox 3.x browser both with Acrobat 8.x and Acrobat 9.3. I have tried setting maxCachedFileSize parameters to both 1,000,000 and 10,000,000 while having acceptRanges set to true and have been unable to get it to fail.
It appears from the Wireshark traces you provided that you are using MSIE 6.0. Could you please try the same scenario using Firefox 3.x and let us know if it works for you.
Also, it would be very helpful if you could provide the configuration that you are using for the connector that is configured in your Jetty instance so that we can analyze the same.
Thanks,
Michael
I am not sure when I will be able to provide you with the dump info. I was out of work for a few days and we are nearing the end of our release. We have the same issue with IE 7 and 8. We only support IE so there was no reason to test with Firefox.
Please note the following:
1) If the Jetty install and the browser are on the same machine the file always downloads successfully.
2) I always clear my browser cache before running any of these tests. I believe if the file is cached there are circumstances when the file will download, but I have not really been focusing on that scenario.
One of the stranger things I noticed was that when I have Fiddler running, in order to get the http headers, the download always works, no matter what any of the Jetty configuration settings are.
Attached are the jetty.xml and webdefault.xml files.
Rich
Looking at Michaels analysis of your dumps, I can see something
strange
In response to
GET /rm/iqm/pdf/stateguidelines/Colorado.pdf HTTP/1.1
Jetty responds with
HTTP/1.1 200 OK
Accept-Ranges: bytes
Content-Length: 4654100
The next request is then
GET /rm/iqm/pdf/stateguidelines/Colorado.pdf HTTP/1.1
Range: bytes=4650004-4654099
which is asking for the last bytes. This looks perfectly
legal, but the response is:
HTTP/1.1 416 Requested Range Not Satisfiable
So this is something that we need to investigate more.
I will try to replicate this in a test harness.
I've been unable to reproduce the conditions for this problem.
The only way I can see that jetty would send a 416 response like that, would be for it to not know the content-length of the resource that it was trying to serve.
So I've made some defensive changes to make sure that all content length sources are tried, then failing that if the content length is not known, the entire content is served.
Could you try this out by either building jetty or downloading the latest snapshot jar from:
http://oss.sonatype.org/content/groups/jetty-with-staging/org/mortbay/jetty/jetty/6.1-SNAPSHOT/
Good news. I downloaded jetty-6.1-20100215.035415-21.jar and re-ran the test. The PDF downloaded successfully.
I am currently connected over VPN and the Wireshark dump does not seem to be capturing the http data correctly. I can re-run the test with a dump tomorrow from my office if you like.
Thanks,
Rich
Richard,
thanks for testing this.
The dump would be useful to confirm that all is ok.
Hopefully we will be doing releases in the next 2 or 3 weeks.
cheers
I have attached fixed.zip which contains the Wireshark dump of the successful download with the latest jar file.
Hi,
As I understand it, the plugin would be making http range requests to the server. Jetty's DefaultServlet specifically supports range requests, and was known to be working with pdfs in the past, so I would have thought this would handled just fine. Do you have a wireshark or other type of dump of the http headers from one of these exchanges that shows some problem? Can you explain the purpose of the code in your filter, and why the DefaultServlet's range handling was not working/was not sufficient?
thanks
Jan