Class HttpPostRequestEncoder

  • All Implemented Interfaces:
    ChunkedInput<HttpContent>

    public class HttpPostRequestEncoder
    extends java.lang.Object
    implements ChunkedInput<HttpContent>
    This encoder will help to encode Request for a FORM as POST.

    According to RFC 7231, POST, PUT and OPTIONS allow to have a body. This encoder will support widely all methods except TRACE since the RFC notes for GET, DELETE, HEAD and CONNECT: (replaces XXX by one of these methods)

    "A payload within a XXX request message has no defined semantics; sending a payload body on a XXX request might cause some existing implementations to reject the request."

    On the contrary, for TRACE method, RFC says:

    "A client MUST NOT send a message body in a TRACE request."

    • Field Detail

      • percentEncodings

        private static final java.util.Map.Entry[] percentEncodings
      • factory

        private final HttpDataFactory factory
        Factory used to create InterfaceHttpData
      • request

        private final HttpRequest request
        Request to encode
      • charset

        private final java.nio.charset.Charset charset
        Default charset to use
      • isChunked

        private boolean isChunked
        Chunked false by default
      • bodyListDatas

        private final java.util.List<InterfaceHttpData> bodyListDatas
        InterfaceHttpData for Body (without encoding)
      • multipartHttpDatas

        final java.util.List<InterfaceHttpData> multipartHttpDatas
        The final Multipart List of InterfaceHttpData including encoding
      • isMultipart

        private final boolean isMultipart
        Does this request is a Multipart request
      • multipartDataBoundary

        java.lang.String multipartDataBoundary
        If multipart, this is the boundary for the flobal multipart
      • multipartMixedBoundary

        java.lang.String multipartMixedBoundary
        If multipart, there could be internal multiparts (mixed) to the global multipart. Only one level is allowed.
      • headerFinalized

        private boolean headerFinalized
        To check if the header has been finalized
      • isLastChunk

        private boolean isLastChunk
        Does the last non empty chunk already encoded so that next chunk will be empty (last chunk)
      • isLastChunkSent

        private boolean isLastChunkSent
        Last chunk already sent
      • currentFileUpload

        private FileUpload currentFileUpload
        The current FileUpload that is currently in encode process
      • duringMixedMode

        private boolean duringMixedMode
        While adding a FileUpload, is the multipart currently in Mixed Mode
      • globalBodySize

        private long globalBodySize
        Global Body size
      • globalProgress

        private long globalProgress
        Global Transfer progress
      • iterator

        private java.util.ListIterator<InterfaceHttpData> iterator
        Iterator to be used when encoding will be called chunk after chunk
      • currentBuffer

        private ByteBuf currentBuffer
        The ByteBuf currently used by the encoder
      • currentData

        private InterfaceHttpData currentData
        The current InterfaceHttpData to encode (used if more chunks are available)
      • isKey

        private boolean isKey
        If not multipart, does the currentBuffer stands for the Key or for the Value
    • Method Detail

      • cleanFiles

        public void cleanFiles()
        Clean all HttpDatas (on Disk) for the current request.
      • isMultipart

        public boolean isMultipart()
        True if this request is a Multipart request
        Returns:
        True if this request is a Multipart request
      • initDataMultipart

        private void initDataMultipart()
        Init the delimiter for Global Part (Data).
      • initMixedMultipart

        private void initMixedMultipart()
        Init the delimiter for Mixed Part (Mixed).
      • getNewMultipartDelimiter

        private static java.lang.String getNewMultipartDelimiter()
        Returns:
        a newly generated Delimiter (either for DATA or MIXED)
      • getBodyListAttributes

        public java.util.List<InterfaceHttpData> getBodyListAttributes()
        This getMethod returns a List of all InterfaceHttpData from body part.
        Returns:
        the list of InterfaceHttpData from Body part
      • addBodyFileUpload

        public void addBodyFileUpload​(java.lang.String name,
                                      java.io.File file,
                                      java.lang.String contentType,
                                      boolean isText)
                               throws HttpPostRequestEncoder.ErrorDataEncoderException
        Add a file as a FileUpload
        Parameters:
        name - the name of the parameter
        file - the file to be uploaded (if not Multipart mode, only the filename will be included)
        contentType - the associated contentType for the File
        isText - True if this file should be transmitted in Text format (else binary)
        Throws:
        java.lang.NullPointerException - for name and file
        HttpPostRequestEncoder.ErrorDataEncoderException - if the encoding is in error or if the finalize were already done
      • addBodyFileUpload

        public void addBodyFileUpload​(java.lang.String name,
                                      java.lang.String filename,
                                      java.io.File file,
                                      java.lang.String contentType,
                                      boolean isText)
                               throws HttpPostRequestEncoder.ErrorDataEncoderException
        Add a file as a FileUpload
        Parameters:
        name - the name of the parameter
        file - the file to be uploaded (if not Multipart mode, only the filename will be included)
        filename - the filename to use for this File part, empty String will be ignored by the encoder
        contentType - the associated contentType for the File
        isText - True if this file should be transmitted in Text format (else binary)
        Throws:
        java.lang.NullPointerException - for name and file
        HttpPostRequestEncoder.ErrorDataEncoderException - if the encoding is in error or if the finalize were already done
      • addBodyFileUploads

        public void addBodyFileUploads​(java.lang.String name,
                                       java.io.File[] file,
                                       java.lang.String[] contentType,
                                       boolean[] isText)
                                throws HttpPostRequestEncoder.ErrorDataEncoderException
        Add a series of Files associated with one File parameter
        Parameters:
        name - the name of the parameter
        file - the array of files
        contentType - the array of content Types associated with each file
        isText - the array of isText attribute (False meaning binary mode) for each file
        Throws:
        java.lang.IllegalArgumentException - also throws if array have different sizes
        HttpPostRequestEncoder.ErrorDataEncoderException - if the encoding is in error or if the finalize were already done
      • finalizeRequest

        public HttpRequest finalizeRequest()
                                    throws HttpPostRequestEncoder.ErrorDataEncoderException
        Finalize the request by preparing the Header in the request and returns the request ready to be sent.
        Once finalized, no data must be added.
        If the request does not need chunk (isChunked() == false), this request is the only object to send to the remote server.
        Returns:
        the request object (chunked or not according to size of body)
        Throws:
        HttpPostRequestEncoder.ErrorDataEncoderException - if the encoding is in error or if the finalize were already done
      • isChunked

        public boolean isChunked()
        Returns:
        True if the request is by Chunk
      • fillByteBuf

        private ByteBuf fillByteBuf()
        Returns:
        the next ByteBuf to send as an HttpChunk and modifying currentBuffer accordingly
      • encodeNextChunkMultipart

        private HttpContent encodeNextChunkMultipart​(int sizeleft)
                                              throws HttpPostRequestEncoder.ErrorDataEncoderException
        From the current context (currentBuffer and currentData), returns the next HttpChunk (if possible) trying to get sizeleft bytes more into the currentBuffer. This is the Multipart version.
        Parameters:
        sizeleft - the number of bytes to try to get from currentData
        Returns:
        the next HttpChunk or null if not enough bytes were found
        Throws:
        HttpPostRequestEncoder.ErrorDataEncoderException - if the encoding is in error
      • encodeNextChunkUrlEncoded

        private HttpContent encodeNextChunkUrlEncoded​(int sizeleft)
                                               throws HttpPostRequestEncoder.ErrorDataEncoderException
        From the current context (currentBuffer and currentData), returns the next HttpChunk (if possible) trying to get sizeleft bytes more into the currentBuffer. This is the UrlEncoded version.
        Parameters:
        sizeleft - the number of bytes to try to get from currentData
        Returns:
        the next HttpChunk or null if not enough bytes were found
        Throws:
        HttpPostRequestEncoder.ErrorDataEncoderException - if the encoding is in error
      • close

        public void close()
                   throws java.lang.Exception
        Description copied from interface: ChunkedInput
        Releases the resources associated with the input.
        Specified by:
        close in interface ChunkedInput<HttpContent>
        Throws:
        java.lang.Exception
      • readChunk

        @Deprecated
        public HttpContent readChunk​(ChannelHandlerContext ctx)
                              throws java.lang.Exception
        Deprecated.
        Specified by:
        readChunk in interface ChunkedInput<HttpContent>
        Parameters:
        ctx - The context which provides a ByteBufAllocator if buffer allocation is necessary.
        Returns:
        the fetched chunk. null if there is no data left in the stream. Please note that null does not necessarily mean that the stream has reached at its end. In a slow stream, the next chunk might be unavailable just momentarily.
        Throws:
        java.lang.Exception
      • calculateRemainingSize

        private int calculateRemainingSize()
      • isEndOfInput

        public boolean isEndOfInput()
                             throws java.lang.Exception
        Description copied from interface: ChunkedInput
        Return true if and only if there is no data left in the stream and the stream has reached at its end.
        Specified by:
        isEndOfInput in interface ChunkedInput<HttpContent>
        Throws:
        java.lang.Exception
      • length

        public long length()
        Description copied from interface: ChunkedInput
        Returns the length of the input.
        Specified by:
        length in interface ChunkedInput<HttpContent>
        Returns:
        the length of the input if the length of the input is known. a negative value if the length of the input is unknown.