Android:方案“http"未在 ICS 4.0.4 w/代理上注册 [英] Android: Scheme 'http' not registered on ICS 4.0.4 w/ proxy

查看:17
本文介绍了Android:方案“http"未在 ICS 4.0.4 w/代理上注册的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我将 HttpClient 用于 HTTPS 请求,直到现在它都运行良好.升级到 ICS 后,一些用户报告连接 3G 连接时出现问题.

I'm using HttpClient for HTTPS requests, which has worked fine up until now. After upgrading to ICS, some users are reporting problems connecting on 3G connections.

他们中的大多数似乎都在使用代理,我可以使用他们的代理通过 T-Mobile SIM 在本地重现这一点.

Most of them seem to be using a proxy, and I can reproduce this locally with a T-Mobile SIM using their proxy.

日志有这个堆栈跟踪:

java.lang.IllegalStateException: Scheme 'http' not registered.
org.apache.http.conn.scheme.SchemeRegistry.getScheme(SchemeRegistry.java:80)
org.apache.http.impl.conn.DefaultClientConnectionOperator.openConnection(DefaultClientConnectionOperator.java:126)
org.apache.http.impl.conn.AbstractPoolEntry.open(AbstractPoolEntry.java:164)
org.apache.http.impl.conn.AbstractPooledConnAdapter.open(AbstractPooledConnAdapter.java:119)
org.apache.http.impl.client.DefaultRequestDirector.execute(DefaultRequestDirector.java:360)
org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:555)
org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:487)
org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:465)

我们的端点仅为 HTTPS,因此我们不会故意在 SchemeRegistry 中注册 HTTP 端点.我们没有任何地方 (AFAIK) 重定向到 HTTP.

Our endpoint is HTTPS only, so we do not register a HTTP endpoint in our SchemeRegistry on purpose. There isn't anywhere (AFAIK) where we redirect to HTTP.

这是为 HTTPS 客户端设置 HttpClient 的代码:

Here is the code that sets up the HttpClient for the HTTPS client:

    DefaultHttpClient ret = null;

    // sets up parameters
    HttpParams params = new BasicHttpParams();
    HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1);
    HttpProtocolParams.setContentCharset(params, "utf-8");
    params.setBooleanParameter("http.protocol.expect-continue", false);

    HttpConnectionParams.setConnectionTimeout(params, DEFAULT_CONN_TIMEOUT_MSEC);
    HttpConnectionParams.setSoTimeout(params, timeoutMsec);
    HttpConnectionParams.setStaleCheckingEnabled(params, true);

    SchemeRegistry registry = new SchemeRegistry();
    final SocketFactory sslSocketFactory = getPreferredSSLSocketFactory();
    registry.register(new Scheme("https", sslSocketFactory, 443));

    ThreadSafeClientConnManager manager = new ThreadSafeClientConnManager(params, registry);
    ret = new DefaultHttpClient(manager, params);
    // for preemptive authentication
    // http://dlinsin.blogspot.com/2009/08/http-basic-authentication-with-android.html
    ret.addRequestInterceptor(preemptiveAuth, 0);
    ret.setCookieStore(communalCookieJar);

    SimpleCredentialsProvider credProvider = new SimpleCredentialsProvider(getAccountPreferences());
    ret.setCredentialsProvider(credProvider);

    return ret;

注意:我们在多个线程之间共享这个 HttpClient 实例.

Note: We share this HttpClient instance among multiple threads.

推荐答案

问题似乎是一些运营商在 4.0.4 更新中推送无效的代理定义.这破坏了 HTTPS,但 HTTP 正常工作(例如,Google Play 无法正常工作).

The issue seemed to be that some carriers were pushing invalid proxy definitions with the 4.0.4 update. This broke HTTPS but HTTP worked properly (Google Play didn't work, for instance).

一种可能的解决方法(除了修复无效的代理条目)是在执行 HttpClient 请求时捕获 IllegalStateException 并设置一个标志.此代码将绕过任何代理:

One possible fix (besides fixing the invalid proxy entry) is to catch IllegalStateException when performing HttpClient requests and set a flag. This code will bypass any proxies:

    hc = new DefaultHttpClient(manager, params);
    if (BYPASS_PROXY)
        hc.setRoutePlanner(new DefaultHttpRoutePlanner(registry));

这篇关于Android:方案“http"未在 ICS 4.0.4 w/代理上注册的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆