轉自:http://codingnow.cn/android/723.html
這篇文章主要實現了在Android中使用JDK的HttpURLConnection和Apache的HttpClient訪問網絡資源,服務端採用python+flask編寫,使用Servlet太麻煩了。關於Http協議的相關知識,可以在網上查看相關資料。代碼比較簡單,就不詳細解釋了。
1. 使用JDK中HttpURLConnection訪問網絡資源
(1)get請求
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
|
public
String executeHttpGet() { String
result = null ; URL
url = null ; HttpURLConnection
connection = null ; InputStreamReader
in = null ; try
{ url
= new
URL( "http://10.0.2.2:8888/data/get/?token=alexzhou" ); connection
= (HttpURLConnection) url.openConnection(); in
= new
InputStreamReader(connection.getInputStream()); BufferedReader
bufferedReader = new
BufferedReader(in); StringBuffer
strBuffer = new
StringBuffer(); String
line = null ; while
((line = bufferedReader.readLine()) != null )
{ strBuffer.append(line); } result
= strBuffer.toString(); } catch
(Exception e) { e.printStackTrace(); } finally
{ if
(connection != null )
{ connection.disconnect(); } if
(in != null )
{ try
{ in.close(); } catch
(IOException e) { e.printStackTrace(); } } } return
result; } |
注意:因爲是通過android模擬器訪問本地pc服務端,所以不能使用localhost和127.0.0.1,使用127.0.0.1會訪問模擬器自身。Android系統爲實現通信將PC的IP設置爲10.0.2.2
(2)post請求
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
|
public
String executeHttpPost() { String
result = null ; URL
url = null ; HttpURLConnection
connection = null ; InputStreamReader
in = null ; try
{ url
= new
URL( "http://10.0.2.2:8888/data/post/" ); connection
= (HttpURLConnection) url.openConnection(); connection.setDoInput( true ); connection.setDoOutput( true ); connection.setRequestMethod( "POST" ); connection.setRequestProperty( "Content-Type" , "application/x-www-form-urlencoded" ); connection.setRequestProperty( "Charset" , "utf-8" ); DataOutputStream
dop = new
DataOutputStream( connection.getOutputStream()); dop.writeBytes( "token=alexzhou" ); dop.flush(); dop.close(); in
= new
InputStreamReader(connection.getInputStream()); BufferedReader
bufferedReader = new
BufferedReader(in); StringBuffer
strBuffer = new
StringBuffer(); String
line = null ; while
((line = bufferedReader.readLine()) != null )
{ strBuffer.append(line); } result
= strBuffer.toString(); } catch
(Exception e) { e.printStackTrace(); } finally
{ if
(connection != null )
{ connection.disconnect(); } if
(in != null )
{ try
{ in.close(); } catch
(IOException e) { e.printStackTrace(); } } } return
result; } |
如果參數中有中文的話,可以使用下面的方式進行編碼解碼:
1
2
|
URLEncoder.encode( "測試" , "utf-8" ) URLDecoder.decode( "測試" , "utf-8" ); |
2.使用Apache的HttpClient訪問網絡資源
(1)get請求
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
|
public
String executeGet() { String
result = null ; BufferedReader
reader = null ; try
{ HttpClient
client = new
DefaultHttpClient(); HttpGet
request = new
HttpGet(); request.setURI( new
URI( "http://10.0.2.2:8888/data/get/?token=alexzhou" )); HttpResponse
response = client.execute(request); reader
= new
BufferedReader( new
InputStreamReader(response .getEntity().getContent())); StringBuffer
strBuffer = new
StringBuffer( "" ); String
line = null ; while
((line = reader.readLine()) != null )
{ strBuffer.append(line); } result
= strBuffer.toString(); } catch
(Exception e) { e.printStackTrace(); } finally
{ if
(reader != null )
{ try
{ reader.close(); reader
= null ; } catch
(IOException e) { e.printStackTrace(); } } } return
result; } |
(2)post請求
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
|
public
String executePost() { String
result = null ; BufferedReader
reader = null ; try
{ HttpClient
client = new
DefaultHttpClient(); HttpPost
request = new
HttpPost(); request.setURI( new
URI( "http://10.0.2.2:8888/data/post/" )); List<NameValuePair>
postParameters = new
ArrayList<NameValuePair>(); postParameters.add( new
BasicNameValuePair( "token" , "alexzhou" )); UrlEncodedFormEntity
formEntity = new
UrlEncodedFormEntity( postParameters); request.setEntity(formEntity); HttpResponse
response = client.execute(request); reader
= new
BufferedReader( new
InputStreamReader(response .getEntity().getContent())); StringBuffer
strBuffer = new
StringBuffer( "" ); String
line = null ; while
((line = reader.readLine()) != null )
{ strBuffer.append(line); } result
= strBuffer.toString(); } catch
(Exception e) { e.printStackTrace(); } finally
{ if
(reader != null )
{ try
{ reader.close(); reader
= null ; } catch
(IOException e) { e.printStackTrace(); } } } return
result; } |
3.服務端代碼實現
上面是採用兩種方式的get和post請求的代碼,下面來實現服務端的代碼編寫,使用python+flask真的非常的簡單,就一個文件,前提是你得搭建好python+flask的環境,代碼如下:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
|
#coding=utf-8 import
json from
flask import
Flask,request,render_template app =
Flask(__name__) def
send_ok_json(data = None ): if
not
data: data =
{} ok_json =
{ 'ok' : True , 'reason' :' ',' data':data} return
json.dumps(ok_json) @app .route( '/data/get/' ,methods = [ 'GET' ]) def
data_get(): token =
request.args.get( 'token' ) ret =
'%s**%s'
% (token, 'get' ) return
send_ok_json(ret) @app .route( '/data/post/' ,methods = [ 'POST' ]) def
data_post(): token =
request.form.get( 'token' ) ret =
'%s**%s'
% (token, 'post' ) return
send_ok_json(ret) if
__name__ = =
"__main__" : app.run(host = "localhost" ,port = 8888 ,debug = True ) |
運行服務器,如圖:
4. 編寫單元測試代碼
右擊項目:new–》Source Folder取名tests,包名是:com.alexzhou.androidhttp.test(隨便取,沒有要求),結構如圖:
在該包下創建測試類HttpTest,繼承自AndroidTestCase。編寫這四種方式的測試方法,代碼如下:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
|
public
class
HttpTest extends
AndroidTestCase { @Override protected
void
setUp() throws
Exception { Log.e( "HttpTest" , "setUp" ); } @Override protected
void
tearDown() throws
Exception { Log.e( "HttpTest" , "tearDown" ); } public
void
testExecuteGet() { Log.e( "HttpTest" , "testExecuteGet" ); HttpClientTest
client = HttpClientTest.getInstance(); String
result = client.executeGet(); Log.e( "HttpTest" ,
result); } public
void
testExecutePost() { Log.e( "HttpTest" , "testExecutePost" ); HttpClientTest
client = HttpClientTest.getInstance(); String
result = client.executePost(); Log.e( "HttpTest" ,
result); } public
void
testExecuteHttpGet() { Log.e( "HttpTest" , "testExecuteHttpGet" ); HttpClientTest
client = HttpClientTest.getInstance(); String
result = client.executeHttpGet(); Log.e( "HttpTest" ,
result); } public
void
testExecuteHttpPost() { Log.e( "HttpTest" , "testExecuteHttpPost" ); HttpClientTest
client = HttpClientTest.getInstance(); String
result = client.executeHttpPost(); Log.e( "HttpTest" ,
result); } } |
附上HttpClientTest.java的其他代碼:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
|
public
class
HttpClientTest { private
static
final
Object mSyncObject = new
Object(); private
static
HttpClientTest mInstance; private
HttpClientTest() { } public
static
HttpClientTest getInstance() { synchronized
(mSyncObject) { if
(mInstance != null )
{ return
mInstance; } mInstance
= new
HttpClientTest(); } return
mInstance; } /**...上面的四個方法...*/ } |
現在還需要修改Android項目的配置文件AndroidManifest.xml,添加網絡訪問權限和單元測試的配置,AndroidManifest.xml配置文件的全部代碼如下:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
|
< manifest
xmlns:android = "http://schemas.android.com/apk/res/android" package = "com.alexzhou.androidhttp" android:versionCode = "1" android:versionName = "1.0"
> < uses-permission
android:name = "android.permission.INTERNET"
/> < uses-sdk android:minSdkVersion = "8" android:targetSdkVersion = "15"
/> < application android:icon = "@drawable/ic_launcher" android:label = "@string/app_name" android:theme = "@style/AppTheme"
> < uses-library
android:name = "android.test.runner"
/> < activity android:name = ".MainActivity" android:label = "@string/title_activity_main"
> < intent-filter > < action
android:name = "android.intent.action.MAIN"
/> < category
android:name = "android.intent.category.LAUNCHER"
/> </ intent-filter > </ activity > </ application > < instrumentation android:name = "android.test.InstrumentationTestRunner" android:targetPackage = "com.alexzhou.androidhttp"
/> </ manifest > |
注意:
android:name=”android.test.InstrumentationTestRunner”這部分不用更改
android:targetPackage=”com.alexzhou.androidhttp”,填寫應用程序的包名
5.測試結果
展開測試類HttpTest,依次選中這四個測試方法,右擊:Run As–》Android Junit Test。
(1)運行testExecuteHttpGet,結果如圖:
(2)運行testExecuteHttpPost,結果如圖:
(3)運行testExecuteGet,結果如圖:
(4)運行testExecutePost,結果如圖: