Image uploaded in byte array to server get corrupted(Image can't be opened)

992 Views Asked by At

Server side expect image to be send in byte array, I am able upload image successfully(200 response) but when check image in server image get corrupted(image can't be open).

I tried following ways upload image(in byte array).

1st way

HttpClient httpclient = new DefaultHttpClient();

HttpPost httppost = new HttpPost(url);
httppost.addHeader("Content-Type", "multipart/form-data");

try {
    AndroidMultiPartEntity entity = new AndroidMultiPartEntity(
            new AndroidMultiPartEntity.ProgressListener() {

                @Override
                public void transferred(long num) {

                    publishProgress((int) ((num / (float) totalSize) * 100));
                }
            });

    File sourceFile = new File("filepath");

    // Adding file data to http body
    entity.addPart("image", new FileBody(sourceFile));

    totalSize = entity.getContentLength();
    httppost.setEntity(entity);

    // Making server call
    HttpResponse response = httpclient.execute(httppost);
    HttpEntity r_entity = response.getEntity();

2nd way

HttpPost httppost = new HttpPost(url);

try {
    AndroidMultiPartEntity entity = new AndroidMultiPartEntity(HttpMultipartMode.BROWSER_COMPATIBLE,
            new AndroidMultiPartEntity.ProgressListener() {

                @Override
                public void transferred(long num) {

                    publishProgress((int) ((num / (float) totalSize) * 100));
                }
            });

    File sourceFile = new File("filepath");
    FileInputStream fis = new FileInputStream(sourceFile);
    ByteArrayOutputStream bos = new ByteArrayOutputStream();
    byte[] buf = new byte[1024];
    try {
        for (int readNum; (readNum = fis.read(buf)) != -1;) {
            bos.write(buf, 0, readNum); //no doubt here is 0
            //Writes len bytes from the specified byte array starting at offset off to this byte array output stream.
            System.out.println("read " + readNum + " bytes,");
        }
    } catch (IOException ex) {

    }

    httppost.addHeader("Content-Type", "multipart/form-data");
    httppost.setEntity(new ByteArrayEntity(buf));
     // Making server call
    HttpResponse response = httpclient.execute(httppost);
    HttpEntity r_entity = response.getEntity();

In both cases image getting upload but its get corrupted (not viewable) after upload.

Could someone please me know what I am doing wrong? How can I upload image in byte array to server without getting image corrupted?

1

There are 1 best solutions below

1
Reaz Murshed On

Here's a sample upload image function that I have used and this is working. However, I have implemented the image uploading with Volley. You might require some changes in the function to make it work in your case.

public static void uploadImage(final Context context, final String filePath) {
    VolleyMultipartRequest multipartRequest = new VolleyMultipartRequest(Request.Method.POST, postUrl, new Response.Listener<NetworkResponse>() {
        @Override
        public void onResponse(NetworkResponse response) {
            String resultResponse = new String(response.data);
            try {
                JSONObject result = new JSONObject(resultResponse);
            } catch (JSONException e) {
                e.printStackTrace();
            }
        }
    }, new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError error) {
            NetworkResponse networkResponse = error.networkResponse;
            String errorMessage = "Unknown error";
            if (networkResponse == null) {
                if (error.getClass().equals(TimeoutError.class)) {
                    errorMessage = "Request timeout";
                } else if (error.getClass().equals(NoConnectionError.class)) {
                    errorMessage = "Failed to connect server";
                }
            } else {
                String result = new String(networkResponse.data);
                try {
                    JSONObject response = new JSONObject(result);
                    String status = response.getString("status");
                    String message = response.getString("message");

                    Log.e("Error Status", status);
                    Log.e("Error Message", message);

                    if (networkResponse.statusCode == 404) {
                        errorMessage = "Resource not found";
                    } else if (networkResponse.statusCode == 401) {
                        errorMessage = message + " Please login again";
                    } else if (networkResponse.statusCode == 400) {
                        errorMessage = message + " Check your inputs";
                    } else if (networkResponse.statusCode == 500) {
                        errorMessage = message + " Something is getting wrong";
                    }
                } catch (JSONException e) {
                    e.printStackTrace();
                }
            }
            Log.i("Error", errorMessage);
            error.printStackTrace();
        }
    }) {
        @Override
        protected Map<String, String> getParams() {
            Map<String, String> params = new HashMap<>();
            return params;
        }

        @Override
        protected Map<String, DataPart> getByteData() {
            Map<String, DataPart> params = new HashMap<>();
            // file name could found file base or direct access from real path
            // for now just get bitmap data from ImageView
            params.put("template", new DataPart("profile_picture",
                    readImageFile(filePath)));
            return params;
        }
    };

    VolleySingleton.getInstance(context).addToRequestQueue(multipartRequest);
}

public static byte[] readImageFile(String fileName) {
    File root = android.os.Environment.getExternalStorageDirectory();
    File dir = new File(root.getAbsolutePath() + IMAGE_DIRECTORY);
    File file = new File(dir, fileName);

    int size = (int) file.length();
    byte[] bytes = new byte[size];
    try {
        BufferedInputStream buf = new BufferedInputStream(new FileInputStream(file));
        buf.read(bytes, 0, bytes.length);
        buf.close();
    } catch (FileNotFoundException e) {
        e.printStackTrace();
        return null;
    } catch (IOException e) {
        e.printStackTrace();
        return null;
    }

    return bytes;
}

To use Volley, you need to add the following dependency in your build.gradle file.

dependencies {
    // ... Other dependencies
    compile 'com.android.volley:volley:1.0.0'
}