http客户端发送multipart/form-data格式报文体,报文体中是压缩包的二进制流,发送后文件损坏

基于jdk1.8,从服务器的目录下读取了zip压缩包,通过http客户端传输文件的二进制流发送到对方,二进制流要求multipart/form-part格式,并且用boundary分割,我用Stringbuffer拼的multipart/form-data格式的报文体,包含文件名,文件内容,但是通过http发送对方后,对方读到的压缩包字节数比我这边原始包字节数多,而且他读到的压缩包无法解压,提示损坏。请问是我这边拼的报文体有问题吗?读出的文件二进制流,怎么拼在Stringbuffer中?

引用 皆我百晓生 小程序回复内容作答:

从你的描述来看,可能是在拼接multipart/form-data格式的报文体时出现了问题。下面是一个示例代码,展示了如何正确拼接multipart/form-data格式的报文体,并发送压缩包的二进制流。

import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;

public class HttpClientExample {
    public static void main(String[] args) {
        String boundary = '----Boundary';
        String lineEnd = '\r\n';
        String twoHyphens = '--';

        try {
            // 读取压缩包文件
            File file = new File('path/to/your/zip/file.zip');
            FileInputStream fileInputStream = new FileInputStream(file);

            // 创建URL对象
            URL url = new URL('http://example.com/upload');
            HttpURLConnection connection = (HttpURLConnection) url.openConnection();

            // 设置请求方法为POST
            connection.setRequestMethod('POST');
            connection.setDoOutput(true);
            connection.setDoInput(true);
            connection.setUseCaches(false);
            connection.setRequestProperty('Connection', 'Keep-Alive');
            connection.setRequestProperty('Content-Type', 'multipart/form-data; boundary=' + boundary);

            // 创建输出流
            DataOutputStream outputStream = new DataOutputStream(connection.getOutputStream());

            // 写入压缩包文件的二进制流
            outputStream.writeBytes(twoHyphens + boundary + lineEnd);
            outputStream.writeBytes('Content-Disposition: form-data; name=\'file\'; filename=\'' + file.getName() + '\'' + lineEnd);
            outputStream.writeBytes(lineEnd);

            byte[] buffer = new byte[1024];
            int bytesRead;
            while ((bytesRead = fileInputStream.read(buffer)) != -1) {
                outputStream.write(buffer, 0, bytesRead);
            }

            outputStream.writeBytes(lineEnd);
            outputStream.writeBytes(twoHyphens + boundary + twoHyphens + lineEnd);

            // 关闭流
            fileInputStream.close();
            outputStream.flush();
            outputStream.close();

            // 获取响应结果
            int responseCode = connection.getResponseCode();
            if (responseCode == HttpURLConnection.HTTP_OK) {
                // 处理响应结果
                InputStream inputStream = connection.getInputStream();
                // ...
            } else {
                // 处理错误情况
                InputStream errorStream = connection.getErrorStream();
                // ...
            }

            // 断开连接
            connection.disconnect();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

请注意,上述代码仅为示例,你需要根据实际情况进行适当的修改。确保文件路径、URL、boundary等参数正确设置。另外,建议使用try-with-resources语句来自动关闭流,以确保资源的正确释放。

【以下回答由 GPT 生成】

我可以为您提供解决方案。

您在拼接multipart/form-data格式的报文体时,将文件的二进制流拼接到StringBuffer中是有问题的。因为文件的二进制流是字节流,而StringBuffer是用于拼接字符串的,不适合直接拼接字节流。

为了正确发送二进制文件,您应该使用InputStreamEntity来构建请求实体,并将其设置为HttpClient请求的实体。以下是具体步骤:

步骤1:首先,您需要获取文件的二进制流。您可以使用FileInputStream来读取文件并获取输入流,然后使用ByteArrayOutputStream来将输入流转换为字节数组。

File file = new File("path/to/file.zip");
InputStream inputStream = new FileInputStream(file);
ByteArrayOutputStream byteStream = new ByteArrayOutputStream();
byte[] buffer = new byte[4096];
int bytesRead;
while ((bytesRead = inputStream.read(buffer)) != -1) {
    byteStream.write(buffer, 0, bytesRead);
}
byte[] fileBytes = byteStream.toByteArray();

步骤2:然后,您需要创建MultipartEntity来构建请求体,并添加文件字段和文件的二进制流。

MultipartEntityBuilder builder = MultipartEntityBuilder.create();
builder.setMode(HttpMultipartMode.BROWSER_COMPATIBLE);
builder.addBinaryBody("file", fileBytes, ContentType.APPLICATION_OCTET_STREAM, "filename.zip");

HttpEntity entity = builder.build();

步骤3:最后,您需要将MultipartEntity设置为请求的实体,并将实体添加到HttpPost请求中。

HttpPost httpPost = new HttpPost("http://example.com/upload");
httpPost.setEntity(entity);

HttpClient httpClient = HttpClientBuilder.create().build();
HttpResponse response = httpClient.execute(httpPost);

请注意,以上代码是使用Apache HttpClient 4.5.x版本进行的示例。如果您使用的是其他版本,请查阅相关文档以获得正确的使用方式。

通过以上步骤,您将能够正确地发送multipart/form-data格式的HTTP请求,并保持文件的二进制流完整,接收方也将能够正常接收和解压文件。

希望能对您有所帮助!如果您还有其他问题,请随时提问。


如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^