在Android中使用HttpURLConnection发送JSON和图像

4

我试图向服务器发送一些数据。服务器正在等待一个json和一张图片。我尝试了我找到的每个例子,但我无法发送数据。实际上,我正在使用PrintWriter对象发送json参数,但它不接受图片。我需要使用HttpURLConnection而不是apache库。这是我的工作代码片段:

HttpURLConnection connection = null;
    PrintWriter output = null;

    ByteArrayOutputStream stream = new ByteArrayOutputStream();
    attachImage.compress(Bitmap.CompressFormat.PNG, 40, stream);
    byte[] imageData = stream.toByteArray();
    String imagebase64 = Base64.encodeToString(imageData, Base64.DEFAULT); 

    Log.d(tag, "POST to " + url);
    try{
        URL url = new URL(this.url);
        connection = (HttpURLConnection) url.openConnection();

        connection.setRequestMethod("POST");

        connection.setDoInput(true);
        connection.setDoOutput(true);
        connection.setUseCaches(false);

        connection.setRequestProperty(HTTP_CONTENT_TYPE, "application/json; charset=utf-8");
        connection.setRequestProperty(HTTP_USER_AGENT, mUserAgent);
        connection.setRequestProperty(HTTP_HEADER_ACCEPT, "application/json; charset=utf-8");
        connection.connect();
        output = new PrintWriter(connection.getOutputStream());

        JSONObject jsonParam = new JSONObject();
        jsonParam.put("oauth_token", params.get("oauth_token"));
        jsonParam.put("rating", "1");
        jsonParam.put("comments", "ASDASDASDASDASDASDAS");


        Log.d(tag, jsonParam.toString());

        output.print(jsonParam);
        output.flush();
        output.close();

        Log.d(tag, connection.getResponseCode() + connection.getResponseMessage());
    }catch(Exception e ){

    }

当我尝试在JSON参数中发送图片时,收到了一个500内部错误消息。

谢谢!


HTTP 500错误意味着服务器端错误... - shkschneider
http://en.wikipedia.org/wiki/List_of_HTTP_status_codes#500 - dieter
是的,我知道那是什么意思。但是可能是因为我发送了错误的参数吗?如果我按照上面的示例不发送图像,它可以正常工作。 - Augusto Pinto
当我尝试在JSON参数中发送图像时,请添加您尝试的代码。 - greenapps
不,这不是我的服务器问题。我无法访问它。 - Augusto Pinto
显示剩余4条评论
5个回答

2

我尝试了第一种选项,但没有用。现在让我们尝试第二种。谢谢。 - Augusto Pinto
根据第二个选项,您需要将服务托管到本地主机或实时环境中,然后您就可以这样做! - Madhav Anadkat
我不想使用MultipartEntity。 - Augusto Pinto
然后进行Base64字符串转换并将该字符串发送到您的服务器! - Madhav Anadkat
也许你漏掉了什么!!请检查下面的链接,我已经完成了相同的操作!!http://stackoverflow.com/questions/9987343/android-upload-image-to-server-using-base64 - Madhav Anadkat

1

我也在尝试向服务器发送数据。到目前为止,我一直在使用过时的教程,但什么都不起作用。我甚至无法将NameValuePair发送到服务器。由于某种原因,“setEntity”方法不起作用。你能帮我实现一个可以发布文本和图片的POST方法吗? - Bogdan Daniel
你看过上面的链接了吗?我使用了tradefed库中的一些类,并将其适应到我的代码中。另一个解决方案是使用apache库,但我不推荐。此外,你必须阅读这个链接以了解httpURLConnection的工作原理。http://www.17od.com/2010/02/18/multipart-form-upload-on-android/ - Augusto Pinto

0
检查下面的代码以发送表单数据和包含图像或其他任何媒体文件的压缩文件。
private class MultipartFormTask extends AsyncTask<String, Void, String> {

        String getStringFromInputStream(HttpURLConnection conn) {
            String strResponse = "";
            try {
                DataInputStream inStream = new DataInputStream(
                        conn.getInputStream());

                BufferedReader br = new BufferedReader(new InputStreamReader(
                        inStream));
                String line;
                while ((line = br.readLine()) != null) {
                    strResponse += line;
                }
                br.close();
                inStream.close();
            } catch (IOException ioex) {
                Log.e("Debug", "error: " + ioex.getMessage(), ioex);
            }
            return strResponse;
        }

        void uploadJSONFeed(HttpURLConnection conn, DataOutputStream dos,
                String lineEnd) {
            String issue_details_key = "issue_details";
            String issue_details_value = "Place your Jsondata HERE";
            try {
                dos.writeBytes("Content-Disposition: form-data; name=\""
                        + issue_details_key + "\"" + lineEnd
                        + "Content-Type: application/json" + lineEnd);
                dos.writeBytes(lineEnd);
                dos.writeBytes(issue_details_value);
                dos.writeBytes(lineEnd);
            } catch (IOException ioe) {
                Log.e("Debug", "error: " + ioe.getMessage(), ioe);
            }

        }

        void uploadZipFile(HttpURLConnection conn, DataOutputStream dos,
                String lineEnd) {
            int bytesRead, bytesAvailable, bufferSize;
            byte[] buffer;
            int maxBufferSize = 1 * 1024 * 1024;
            try {

                InputStream is = null;
                try {
                    is = getAssets().open("Test.zip");
                } catch (IOException ioe) {
                    // TODO Auto-generated catch block
                    Log.e("Debug", "error: " + ioe.getMessage(), ioe);
                }

                String zip_file_name_key = "file_zip";
                String upload_file_name = "test.zip";

                dos.writeBytes("Content-Disposition: form-data; name=\""
                        + zip_file_name_key + "\";filename=\""
                        + upload_file_name + "\"" + lineEnd); // uploaded_file_name
                                                                // is the Name
                                                                // of the File
                                                                // to be
                                                                // uploaded
                dos.writeBytes(lineEnd);
                bytesAvailable = is.available();
                bufferSize = Math.min(bytesAvailable, maxBufferSize);
                buffer = new byte[bufferSize];
                bytesRead = is.read(buffer, 0, bufferSize);
                while (bytesRead > 0) {
                    dos.write(buffer, 0, bufferSize);
                    bytesAvailable = is.available();
                    bufferSize = Math.min(bytesAvailable, maxBufferSize);
                    bytesRead = is.read(buffer, 0, bufferSize);
                }
                dos.writeBytes(lineEnd);

                is.close();
            } catch (IOException ioe) {
                Log.e("Debug", "error: " + ioe.getMessage(), ioe);
            }
        }

        @Override
        protected String doInBackground(String... params) {
            // TODO Auto-generated method stub

            HttpURLConnection conn = null;
            DataOutputStream dos = null;
            String lineEnd = "\r\n";
            String twoHyphens = "--";
            String boundary = "*****";

            String urlString = "http://www.example.org/api/file.php";
            try {
                // ------------------ CLIENT REQUEST

                // FileInputStream fileInputStream = new FileInputStream(new
                // File(existingFileName) );
                // open a URL connection to the Servlet
                URL url = new URL(urlString);
                // Open a HTTP connection to the URL
                conn = (HttpURLConnection) url.openConnection();
                // Allow Inputs
                conn.setDoInput(true);
                // Allow Outputs
                conn.setDoOutput(true);
                // Don't use a cached copy.
                conn.setUseCaches(false);
                // Use a post method.
                conn.setRequestMethod("POST");
                conn.setRequestProperty("Connection", "Keep-Alive");
                conn.setRequestProperty("Content-Type",
                        "multipart/form-data;boundary=" + boundary);
                dos = new DataOutputStream(conn.getOutputStream());

                dos.writeBytes(twoHyphens + boundary + lineEnd);
                uploadJSONFeed(conn, dos, lineEnd);

                dos.writeBytes(twoHyphens + boundary + lineEnd);
                uploadZipFile(conn, dos, lineEnd);

                dos.writeBytes(twoHyphens + boundary + twoHyphens + lineEnd);
                dos.flush();
                dos.close();
            } catch (MalformedURLException ex) {
                Log.e("Debug", "error: " + ex.getMessage(), ex);
            } catch (IOException ioe) {
                Log.e("Debug", "error: " + ioe.getMessage(), ioe);
            }
            // ------------------ read the SERVER RESPONSE
            String strResponse = getStringFromInputStream(conn);

            return strResponse;
        }

        @Override
        protected void onPostExecute(String result) {
            // might want to change "executed" for the returned string passed
            // into onPostExecute() but that is upto you

            Toast.makeText(getApplicationContext(), result, Toast.LENGTH_LONG)
                    .show();
            Log.e("Result:", result);
        }
    }

0
 you can upload large jsonstring using buffer please use bellow code .

HttpsURLConnection connection = null;
        OutputStream os = null;
        InputStream is = null;
        InputStreamReader isr = null;
        try {
            connection = (HttpsURLConnection) url.openConnection();

            SSLContext contextSSL = SSLContext.getInstance("TLS");
            contextSSL.init(null, new TrustManager[]{new DefaultTrustManager()}, new SecureRandom());
            HttpsURLConnection.setDefaultSSLSocketFactory(contextSSL.getSocketFactory());
           MySSLFactory(context.getSocketFactory()));
            HttpsURLConnection.setDefaultHostnameVerifier(new MyHostnameVerifier());
            connection.setDoInput(true);
            connection.setDoOutput(true);
            connection.setUseCaches(false);
            connection.setChunkedStreamingMode(0);
            connection.setRequestMethod("POST");
            connection.setRequestProperty("Content-Type", "application/json");
            connection.setRequestProperty("Accept", "application/json");
            connection.setRequestProperty("Authorization", auth);
            connection.setConnectTimeout(timeoutMillis);
            OutputStream os ;
            if (input != null && !input.isEmpty()) {
                os = connection.getOutputStream();
               InputStream stream = new ByteArrayInputStream(input.getBytes(StandardCharsets.UTF_8));
                BufferedInputStream bis = new BufferedInputStream(stream, 8 * 1024);
                byte[] buffer = new byte[8192];
                int availableByte = 0;
               while ((availableByte = bis.read(buffer)) != -1) {
                   os.write(buffer, 0, availableByte);
                   os.flush();
               }

            }
            int responseCode = connection.getResponseCode();

-1

HTTP 500错误代码表示发生了服务器端错误。

这与您的代码无关。

服务器出现了错误,而不是您的代码。


你是在暗示服务器遇到错误是因为客户端的 bug 而不可能吗?有趣。 - class stacker
可能会,但这里提出的问题暗示着暴露的代码包含了错误,而在发生500错误时,这种错误是来自于服务器端而不是客户端。服务器应该避免因为错误输入或其他原因发送500错误代码。其他4xx代码可以用于此类情况。 - shkschneider
我尝试了这个例子https://dev59.com/neo6XIcBkEYKwwoYIAgL?rq=1 但它没有起作用。 - Augusto Pinto
那是无稽之谈。你还应该阅读服务器的回复/回声。从InputStream中读取。你还没有这样做。添加它。代码已经发布了一百次。 - greenapps

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接