[ 
https://issues.apache.org/jira/browse/CXF-9057?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=17886376#comment-17886376
 ] 

Johannes Herr commented on CXF-9057:
------------------------------------

Hi Andriy, I will create a small project to demonstrate the problem. Might take 
until next week though.

> Chunked Stream is closed regularly when Exception is thrown
> -----------------------------------------------------------
>
>                 Key: CXF-9057
>                 URL: https://issues.apache.org/jira/browse/CXF-9057
>             Project: CXF
>          Issue Type: Bug
>    Affects Versions: 3.5.8
>            Reporter: Johannes Herr
>            Priority: Major
>
> In response to SOAP requests served by Apache CXF we send large datasets 
> streamed directly from a database. Because of the size of the data, chunked 
> encoding is used. Unfortunately when a database error occurs and an exception 
> is thrown while data is sent, the client will receive a regular ending to the 
> chunked data stream. That means he has no way to recognise that an error 
> occurred and that he has only received a partial file.
> To be more specific the response looks somewhat like this:
> {code:java}
> HTTP/1.1 200 OK
> Date: Tue, 10 Sep 2024 16:17:45 GMT
> Content-Type: multipart/related; type="application/xop+xml"; 
> boundary="uuid:49aa53f9-ec29-4f1a-bc07-a21256c2f940"; 
> start="<root.mess...@cxf.apache.org>"; start-info="text/xml"
> Transfer-Encoding: chunked
> Server: Jetty(10.0.21)
> 8000
> --uuid:49aa53f9-ec29-4f1a-bc07-a21256c2f940
> Content-Type: application/xop+xml; charset=UTF-8; type="text/xml"
> Content-Transfer-Encoding: binary
> Content-ID: <root.mess...@cxf.apache.org>
> <soap:Envelope 
> xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/";>[...]</soap:Envelope>
> --uuid:49aa53f9-ec29-4f1a-bc07-a21256c2f940
> Content-Type:
> Content-Transfer-Encoding: binary
> Content-ID: <03d4ea67-6e8b-4d1f-91b0-b63208989f9...@cxf.apache.org>
> xxxxxxxxxxxx[...]xxxxxxx
> 356
> xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
> 0
> {code}
> That means the response ends with the "0" entry, indicating that the transfer 
> is complete.
> What should happen instead is that the response should be closed without 
> sending the final 0 entry. ([https://stackoverflow.com/a/17203961/136247])
> For example when we use a Servlet to stream data to a client a throw an 
> exception the result will look something like this:
> {code:java}
> HTTP/1.1 200 OK
> Date: Fri, 13 Sep 2024 09:31:48 GMT
> Content-Type: text/plain;charset=utf-8
> Transfer-Encoding: chunked
> Server: Jetty(10.0.21)
> 8
> Chunk 1
> 8
> Chunk 2
> 8
> Chunk 3
> 8
> Chunk 4
> 8
> Chunk 5
> {code}
> Here there is no closing 0 marker. As a result clients can recognise the 
> error. (Curl will report "curl: (18) transfer closed with outstanding read 
> data remaining", Chrome "Failed to load resource: 
> net::ERR_INCOMPLETE_CHUNKED_ENCODING")
> CXF should do the same and not end the chunked stream regularly, when an 
> exception is thrown.
> I have tested with Tomcat and Jetty. Both show the same behaviour.
> To provide some detail, Exceptions are caught by CXF here:
> org/apache/cxf/phase/PhaseInterceptorChain.java:328
> {code:java}
>                 } catch (RuntimeException ex) {
>                     if (!faultOccurred) {
>                         faultOccurred = true;
>                         wrapExceptionAsFault(message, ex);
>                     }
>                     state = State.ABORTED;
>                 }
> {code}
> The exception is logged, but not rethrown.
> If the exception would be thrown, for instance Tomcats ErrorReportValve would 
> shut down the output and thereby prevent the end of the input and closing 0 
> to be written.
> org/apache/catalina/valves/ErrorReportValve.java:112
> {code:java}
>                     // Now close immediately to signal to the client that
>                     // something went wrong
>                     response.getCoyoteResponse().action(ActionCode.CLOSE_NOW,
>                             
> request.getAttribute(RequestDispatcher.ERROR_EXCEPTION));
> {code}
> Without an exception to prevent this, a regular end of the stream will be 
> written by
> org/apache/catalina/connector/CoyoteAdapter.java:371
> response.finishResponse();
> In Summary: CXF ends a chunked encoded stream in a regular way in spite of 
> exceptions occurring, which makes it impossible for clients to recognise that 
> they have downloaded partial and therefore corrupt data.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

Reply via email to