HttpClient 上传文件接口报错“missing content-type boundary” 原因解析

问题描述:

    同事在使用HttpClient4.4.1版本上传文件时,接口报错“missing content-type boundary”。找我过来一起分析原因。部分代码如下:

            HttpPut uploadFile = new HttpPut(uri);
            uploadFile.setHeader("Authorization", "");
            uploadFile.setHeader("Content-Type", "multipart/form-data");
            uploadFile.setHeader("Ocp-Apim-Subscription-Key", key);
            uploadFile.setHeader("Authorization", bearer);
			
			 //HttpMultipartMode.RFC6532参数的设定是为避免文件名为中文时乱码
            MultipartEntityBuilder multipartEntityBuilder = MultipartEntityBuilder.create().setMode(HttpMultipartMode.RFC6532);
            multipartEntityBuilder.addBinaryBody("file",new FileInputStream(uploadFile), ContentType.APPLICATION_OCTET_STREAM,uploadFile.getName());
            HttpEntity httpEntity = multipartEntityBuilder.build();
            httpPut.setEntity(httpEntity);

            // 设置请求超时
            RequestConfig requestConfig = RequestConfig.custom().setConnectTimeout(2000).build();
            httpPut.setConfig(requestConfig);

            // 发送请求
            CloseableHttpResponse response = httpClient.execute(httpPut);

问题处理:

经过网上一顿分析查找,网上说把   

//uploadFile.setHeader("Content-Type", "multipart/form-data");

这行代码注释掉就可以。我们一试,果然接口成功调用。

问题分析:

 想必大家都和我有同样的疑问:为什么注释掉那行代码就可以了?

1、boundary是什么?有什么作用?

官方解析:

       当content-type为multipart/form-data类型时,需要用boundary指定分隔符。所以boundary后面跟的随机数,就是分隔符,后端就是通过解析到boundary的值作为分隔符来分隔参数的。

      想必大家和我一样看到这段解析时,也是不太理解。既然boundary是来分割参数的,参数是在Entity里。那么我们来看下MultipartFormEntity.writeTo()方法的源码,看看能不能找到答案。

    private final AbstractMultipartForm multipart;
    @Override
    public void writeTo(final OutputStream outstream) throws IOException {
        this.multipart.writeTo(outstream);
    }

可以看到调用的是AbstractMultipartForm.doWriteTo()

private static final ByteArrayBuffer CR_LF = encode(MIME.DEFAULT_CHARSET, "\r\n");
    private static final ByteArrayBuffer TWO_DASHES = encode(MIME.DEFAULT_CHARSET, "--");

 public void writeTo(fina
  • 8
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
当你在发送HTTP请求时设置`Content-Type`头部,有时候可能会遇到错误,这通常是因为以下几个原因: 1. **拼写或格式错误**:检查`Content-Type`字段是否正确拼写,例如应该是`"application/json"`而不是`"application/json;"`。确保没有额外的空格或分号。 2. **无效的内容类型**:确保你正在使用的MIME类型对应于你的数据格式。比如,如果你传递的是JSON数据,应设置`Content-Type: application/json`,而非文本或其他非预期类型。 3. **跨域问题**:如果在浏览器环境中,可能存在同源策略限制。除非服务器允许,否则你无法直接向其他域名发送带有特定`Content-Type`的请求。 4. **HttpClient配置**:如果你使用的是`HttpClient`,可能需要显式配置它的`DefaultRequestHeaders.ContentType`属性。确保你是在适当的时间点设置,并且是在构建请求前进行。 5. **请求方法不匹配**:如果是POST、PUT等需要携带内容类型的请求,确保方法与内容类型相匹配。GET请求通常不需要指定`Content-Type`,因为它默认为`text/plain`. 一个正确的例子: ```csharp using HttpClientHandler = System.Net.Http.HttpClientHandler; // 如果你使用的是.Net Framework,请替换为HttpClientHandler using HttpResponseMessage = System.Net.Http.HttpResponseMessage; // 同上 HttpClient client = new HttpClient(new HttpClientHandler()); client.DefaultRequestHeaders.ContentType = MediaTypeHeaderValue.Parse("application/json"); // 这里设置Content-Type string jsonPayload = "{\"key\":\"value\"}"; var content = new StringContent(jsonPayload, Encoding.UTF8, "application/json"); try { HttpResponseMessage response = await client.PostAsync("https://api.example.com/endpoint", content); // ... } catch (HttpRequestException e) { Console.WriteLine($"Request failed with status code: {e.Response?.StatusCode}"); } ```
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值