今天下了个新浪微博的API研究研究,目前实现了发布微博功能,包括带图片的微博。为了安全,新浪微博的API中并没有提供用微博帐号密码登录的功能,而是采用OAuth授权,用户通过浏览器访问新浪网站登录,登录成功后,浏览器再返回key和secret给程序。
main.xml:
1
2
3
4
5
6
7
8
9
10
11
12
13
|
<? xml version = "1.0" encoding = "utf-8" ?> < LinearLayout xmlns:android = "http://schemas.android.com/apk/res/android" android:orientation = "vertical" android:layout_width = "fill_parent" android:layout_height = "fill_parent" > < Button android:layout_width = "fill_parent" android:layout_height = "wrap_content" android:id = "@+id/login" android:text = "登录" /> < EditText android:id = "@+id/status" android:layout_width = "fill_parent" android:layout_height = "300sp" android:hint = "输入微博消息" /> < Button android:layout_width = "fill_parent" android:layout_height = "wrap_content" android:id = "@+id/send" android:text = "发布" /> </ LinearLayout > |
一个登录按钮,一个输入框,一个发布按钮
因为要接收浏览器返回的数据,所以,AndroidManifest.xml注册Activity的时候要加个Intent-Filter
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
|
<? xml version = "1.0" encoding = "utf-8" ?> < manifest xmlns:android = "http://schemas.android.com/apk/res/android" package = "com.pocketdigi.weibo" android:versionCode = "1" android:versionName = "1.0" > < uses-sdk android:minSdkVersion = "7" /> < application android:icon = "@drawable/icon" android:label = "@string/app_name" > < activity android:name = ".Main" android:label = "@string/app_name" > < intent-filter > < action android:name = "android.intent.action.MAIN" /> < category android:name = "android.intent.category.LAUNCHER" /> </ intent-filter > < intent-filter > < action android:name = "android.intent.action.VIEW" /> < category android:name = "android.intent.category.DEFAULT" /> < category android:name = "android.intent.category.BROWSABLE" /> < data android:scheme = "sina" android:host = "weibo" /> <!-- 监控sina://weibo这样的地址 --> </ intent-filter > </ activity > </ application > < uses-permission android:name = "android.permission.INTERNET" ></ uses-permission > </ manifest > |
intent-filter必须分成两段写,如果合在一起写,就启动不了了。
为了简便,直接把新浪Sample里的OAuthConstant类拷过来:
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
45
46
47
48
49
50
51
52
53
|
package weibo4android.androidexamples; import weibo4android.Weibo; import weibo4android.http.AccessToken; import weibo4android.http.RequestToken; public class OAuthConstant { private static Weibo weibo= null ; private static OAuthConstant instance= null ; private RequestToken requestToken; private AccessToken accessToken; private String token; private String tokenSecret; private OAuthConstant(){}; public static synchronized OAuthConstant getInstance(){ if (instance== null ) instance= new OAuthConstant(); return instance; } public Weibo getWeibo(){ if (weibo== null ) weibo= new Weibo(); return weibo; } public AccessToken getAccessToken() { return accessToken; } public void setAccessToken(AccessToken accessToken) { this .accessToken = accessToken; this .token=accessToken.getToken(); this .tokenSecret=accessToken.getTokenSecret(); } public RequestToken getRequestToken() { return requestToken; } public void setRequestToken(RequestToken requestToken) { this .requestToken = requestToken; } public String getToken() { return token; } public void setToken(String token) { this .token = token; } public String getTokenSecret() { return tokenSecret; } public void setTokenSecret(String tokenSecret) { this .tokenSecret = tokenSecret; } } |
接下来就是最关键的主程序:
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
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
|
package com.pocketdigi.weibo; import java.io.File; import weibo4android.Weibo; import weibo4android.WeiboException; import weibo4android.http.AccessToken; import weibo4android.http.RequestToken; import android.app.Activity; import android.content.Intent; import android.content.SharedPreferences; import android.content.SharedPreferences.Editor; import android.net.Uri; import android.os.Bundle; import android.view.View; import android.view.View.OnClickListener; import android.widget.Button; import android.widget.EditText; import android.widget.Toast; public class Main extends Activity { /** Called when the activity is first created. */ String key = "" , secret = "" ; Button login,send; EditText status; @Override public void onCreate(Bundle savedInstanceState) { super .onCreate(savedInstanceState); setContentView(R.layout.main); System.setProperty( "weibo4j.oauth.consumerKey" , "3997936609" ); System.setProperty( "weibo4j.oauth.consumerSecret" , "8bc9e3bfd6ae8e3b2b8bda9079918950" ); //设置在新浪应用开放平台申请的应用的key和secret login=(Button)findViewById(R.id.login); send=(Button)findViewById(R.id.send); status=(EditText)findViewById(R.id.status); login.setOnClickListener( new OnClickListener(){ @Override public void onClick(View v) { // TODO Auto-generated method stub login(); //登录 }}); send.setOnClickListener( new OnClickListener(){ @Override public void onClick(View v) { // TODO Auto-generated method stub String text=String.valueOf(status.getText()); Weibo weibo = new Weibo(); weibo.setToken(key,secret); try { //weibo.updateStatus(text); //只发文字 File f= new File( "/sdcard/wallpaper/129567208597069400.jpg" ); weibo.uploadStatus(text,f ); //发文字+图片,这里需要导入commons-httpclient-3.0.1.jar,自己网上下 //在实际项目上,最好放Thread里,因为按下去的时候按钮会卡 } catch (WeiboException e) { // TODO Auto-generated catch block e.printStackTrace(); } }}); } @Override protected void onStart() { // TODO Auto-generated method stub super .onStart(); //启动时执行检测是否来自网页登录返回 //如果是,获取key和secret //否则读取SharedPreferences //若得不到key和secret,直接跳转登录 Uri uri = this .getIntent().getData(); if (uri != null ) { //如果是浏览器返回 try { RequestToken requestToken = OAuthConstant.getInstance() .getRequestToken(); AccessToken accessToken = requestToken.getAccessToken(uri .getQueryParameter( "oauth_verifier" )); OAuthConstant.getInstance().setAccessToken(accessToken); // 保存 Editor sharedata = getSharedPreferences( "WeiBo" , 0 ).edit(); sharedata.putString( "key" , accessToken.getToken()); sharedata.putString( "secret" , accessToken.getTokenSecret()); sharedata.commit(); key = accessToken.getToken(); secret = accessToken.getTokenSecret(); } catch (WeiboException e) { e.printStackTrace(); } } else { //如果是用户自己启动 SharedPreferences settings = getSharedPreferences( "WeiBo" , 0 ); key = settings.getString( "key" , "" ); secret = settings.getString( "secret" , "" ); } if (key.equals( "" ) || secret.equals( "" )) { Toast.makeText( this , "尚未登录" , Toast.LENGTH_LONG).show(); login(); //跳转到浏览器登录 } } public void login(){ Weibo weibo = OAuthConstant.getInstance().getWeibo(); RequestToken requestToken; try { requestToken =weibo.getOAuthRequestToken( "sina://weibo" ); //为了避免与同类应用冲突,还是自己改下URI吧 Uri uri2 = Uri.parse(requestToken.getAuthenticationURL()+ "&from=xweibo" ); OAuthConstant.getInstance().setRequestToken(requestToken); startActivity( new Intent(Intent.ACTION_VIEW, uri2)); } catch (WeiboException e) { e.printStackTrace(); } } } |
发图片需要导入commons-httpclient-3.0.1.jar,否则启动报错,当然weibo4android-1.2.0.jar是不可少的