建议使用以下浏览器,以获得最佳体验。 IE 9.0+以上版本 Chrome 31+ 谷歌浏览器 Firefox 30+ 火狐浏览器
请选择 进入手机版 | 继续访问电脑版
设置昵称

在此一键设置昵称,即可参与社区互动!

确定
我再想想
选择版块

大象

发帖: 3粉丝: 0

级别 : 新手上路

Rank: 1

发消息 + 关注

发表于2018-6-30 15:19:00 107645 楼主 显示全部楼层
[教程] 使用Content-MD5上传对象出现错误的解决办法

【问题现象描述】


上传到OBS中的对象的使用图片转码后显示不正常,经过初步分析发现上传的原图是破损的。


我们建议在上传文件时设置Content-MD5值, 以保证服务端对上传的对象进行完整性校验。进一步分析发现客户端使用Android SDK上传对象,设置Content-MD5值后上传出现如下日志:

ResponseCode: 400, ResponseStatus: Bad Request, XML ErrorMessage:


BadDigest

The Content-MD5 you specified didnot match what we received.

101200000163D6154895799445D7A6F8

  ……

  


根据此日志表明客户端MD5值与服务端不匹配,两端 MD5值计算方法不一样。


【问题的根因】


在客户端计算Content-MD5值时先计算MD5加密的二进制数组(128),  再将二进制数组转成了字符串后再进行的Base64编码。

而服务端生成Content-MD5原理是:先计算MD5加密的二进制数组(128位),  再对这个二进制进行Base64编码


因此客户端在计算Content-MD5时需要与服务端原理一致,正确的代码(以AndroidSDK为例):


public staticString getMD5File(File file) {

   FileInputStream in = null;

   try {

       in = new FileInputStream(file);

       FileChannel channel = in.getChannel();

       MappedByteBuffer buffer = channel.map(FileChannel.MapMode.READ_ONLY, 0,file.length());

       MessageDigest md = MessageDigest.getInstance("MD5");

       md.update(buffer);

       return Base64.encodeToString(md.digest(), Base64.NO_WRAP);

   } catch (NoSuchAlgorithmException | IOException e) {

       e.printStackTrace();

   } finally {

       if (in != null) {

           try {

               in.close();

           } catch (IOException ignored) {

           }

       }

   }

   return "";

}


NO_WRAP参数说明:使用Android SDK  Base64编码时要使用NO_WRAP参数

【问题结果】

客户端侧修改Content-MD5方法后问题解决。

回复 举报
分享

分享文章到朋友圈

分享文章到微博

西秦公子

发帖: 0粉丝: 3

级别 : 版主

Rank: 7Rank: 7Rank: 7

发消息 + 关注

发表于2018-7-1 09:05:09 沙发 显示全部楼层
感谢分享!对于后面出现同样问题的人来说,有很大的帮助。如果在官方的 SDK 默认开启这个就好了。
点赞 回复 举报

天天加班

发帖: 1粉丝: 0

级别 : 新手上路

Rank: 1

发消息 + 关注

发表于2018-7-4 10:34:17 板凳 显示全部楼层
非常有价值!
点赞 回复 举报

yd_2012_bp...

发帖: 1粉丝: 0

级别 : 新手上路

Rank: 1

发消息 + 关注

发表于2018-7-4 10:35:17 地板 显示全部楼层
牛逼,你的分享很有意义
点赞 回复 举报

英勇的馒头

发帖: 0粉丝: 0

级别 : 新手上路

Rank: 1

发消息 + 关注

发表于2018-7-4 10:39:11 5# 显示全部楼层
查了下,NO_WRAP 这个参数意思是略去所有的换行符。
就是说默认服务端计算的方法是忽略换行符的,客户端如果不忽略,就对不上。
不过觉得服务端做的这个处理看起来有点奇怪。。。为什么要忽略换行呢?

点赞 回复 举报

tayoushuo

发帖: 0粉丝: 0

级别 : 新手上路

Rank: 1

发消息 + 关注

发表于2018-7-4 10:40:05 6# 显示全部楼层
有用!
点赞 回复 举报

游客

您需要登录后才可以回帖 登录 | 立即注册