java - 使用 HTTPClient 在 android 中发送 HTTPS post 请求以获得未验证的证书

标签 java android node.js android-studio ssl

我编写了这段代码,用于将 POST 请求发送到运行 nodejs 的本地主机服务器,该服务器具有使用 openssl 命令生成的证书。但是当我尝试发送发布请求时,我可以在 android 日志中看到 trust anchor 的问题和 https 上的 POST 请求不起作用,但如果我从 nodejs 服务器中删除证书并使用 http 发送请求。我知道这是因为我的证书没有经过任何知名 CA(如 verisign)的验证。那么,如何将请求发送到此 https 服务器?我也尝试在我的 android 手机中安装证书,但它也没有解决我的问题。我也可以发布 HttpClient.java 的源代码。

public class MainActivity extends AppCompatActivity {
    Button encAndSendBtn;
    TextView companyName, modelNumber, specification;

    public MainActivity() throws MalformedURLException {
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        encAndSendBtn = (Button) findViewById(R.id.encAndSend);
        companyName = (TextView) findViewById(R.id.company);
        modelNumber = (TextView) findViewById(R.id.modNum);
        specification = (TextView) findViewById(R.id.spec);
    }
    public void onclickbutton(View view) {

        encSend scv = new encSend();
        scv.execute();
    }

    private class encSend extends AsyncTask {

        String companyNameS = companyName.getText().toString();
        String modelNumberS = modelNumber.getText().toString();
        String specificationS = specification.getText().toString();

        @Override
        protected Object doInBackground(Object[] objects) {
           JSONObject jsonObjSend = new JSONObject();
           JSONObject encrptObjSend = new JSONObject();

           try {
                jsonObjSend.put("Company", companyNameS);
                jsonObjSend.put("Model Number", modelNumberS);
                jsonObjSend.put("Specification", specificationS);

                String finalData = jsonObjSend.toString();
                Log.i("data", finalData); 
                String key = "HelloWorld321@!";
                String encrypt;
                try {
                    CryptLib cryptLib = new CryptLib();
                    String iv = "1234123412341234";
                    encrypt = cryptLib.encryptSimple(finalData, key, iv);

                    encrptObjSend.put("encrptedtext", encrypt);
            } catch (Exception e) {
                    e.printStackTrace();
                }

                Log.i("Encrypted data", encrptObjSend.toString());

                JSONObject header = new JSONObject();
                header.put("deviceType", "Android"); // Device type
                header.put("deviceVersion", "2.0"); // Device OS version
                header.put("language", "es-es");    // Language of the Android client
                encrptObjSend.put("header", header);

            } catch (JSONException e) {
                e.printStackTrace();
            }
            JSONObject jsonObjRecv = HttpClient.SendHttpPost("https://192.168.43.59:443/api/aes", encrptObjSend);
            return "success";
        }
    }
}

更新:

public class HttpClient {
private static final String TAG = "HttpClient";

public static JSONObject SendHttpPost(String URL, JSONObject jsonObjSend) {

    try {
        DefaultHttpClient httpclient = new DefaultHttpClient();
        HttpPost httpPostRequest = new HttpPost(URL);

        StringEntity se;
        se = new StringEntity(jsonObjSend.toString());

        // Set HTTP parameters
        httpPostRequest.setEntity(se);
        httpPostRequest.setHeader("Accept", "application/json");
        httpPostRequest.setHeader("Content-type", "application/json");
        httpPostRequest.setHeader("Accept-Encoding", "gzip"); // only set this parameter if you would like to use gzip compression

        long t = System.currentTimeMillis();
        HttpResponse response = (HttpResponse) httpclient.execute(httpPostRequest);
        Log.i(TAG, "HTTPResponse received in [" + (System.currentTimeMillis()-t) + "ms]");

        // Get hold of the response entity (-> the data):
        HttpEntity entity = response.getEntity();

        if (entity != null) {
            // Read the content stream
            InputStream instream = entity.getContent();
            Header contentEncoding = response.getFirstHeader("Content-Encoding");
            if (contentEncoding != null && contentEncoding.getValue().equalsIgnoreCase("gzip")) {
                instream = new GZIPInputStream(instream);
            }

            // convert content stream to a String
            String resultString= convertStreamToString(instream);
            instream.close();
            resultString = resultString.substring(1,resultString.length()-1); // remove wrapping "[" and "]"

            // Transform the String into a JSONObject
            JSONObject jsonObjRecv = new JSONObject(resultString);
            // Raw DEBUG output of our received JSON object:
            Log.i(TAG,"<JSONObject>\n"+jsonObjRecv.toString()+"\n</JSONObject>");

            return jsonObjRecv;
        }

    }
    catch (Exception e)
    {
        // More about HTTP exception handling in another tutorial.
        // For now we just print the stack trace.
        e.printStackTrace();
    }
    return null;
}


private static String convertStreamToString(InputStream is) {
    /*
     * To convert the InputStream to String we use the BufferedReader.readLine()
     * method. We iterate until the BufferedReader return null which means
     * there's no more data to read. Each line will appended to a StringBuilder
     * and returned as String.
     *
     * (c) public domain: http://senior.ceng.metu.edu.tr/2009/praeda/2009/01/11/a-simple-restful-client-at-android/
     */
    BufferedReader reader = new BufferedReader(new InputStreamReader(is));
    StringBuilder sb = new StringBuilder();

    String line = null;
    try {
        while ((line = reader.readLine()) != null) {
            sb.append(line + "\n");
        }
    } catch (IOException e) {
        e.printStackTrace();
    } finally {
        try {
            is.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    return sb.toString();
}

最佳答案

您应该使用始终正常的委托(delegate)来避免服务器证书验证。当然你必须使用 https 连接。检查此链接,例如:http://www.nakov.com/blog/2009/07/16/disable-certificate-validation-in-java-ssl-connections/

关于java - 使用 HTTPClient 在 android 中发送 HTTPS post 请求以获得未验证的证书,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47121123/

相关文章:

node.js - 将 MongoStore 与 Express 一起使用时出错

javascript - 数字数组中的重复项失败

java - Jmeter:了解吞吐量和 KB/秒之间的相关性

java - 如何在Java中读取树形结构制表符分隔的文本文件

Java 应用程序使用 AJAX

java - Dagger 注入(inject)的类在 Dagger 中保持为 null

android - 如何控制从服务播放的音频音量?

c# - Xamarin.窗体 : Android project Build Error - Missing Files inside AppData\Local\Xamarin Folders

java - 如何使用 AmazonSNSClient 避免 Android 9 中的应用程序崩溃?

mysql - 使用 Node.js 和 mySQL