最近在帮老板做一个 Android 项目,项目中有修改头像的需求,甲方给的接口是,先将图片传到他们的服务器,返回一个 URL,然后将这个 URL 的变化修改到用户信息。(感觉有点sb)
没办法,他们给的接口如此,也只能这么做了...
然后上网查了一下,发现这玩意儿还挺麻烦的,麻烦的地方在于这个请求报文的拼凑,请求报文的格式如下图,图中也有相应的文字说明。
然后具体的代码如下
public class FileImageUpload { private static final String TAG = FileImageUpload.class.getName(); private static final int TIME_OUT = 8 * 1000; //超时时间 private static final String CHARSET = "utf-8"; //设置编码 public static final String SUCCESS = "1"; public static final String FAILURE = "0"; /** * android上传文件到服务器 * * @param file 需要上传的文件 * @param RequestURL 请求的rul * @return 返回响应的内容 */ public static String uploadFile(File file, String RequestURL, String userToken) { String BOUNDARY = "------" + UUID.randomUUID().toString(); //边界标识 随机生成 String PREFIX = "--", LINE_END = "\r\n"; String CONTENT_TYPE = "multipart/form-data"; //内容类型 try { URL url = new URL(RequestURL); HttpURLConnection conn = (HttpURLConnection) url.openConnection(); conn.setReadTimeout(TIME_OUT); conn.setConnectTimeout(TIME_OUT); conn.setDoInput(true); //允许输入流 conn.setDoOutput(true); //允许输出流 conn.setUseCaches(false); //不允许使用缓存 conn.setRequestMethod("POST"); //请求方式 conn.setRequestProperty("Charset", CHARSET); //设置编码 conn.setRequestProperty("connection", "keep-alive"); conn.setRequestProperty("ApiVersion", "5.0"); conn.setRequestProperty("ApiWay", "Android"); conn.setRequestProperty("MerId", "dc529a26-aecd-4727-86c4-cb62ad24ab99"); conn.setRequestProperty("Referer", "https://uu163yun.com/"); conn.setRequestProperty("UserToken", userToken); conn.setRequestProperty("Content-Type", CONTENT_TYPE + ";boundary=" + BOUNDARY); if (file != null) { /* 当文件不为空,把文件包装并且上传 */ OutputStream outputSteam = conn.getOutputStream(); DataOutputStream dos = new DataOutputStream(outputSteam); StringBuffer sb = new StringBuffer(); sb.append(PREFIX); sb.append(BOUNDARY); sb.append(LINE_END); /* * 这里重点注意: * name里面的值为服务器端需要key 只有这个key 才可以得到对应的文件 * filename是文件的名字,包含后缀名的 比如:abc.png */ sb.append("Content-Disposition: form-data; name=\"img\"; filename=\"" + file.getName() + "\"" + LINE_END); sb.append("Content-Type: application/octet-stream; charset=" + CHARSET + LINE_END); sb.append(LINE_END); dos.write(sb.toString().getBytes()); InputStream is = new FileInputStream(file); byte[] bytes = new byte[1024]; int len = 0; while ((len = is.read(bytes)) != -1) { dos.write(bytes, 0, len); // Log.e(TAG, "写入bytes"); } is.close(); dos.write(LINE_END.getBytes()); byte[] end_data = (PREFIX + BOUNDARY + PREFIX + LINE_END).getBytes(); dos.write(end_data); dos.flush(); /** * 获取响应码 200=成功 * 当响应成功,获取响应的流 */ int res = conn.getResponseCode(); Log.e(TAG, "response code:" + res); if (res == 200) { InputStream is_ = conn.getInputStream(); String successResponseStr = URLDecoder.decode(readInStream(is_), "utf-8"); Map<String,Object> map = new Gson().fromJson(successResponseStr, new TypeToken<HashMap<String,Object>>(){}.getType()); Log.e(TAG, map.toString()); // Log.e(TAG, map.get("url").toString()); if (map.get("result").toString().equals("OK")){ String avatarUrl = Constants.BASE_URL_IMAGE + map.get("url"); Log.e(TAG, "上传头像成功,URL:" + avatarUrl); SPUtils.getInstance(Constants.SP_NAME_GLOBAL).put("avatarUrl",avatarUrl); applyUpdate(avatarUrl); } is_.close(); return SUCCESS; } } } catch (IOException e) { e.printStackTrace(); } return FAILURE; } private static String readInStream(InputStream inputStream) { BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream)); String msg = "msg"; try { msg = bufferedReader.readLine(); } catch (IOException e) { e.printStackTrace(); } // Log.e(TAG, msg); return msg; } private static void applyUpdate(String avatarUrl) { Retrofit retrofit = new Retrofit.Builder() .baseUrl(Constants.BASE_URL) .addConverterFactory(GsonConverterFactory.create()) .build(); IHttpService httpService = retrofit.create(IHttpService.class); String json = "{\"avatarUrl\":\"" + avatarUrl + "\",\"nick\":\"" + SPUtils.getInstance(Constants.SP_NAME_GLOBAL).getString("nick") + "\"}"; RequestBody body = RequestBody.create(okhttp3.MediaType.parse("application/json;charset=UTF-8"), json); Call<HttpResponse> call = httpService.updateNickAndAvatar(Constants.getHeaders(SPUtils.getInstance(Constants.SP_NAME_GLOBAL).getString("login_user_token")), body); call.enqueue(new Callback<HttpResponse>() { @Override public void onResponse(Call<HttpResponse> call, Response<HttpResponse> response) { Log.e(TAG, response.body().toString()); } @Override public void onFailure(Call<HttpResponse> call, Throwable t) { Log.e(TAG, "错误:" + t.getMessage()); } }); }}
参考:https://blog.csdn.net/bboyfeiyu/article/details/41863951