Android 应用程序在 WIFI 和 3G(无代理)上工作,但在 3G 上不工作(如果分配了代理和端口)
Posted
技术标签:
【中文标题】Android 应用程序在 WIFI 和 3G(无代理)上工作,但在 3G 上不工作(如果分配了代理和端口)【英文标题】:Android application working on WIFI and 3G(Without proxy), but not working on 3G(If proxy and port are assigned) 【发布时间】:2012-09-19 00:10:08 【问题描述】:我遇到了一些奇怪的问题,当我切换到 3G 服务(带代理)时,只有我的应用程序无法正常工作,但它在 WIFI 和 3G(不带代理)中运行良好。
我的 Starhub(网络提供商)提供的默认代理和端口:
Proxy: 10.12.1.2
Port: 80
对于数据,我正在向我的网络服务器发送肥皂请求。
这是我的代码:
public class SearchThread extends Thread
private String mUrl;
private SoapSerializationEnvelope mEnvelop;
private Handler mHandler;
private String mSoapAction;
private KeepAliveHttpsTransportSE mTransport;
public SearchThread(String url)
this.mUrl = url;
@Override
public void run()
mEnvelop = new SoapSerializationEnvelope(SoapSerializationEnvelope.VER11);
mEnvelop.setOutputSoapObject(interfaceListener.getSoapObject(element));
mSoapAction = interfaceListener.getSoapAction(element);
try
TrustManagerManipulator.allowAllSSL();
mTransport = new KeepAliveHttpsTransportSE(URLS.URL_MAIN, 443, mUrl, 60000);
mTransport.call(mSoapAction, mEnvelop);
if (this.isInterrupted())
Log.v(TAG,"Interrupted");
return;
recevedSoapResponse(mEnvelop.getResponse());
catch (SocketException ex)
Log.e("Error : ", "Error on soapPrimitiveData() " + ex.getMessage());
ex.printStackTrace();
catch (IOException e)
interfaceListener.recievedParsingResults(
PARSER.RESULT.CONNECTION_FAILED, element, mHandler, mView);
e.printStackTrace();
catch (XmlPullParserException e)
e.printStackTrace();
interfaceListener.recievedParsingResults(
PARSER.RESULT.INTERNAL_ERROR, element, mHandler, mView);
private void recevedSoapResponse(Object response)
//Parsing XML here.
public class KeepAliveHttpsTransportSE extends HttpsTransportSE
private final String host;
private final int port;
private final String file;
private final int timeout;
private ServiceConnection serviceConnection;
public KeepAliveHttpsTransportSE (String host, int port, String file, int timeout)
super(host, port, file, timeout);
this.host = host;
this.port = port;
this.file = file;
this.timeout = timeout;
//@Override
public ServiceConnection getServiceConnection() throws IOException
if (serviceConnection == null)
serviceConnection = new HttpsServiceConnectionSE(host, port, file, timeout);
serviceConnection.setRequestProperty("Connection", "keep-alive");
return serviceConnection;
这是我的 SSL 代码:
public class TrustManagerManipulator implements X509TrustManager
private static TrustManager[] trustManagers;
private static final X509Certificate[] acceptedIssuers = new X509Certificate[] ;
public boolean isClientTrusted(X509Certificate[] chain)
return true;
public boolean isServerTrusted(X509Certificate[] chain)
return true;
public static void allowAllSSL()
HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier()
public boolean verify(String hostname, SSLSession session)
return true;
);
SSLContext context = null;
if (trustManagers == null)
trustManagers = new TrustManager[] new TrustManagerManipulator() ;
try
context = SSLContext.getInstance("TLS");
context.init(null, trustManagers, new SecureRandom());
catch (NoSuchAlgorithmException e)
e.printStackTrace();
catch (KeyManagementException e)
e.printStackTrace();
HttpsURLConnection.setDefaultSSLSocketFactory(context
.getSocketFactory());
public void checkClientTrusted(X509Certificate[] chain, String authType)
throws CertificateException
public void checkServerTrusted(X509Certificate[] chain, String authType)
throws CertificateException
public X509Certificate[] getAcceptedIssuers()
return acceptedIssuers;
例外:
09-27 12:21:03.295: W/System.err(8924): java.net.SocketException: Socket is closed
09-27 12:21:03.295: W/System.err(8924): at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.checkOpen(OpenSSLSocketImpl.java:262)
09-27 12:21:03.295: W/System.err(8924): at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.startHandshake(OpenSSLSocketImpl.java:273)
09-27 12:21:03.295: W/System.err(8924): at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.startHandshake(OpenSSLSocketImpl.java:257)
09-27 12:21:03.295: W/System.err(8924): at libcore.net.http.HttpConnection.setupSecureSocket(HttpConnection.java:210)
09-27 12:21:03.295: W/System.err(8924): at libcore.net.http.HttpsURLConnectionImpl$HttpsEngine.makeSslConnection(HttpsURLConnectionImpl.java:477)
09-27 12:21:03.295: W/System.err(8924): at libcore.net.http.HttpsURLConnectionImpl$HttpsEngine.connect(HttpsURLConnectionImpl.java:441)
09-27 12:21:03.295: W/System.err(8924): at libcore.net.http.HttpEngine.sendSocketRequest(HttpEngine.java:282)
09-27 12:21:03.295: W/System.err(8924): at libcore.net.http.HttpEngine.sendRequest(HttpEngine.java:232)
09-27 12:21:03.295: W/System.err(8924): at libcore.net.http.HttpURLConnectionImpl.connect(HttpURLConnectionImpl.java:80)
09-27 12:21:03.300: W/System.err(8924): at libcore.net.http.HttpURLConnectionImpl.getOutputStream(HttpURLConnectionImpl.java:188)
09-27 12:21:03.300: W/System.err(8924): at libcore.net.http.HttpsURLConnectionImpl.getOutputStream(HttpsURLConnectionImpl.java:280)
09-27 12:21:03.300: W/System.err(8924): at org.ksoap2.transport.HttpsServiceConnectionSE.openOutputStream(HttpsServiceConnectionSE.java:98)
09-27 12:21:03.300: W/System.err(8924): at org.ksoap2.transport.HttpTransportSE.call(HttpTransportSE.java:157)
09-27 12:21:03.300: W/System.err(8924): at org.ksoap2.transport.HttpTransportSE.call(HttpTransportSE.java:96)
09-27 12:21:03.300: W/System.err(8924): at com.mobile.utils.parser.SearchThread.run(SearchThread.java:25)
附加信息:所有其他应用程序都在 3G 网络上运行(带/不带代理设置)并且在我的应用程序中只有 SOAP 请求不起作用。
我已经尝试了所有可能的情况,但没有运气。请提供一些意见。
提前致谢。
【问题讨论】:
【参考方案1】:也许你们四个太晚了,但我希望这对未来像我一样到达这里的人有所帮助,因为同样的问题而疯狂。
这是一个 Android 错误。一切都适用于 WiFi,但它在 3G 上崩溃。它发生在我的 4.1 上,但在 4.2.2 上没有问题。
要解决这个问题,您必须修改文件 org.ksoap2.transport.HttpTransportSE(我扩展了一个新文件并将其命名为 MyHttpTransportSE,因为我使用的是 ksoap2 程序集 jar)。 只需覆盖方法 public void call(String soapAction, SoapEnvelope envelope) 注释掉该行
//connection.setRequestProperty("Connection", "close");
当然,如果您使用 SSL,则需要从新的 MyHttpTransportSE 扩展您自己的 HttpsTransportSE。
HttpTransportSE源代码:https://github.com/karlmdavis/ksoap2-android/blob/master/ksoap2-j2se/src/main/java/org/ksoap2/transport/HttpTransportSE.java?source=c
HttpsTransportSE源代码:https://github.com/mosabua/ksoap2-android/blob/master/ksoap2-j2se/src/main/java/org/ksoap2/transport/HttpsTransportSE.java
更多细节在这里:https://groups.google.com/forum/#!searchin/ksoap2-android/closed/ksoap2-
【讨论】:
【参考方案2】:正如 Ender Muab'Dib 所说,您必须将“连接”属性设置为“关闭”。但是没有必要扩展 HttpTransportSE。根据您的代码编写方式,可能更容易将第三个参数传递给“调用”函数,该函数是参数列表。
ArrayList<HeaderProperty> headerPropertyArrayList = new ArrayList<HeaderProperty>();
headerPropertyArrayList.add(new HeaderProperty("Connection", "close"));
transport.call(soapAction, envelope, headerPropertyArrayList);
【讨论】:
以上是关于Android 应用程序在 WIFI 和 3G(无代理)上工作,但在 3G 上不工作(如果分配了代理和端口)的主要内容,如果未能解决你的问题,请参考以下文章
具有 3G 和 WIFI 网络的 Android 客户端应用程序
Android:在应用程序中间切换 3G 到 WIFI = 失去网络连接
确定 Android 设备中的 3G/WIFI 无线电状态机当前状态
Android 127.0.0.1(环回)连接:在 WiFi 上工作,在 3G/4G 上失败