新浪微博单点授权(SSO)

本文介绍了新浪微博的单点授权(SSO)流程,包括为何选择SSO、使用条件、准备工作,如下载SDK、设置权限、在新浪开放平台创建应用。同时,详细讲解了授权参数接口的定义、授权信息的缓存以及集成SSO授权和获取用户名的步骤。文中还特别提醒了几个常见的错误及解决方案,如MD5签名工具的使用、回调页一致性、开发者身份认证和签名失效问题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

sso授权,指的是通过一键点击的简单方式唤起微博客户端行为的授权的方式,因为操作简单,所以作为很多应用的第三方登录的选择。

当然,你想使用这个功能,首先你得有本地客户端,否则的话,会使用web的授权方式,慢慢的输入你的账户和密码来获取授权。


在编码前,你得为此做些简单的准备工作。

        1.下载官方的SDK,在里面有实例和MD5的签名工具。

官方SDK

在里面的签名工具,根据你输入的包名来得到MD5值,你需要这个值来正确的创建应用。

在里面的还有weiboSDK,你需要把它加入你的应用中,引用其中的方法。

        2.在清单中加入访问网络的权限

        3.你需要在新浪的开放平台创建应用。

创建应用吧!


定义授权参数的接口:

(老实说,我是直接copy的demo,改为自己的授权信息就可以了)。

public interface Constants {

    /** 当前 DEMO 应用的 APP_KEY,第三方应用应该使用自己的 APP_KEY 替换该 APP_KEY */
    public static final String APP_KEY      = "1608434710";

    public static final String REDIRECT_URL = "http://www.sina.com";

    public static final String SCOPE = 
            "email,direct_messages_read,direct_messages_write,"
            + "friendships_groups_read,friendships_groups_write,statuses_to_me_read,"
            + "follow_app_official_microblog," + "invitation_write";
}

缓存授权信息:

/**
 * 该类定义了微博授权时所需要的参数。
 */
public class AccessTokenKeeper {
    private static final String PREFERENCES_NAME = "com_weibo_sdk_android";
    private static final String KEY_UID           = "uid";
    private static final String KEY_ACCESS_TOKEN  = "access_token";
    private static final String KEY_EXPIRES_IN    = "expires_in";
    
    /**
     * 保存 Token 对象到 SharedPreferences。
     * 
     * @param context 应用程序上下文环境
     * @param token   Token 对象
     */
    public static void writeAccessToken(Context context, Oauth2AccessToken token) {
        if (null == context || null == token) {
            return;
        }
        
        SharedPreferences pref = context.getSharedPreferences(PREFERENCES_NAME, Context.MODE_APPEND);
        Editor editor = pref.edit();
        editor.putString(KEY_UID, token.getUid());
        editor.putString(KEY_ACCESS_TOKEN, token.getToken());
        editor.putLong(KEY_EXPIRES_IN, token.getExpiresTime());
        editor.commit();
    }

    /**
     * 从 SharedPreferences 读取 Token 信息。
     * 
     * @param context 应用程序上下文环境
     * 
     * @return 返回 Token 对象
     */
    public static Oauth2AccessToken readAccessToken(Context context) {
        if (null == context) {
            return null;
        }
        
        Oauth2AccessToken token = new Oauth2AccessToken();
        SharedPreferences pref = context.getSharedPreferences(PREFERENCES_NAME, Context.MODE_APPEND);
        token.setUid(pref.getString(KEY_UID, ""));
        token.setToken(pref.getString(KEY_ACCESS_TOKEN, ""));
        token.setExpiresTime(pref.getLong(KEY_EXPIRES_IN, 0));
        return token;
    }

    /**
     * 清空 SharedPreferences 中 Token信息。
     * 
     * @param context 应用程序上下文环境
     */
    public static void clear(Context context) {
        if (null == context) {
            return;
        }
        
        SharedPreferences pref = context.getSharedPreferences(PREFERENCES_NAME, Context.MODE_APPEND);
        Editor editor = pref.edit();
        editor.clear();
        editor.commit();
    }
}


集成的sso授权 +获取用户名:

/**
 * 该类主要演示如何进行授权、SSO登陆。
 */
public class WBAuthActivity extends Activity implements OnClickListener {
	/** 显示认证后的信息,如 AccessToken */
	private TextView mTokenText;
	/** 微博 Web 授权类,提供登陆等功能 */
	private WeiboAuth mWeiboAuth;
	/** 封装了 "access_token","expires_in","refresh_token",并提供了他们的管理功能 */
	private Oauth2AccessToken mAccessToken;
	/** 注意:SsoHandler 仅当 SDK 支持 SSO 时有效 */
	private SsoHandler mSsoHandler;
	/** 用户信息接口 */
	private UsersAPI mUsersAPI;
	private Button ssoBtn;

	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.acy_sinasso);
		initView();
	}

	public void initView() {
		mTokenText = (TextView) findViewById(R.id.tv_txt);
		// SSO 授权
		ssoBtn = (Button) findViewById(R.id.btn_sso);

		// 创建微博实例
		mWeiboAuth = new WeiboAuth(this, Constants.APP_KEY,
				Constants.REDIRECT_URL, Constants.SCOPE);
		// 从 SharedPreferences 中读取上次已保存好 AccessToken 等信息,
		// 第一次启动本应用,AccessToken 不可用
		 mAccessToken = AccessTokenKeeper.readAccessToken(this);
		 
		if (mAccessToken.isSessionValid()) {
			updateTokenView(true);
		}
		ssoBtn.setOnClickListener(this);
	}

	/**
	 * 当 SSO 授权 Activity 退出时,该函数被调用。
	 */
	@Override
	protected void onActivityResult(int requestCode, int resultCode, Intent data) {
		super.onActivityResult(requestCode, resultCode, data);
		// SSO 授权回调
		// 重要:发起 SSO 登陆的 Activity 必须重写 onActivityResult
		if (mSsoHandler != null) {
			mSsoHandler.authorizeCallBack(requestCode, resultCode, data);
		}
	}

	/**
	 * 微博认证授权回调类。 1. SSO 授权时,需要在 {@link #onActivityResult} 中调用
	 * {@link SsoHandler#authorizeCallBack} 后, 该回调才会被执行。 2. 非 SSO
	 * 授权时,当授权结束后,该回调就会被执行。 当授权成功后,请保存该 access_token、expires_in、uid 等信息到
	 * SharedPreferences 中。
	 */
	class AuthListener implements WeiboAuthListener {
		// 授权完成
		@Override
		public void onComplete(Bundle values) {
			// 从 Bundle 中解析 Token
			mAccessToken = Oauth2AccessToken.parseAccessToken(values);
			if (mAccessToken.isSessionValid()) {
				// 显示 Token
				updateTokenView(false);

				// 保存 Token 到 SharedPreferences
				AccessTokenKeeper.writeAccessToken(WBAuthActivity.this,
						mAccessToken);
				Toast.makeText(WBAuthActivity.this, "success!!",
						Toast.LENGTH_SHORT).show();

				// 根据uid 获取用户的昵称,因为uid是在回调方法从服务器传递过来的数据中。
				long uid = Long.parseLong(mAccessToken.getUid());
				mUsersAPI.show(uid, mListener);
			} else {
				// 以下几种情况,您会收到 Code:
				// 1. 当您未在平台上注册的应用程序的包名与签名时;
				// 2. 当您注册的应用程序包名与签名不正确时;
				// 3. 当您在平台上注册的包名和签名与您当前测试的应用的包名和签名不匹配时。
				Toast.makeText(WBAuthActivity.this, "fail", Toast.LENGTH_LONG)
						.show();
			}
		}

		// 取消授权
		@Override
		public void onCancel() {
			Toast.makeText(WBAuthActivity.this, "cancel", Toast.LENGTH_LONG)
					.show();
		}

		// 授权异常
		@Override
		public void onWeiboException(WeiboException e) {
			Toast.makeText(WBAuthActivity.this,
					"Auth exception : " + e.getMessage(), Toast.LENGTH_LONG)
					.show();
		}
	}

	/**
	 * 显示当前 Token 信息。 配置文件中是否已存在 token 信息并且合法
	 */
	public void updateTokenView(boolean hasExisted) {
		// 获取用户信息接口
		mUsersAPI = new UsersAPI(mAccessToken);

		String date = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss")
				.format(new java.util.Date(mAccessToken.getExpiresTime()));
		String format = getString(R.string.weibosdk_demo_token_to_string_format_1);
		mTokenText
				.setText(String.format(format, mAccessToken.getToken(), date));
		String message = String.format(format, mAccessToken.getToken(), date);
		if (hasExisted) {
			message = getString(R.string.weibosdk_demo_token_has_existed)
					+ "\n" + message;
			// 根据uid 获取用户的昵称,因为uid是在回调方法从服务器传递过来的数据中。
			long uid = Long.parseLong(mAccessToken.getUid());
			mUsersAPI.show(uid, mListener);
		}
		mTokenText.setText(message);
	}

	/**
	 * 微博 OpenAPI 回调接口。
	 */
	private RequestListener mListener = new RequestListener() {
		@Override
		public void onComplete(String response) {
			if (!TextUtils.isEmpty(response)) {
				// 调用 User#parse 将JSON串解析成User对象
				User user = User.parse(response);
				if (user != null) {
					Toast.makeText(WBAuthActivity.this,
							"获取User信息成功,用户昵称:" + user.screen_name,
							Toast.LENGTH_LONG).show();
					mTokenText.setText(user.screen_name);
				} else {
					Toast.makeText(WBAuthActivity.this, response,
							Toast.LENGTH_LONG).show();
				}
			}
		}

		@Override
		public void onWeiboException(WeiboException e) {
			ErrorInfo info = ErrorInfo.parse(e.getMessage());
			Toast.makeText(WBAuthActivity.this, info.toString(),
					Toast.LENGTH_LONG).show();
		}
	};

	@Override
	public void onClick(View v) {
		// TODO Auto-generated method stub
		if (v == ssoBtn) {
			mSsoHandler = new SsoHandler(WBAuthActivity.this, mWeiboAuth);
			mSsoHandler.authorize(new AuthListener());
		}
	}
}

布局:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >

    <com.sina.weibo.sdk.widget.LoginButton
        android:id="@+id/btn_sso"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginLeft="10dp" />

    <TextView
        android:id="@+id/tv_txt"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="info" />

</LinearLayout>

运行:

注意:

注意:

1.md5签名工具不能使用

你在使用签名工具前,需要先在你的设备上安装该应用。

2.认证消息出错

检查自己的回调页和自己应用中的回调页是否一致。
3.如果你的开发者身份没有认证,那么昨天申请的签名,今天可能不能用了,需要重新申请签名。

4.sso package or sign error:

有可能是签名失效了,你重新用md5签名工具申请个新的就可以了。

sso package or sign error


评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值