检查URL是HTTPS还是HTTP协议?

5
我目前正在使用以下方法从Android文档中读取文件:这里这里。用户可以在设置屏幕中选择他们的网站使用HTTP或HTTPS协议。如果他们的网站使用HTTP协议,则对于HttpURLConnectionHttpsURLConnection都有效,但是如果他们的网站使用HTTPS协议,则对于HttpURLConnection协议无效,最糟糕的是它不会给我异常错误。下面是我正在使用的示例代码。
因此,实质上,我如何检查Web URL是否为HTTPS协议,以检查用户是否选择了正确的协议?
InputStream inputStream;
HttpURLConnection urlConnection;
HttpsURLConnection urlHttpsConnection;
boolean httpYes, httpsYes; 
try {
if (httpSelection.equals("http://")) {
  URL url = new URL(weburi);
  urlConnection = (HttpURLConnection) url.openConnection();
  inputStream = new BufferedInputStream((urlConnection.getInputStream()));
httpYes = True;
}
if (httpSelection.equals("https://")) {
  URL url = new URL(weburi);
  urlHttpsConnection = (HttpsURLConnection) url.openConnection();
  urlHttpsConnection.setSSLSocketFactory(context.getSocketFactory());
  inputStream = urlHttpsConnection.getInputStream();
  https=True;
}

catch (Exception e) {
//Toast Message displays and settings intent re-starts
}
finally {
  readFile(in);
if(httpYes){ 
    urlConnection.disconnect();
    httpYes = False;
 }
if(httpsYes){ 
    urlHttpsConnection.disconnect();
    httpsYes = False;
 } 
}
}

编辑:

进一步阐述,我需要确定它是否从网站返回有效响应?因此,如果用户选择了http而不是https,我如何检查http是否是错误的前缀/协议?

我怎么才能检查网站使用HTTPS还是HTTP协议?如果用户只输入www.google.com,我添加https://http://前缀,我如何知道应该使用哪个正确的前缀?


2
也许我漏掉了什么。你不能检查URL字符串是否以 https://http// 开头吗? - Karim
我可以 @Karim,但是如果用户选择了错误的字符串会发生什么呢?这就是我遇到的问题。 - Dino
1
在所有情况下都使用HttpsURLConnection,或者不要检查httpSelection.equals(...),而是立即检查URL是否以https://http://开头,不要要求用户选择任何内容。 - Karim
@Karim 我认为这可能是目前为止最好的解决方案。无论用户选择了 https:// 还是 http:// ,它都可以正常工作。虽然我不确定这是否是正确的方法。 - Dino
@Karim,我刚意识到它仍然不能正确工作,因为当URL是https时,如果用户输入http,则会给我与以前相同的结果。 - Dino
8个回答

11
你可以使用安卓的URLUtil来检查一个URL是HTTP还是HTTPS:

你可以使用安卓的URLUtil来检查一个URL是HTTP还是HTTPS:

public static boolean isHttpUrl (String url)
Returns True iff the url is an http: url.

public static boolean isHttpsUrl (String url) 
Returns True iff the url is an https: url.

编辑:

public static boolean isValidUrl (String url)
Returns True iff the url is valid.

我已经尝试了上述所有方法。虽然它是正确的并且有效,但如果用户使用http而不是https,它仍然会返回一个有效的响应,这并没有解决问题。 - Dino
这段代码实际上是尝试传输任何数据,还是只返回true,如果连接以https://开头。 - Bojan Kseneman
@Dino 不确定,但可能是您的HTTP URL重定向到HTTPS。 - Dhaval Patel
@DhavalPatel 我不确定它是否尝试重定向,但如果用户输入错误的前缀,我不会收到异常错误。它会返回 true。我已经在 HTTP 和 HTTPS 前缀上都尝试过了。 - Dino
@DhavalPatel,我刚刚使用了getResponseCode(),它确实返回了302(表示重定向)的HTTPS。 - Dino

5
URLConnection result = url.openConnection();
if (result instanceof HttpsURLConnection) {
   // https
}
else if (result instanceof HttpURLConnection) {
   // http
}
else {
  // null or something bad happened
}

4

我已经查看了URLUtil类,并发现它包含许多这种类型的方法,但是我只是扩展了答案,你也可以简单地执行以下操作:

public static boolean isHttpOrHttpsUrl(String url) {
        return url.matches("^(http|https|ftp)://.*$");
    }

3
请尝试以下代码:
mConnexion = (URLUtil.isHttpsUrl(mStringUrl)) ? (HttpsURLConnection) url.openConnection() : (HttpURLConnection) url.openConnection();

2

您可以使用Util功能来检查这一点。

  • isHttpUrl返回 True,当url是一个 http: url 时。
  • isHttpsUrl返回 True,当url是一个 https: url 时。

2
@ Kartheek,这和我的答案不同吗? - Dhaval Patel
1
我没有检查过你的答案 @DhavalPatel - Kartheek

0

你可以尝试这个

    boolean httpYes, httpsYes;
     try {

      URL url = new URL(weburi);
      urlConnection = (HttpURLConnection) url.openConnection();
      inputStream = new BufferedInputStream((urlConnection.getInputStream()));
    httpYes = True;
    }


    catch (Exception e) {
    //Toast Message displays and settings intent re-starts
          URL url = new URL(weburi);
          urlHttpsConnection = (HttpsURLConnection) url.openConnection();
          urlHttpsConnection.setSSLSocketFactory(context.getSocketFactory());
          inputStream = urlHttpsConnection.getInputStream();
          https=True;
    }

@ Tony 为什么要增加try-catch的额外开销?如果我们可以通过简单的if-else条件来检查它呢? - Dhaval Patel
我完全同意你的想法,但它可以作为额外的场景添加。顺便说一下,在这两种情况下,try catch语句都被添加到了HTTP连接中。 - Antwan

-3
我的建议是创建函数表达式正则。 例如:
public void testUrl(Object urlHttp){

    String url = "https://www.google.com";

    if(url.matches("^(https?)://.*$")){
     Object o = (HttpsURLConnection) urlHttp;
    }else{
     Object o = (HttpURLConnection) urlHttp;
    }
}

敬礼


它不能处理URL中未指定协议的情况。 - Mário Feroldi
无论如何,使用这个正则表达式它会将对象转换为https,即使它本身不是。 - Elie G.

-3

我认为这个方法可行,至少看起来是这样的,你们觉得呢?我把这个if语句放在httpsYes = TruehttpYes = True之前。

当选择HTTPS协议时,它似乎想要使用302响应代码进行重定向,但对于所有其他情况,它都会使用200响应代码进行连接。我抛出一个新的ConnectionException()错误,因为这会将用户带回设置屏幕以更正URL错误。

对于HTTPS协议:

if (httpsURLConnection.getResponseCode() != 200) {
     throw new ConnectException();
}

关于HTTP协议:

if (urlConnection.getResponseCode() != 200) {
     throw new ConnectException();
}

有什么意见吗?我应该使用 urlConnection.getResponseCode() > 199 && < 300 吗?以覆盖所有连接成功的情况?


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