使用DotNetOpenAuth来实现有道云笔记的授权

     最近由于公司的需求特别多,而且还不是一个项目的需求,几个数据库几个VS来回切换。难免搞混搞乱,忘记。于是自己用WPF做了一个小工具:AgileToDo,一个待办列表。本来使用sqlce来做本地的存储。但是在这个云时代,搞本地存储显然不能拿出手。于是我决定给它集成有道云笔记,使用有道云笔记的的OPEN API来实现云端的存储。http://note.youdao.com/open/apidoc.html

     有道云笔记的API使用OAuth的方式对第三方应用进行授权。OAuth的介绍就不多说了,说的人也挺多了,自己查资料吧。要使用它的API,我们需要授权。本来想完全有自己去实现一下这个过程的,不过看了授权的整个过程发现还是很复杂的,不花点时间估计还真搞不出来。于是用nuget搜一下发现了DotNetOpenAuth,而且这个类库的排名是很靠前的,想必是个神器。大声笑这里简单说一下DotNetOpenAuth,据我简单了解,DotNetOpenAuth主要是分了2部分的功能。一部分类库是作为消费者,访问第三方OAUTH服务,请求授权,比如我现在要做的事,访问有道云笔记的OAUTH服务。还有一部分类库是用做服务方,实现OAUTH服务提供方的功能,可以使你的用户系统支持OAUTH,供第三方消费者来使用。要深入了解的请直接去下载源码,而且里面包含了很多sample,有web的有desktop的,访问google,twitter的例子等等等。我的代码当然也是参考了这些sample。

      经过一晚上的折腾,终于用.NET实现了有道云笔记的授权。废话不多说,上代码吧。

1.添加DotNetOpenAuth的引用

image

2.YDAuthBaseInfo类

    /// <summary>

    /// OAUTH授权所需的一些基础信息

    /// </summary>

    public class YDAuthBaseInfo

    {

        public static readonly string OwnerId = "";

        public static readonly string ConsumerName = "";

        public static readonly string ConsumerKey = "";//开发者申请的KEY

        public static readonly string ConsumerSecret = "";//开发者申请的Secret



        public static readonly string BaseUrl = "http://sandbox.note.youdao.com";//测试沙箱基础url

        public static readonly ServiceProviderDescription ServiceDescription = null;//OAUTH服务提供方信息

        static YDAuthBaseInfo()

        {

            OwnerId = "kklldog";

            ConsumerName = "AgileToDo";

            ConsumerKey = "xxxx";

            ConsumerSecret = "xxxx";

            ServiceDescription = new ServiceProviderDescription

            {

                RequestTokenEndpoint = new MessageReceivingEndpoint(YDAuthBaseInfo.BaseUrl + "/oauth/request_token",

                    HttpDeliveryMethods.AuthorizationHeaderRequest | HttpDeliveryMethods.GetRequest),

                UserAuthorizationEndpoint = new MessageReceivingEndpoint(YDAuthBaseInfo.BaseUrl + "/oauth/authorize",

                    HttpDeliveryMethods.AuthorizationHeaderRequest | HttpDeliveryMethods.GetRequest),

                AccessTokenEndpoint = new MessageReceivingEndpoint(YDAuthBaseInfo.BaseUrl + "/oauth/access_token", 

                    HttpDeliveryMethods.AuthorizationHeaderRequest | HttpDeliveryMethods.GetRequest),

                TamperProtectionElements = new ITamperProtectionChannelBindingElement[] { new HmacSha1SigningBindingElement() },

            };

        }





    }

3.YDTokenManager 类

    /// <summary>

    /// TokenManager 令牌管理

    /// </summary>

    public class YDTokenManager : IConsumerTokenManager

    {

        private Dictionary<string, string> _tokensAndSecrets = new Dictionary<string, string>();

        private TokenType _tokenType;

        /// <summary>

        /// Initializes a new instance of the <see cref="YDTokenManager"/> class.

        /// </summary>

        /// <param name="consumerKey">The consumer key.</param>

        /// <param name="consumerSecret">The consumer secret.</param>

        public YDTokenManager(string consumerKey, string consumerSecret)

        {

            if (string.IsNullOrEmpty(consumerKey))

            {

                throw new ArgumentNullException("consumerKey");

            }



            this.ConsumerKey = consumerKey;

            this.ConsumerSecret = consumerSecret;

        }



        /// <summary>

        /// Gets the consumer key.

        /// </summary>

        /// <value>The consumer key.</value>

        public string ConsumerKey { get; private set; }



        /// <summary>

        /// Gets the consumer secret.

        /// </summary>

        /// <value>The consumer secret.</value>

        public string ConsumerSecret { get; private set; }



        #region ITokenManager Members





        public string GetTokenSecret(string token)

        {

            return this._tokensAndSecrets[token];

        }



 

        public void StoreNewRequestToken(UnauthorizedTokenRequest request, ITokenSecretContainingMessage response)

        {

            this._tokensAndSecrets[response.Token] = response.TokenSecret;

            _tokenType = TokenType.RequestToken;

        }



        public void ExpireRequestTokenAndStoreNewAccessToken(string consumerKey, string requestToken, string accessToken, string accessTokenSecret)

        {

            this._tokensAndSecrets.Remove(requestToken);

            this._tokensAndSecrets[accessToken] = accessTokenSecret;

            _tokenType = TokenType.AccessToken;

        }



        /// <summary>

        /// Classifies a token as a request token or an access token.

        /// </summary>

        /// <param name="token">The token to classify.</param>

        /// <returns>Request or Access token, or invalid if the token is not recognized.</returns>

        public TokenType GetTokenType(string token)

        {

            return _tokenType;

        }



        #endregion

    }
 
4.YDWebConsumer类
    /// <summary>

    /// 有道OPEN AUTH的web端消费者实现

    /// </summary>

    public class YDWebConsumer:WebConsumer

    {

        public YDWebConsumer(ServiceProviderDescription serviceProvider, IConsumerTokenManager tokenManager)

            : base(serviceProvider, tokenManager)

        {

        }

        /// <summary>

        /// 请求授权

        /// </summary>

        /// <param name="consumer"></param>

        public static void RequestAuthorization(YDWebConsumer consumer)

        {

            if (consumer == null)

            {

                throw new ArgumentNullException("YDWebConsumer");

            }



            Uri callback = GetCallbackUrlFromContext();

            var request = consumer.PrepareRequestUserAuthorization(callback, null, null);

            consumer.Channel.Send(request);

        }



        /// <summary>

        /// 获取CALLBACKURL

        /// </summary>

        /// <returns></returns>

        internal static Uri GetCallbackUrlFromContext()

        {

            Uri callback = MessagingUtilities.GetRequestUrlFromContext().StripQueryArgumentsWithPrefix("oauth_");

            return callback;

        }

    }

5.有了这些我们就可以去请求授权了。让我们来试试,新建一个ASP.NET项目,在Default.aspx下修改代码

<%@ Page Title="主页" Language="C#" MasterPageFile="~/Site.master" AutoEventWireup="true"

    CodeBehind="Default.aspx.cs" Inherits="YDOpenAPI._Default" %>



<asp:Content ID="HeaderContent" runat="server" ContentPlaceHolderID="HeadContent">

</asp:Content>

<asp:Content ID="BodyContent" runat="server" ContentPlaceHolderID="MainContent">

    <h2>

        欢迎使用 ASP.NET!

    </h2>

    <asp:Label runat="server" ID="lbl"></asp:Label>

    </asp:Content>

 

        protected void Page_Load(object sender, EventArgs e)

        {

            if (!IsPostBack)

            {

                var youDao = new YDWebConsumer(YDAuthBaseInfo.ServiceDescription, this.TokenManager);



                // 是否已经授权
                var accessTokenResponse = youDao.ProcessUserAuthorization();

                if (accessTokenResponse != null)

                {

                    this.AccessToken = accessTokenResponse.AccessToken;

                    this.lbl.Text ="Token:"+ this.AccessToken+" Screct:"+this.TokenManager.GetTokenSecret(this.AccessToken);

                }

                else if (this.AccessToken == null)

                {

                    

                    YDWebConsumer.RequestAuthorization(youDao);

                }

            }

        }
 
//TokenManager   

 private YDTokenManager TokenManager

        {

            get

            {

                var tokenManager = (YDTokenManager)Session["tokenManager"];

                if (tokenManager == null)

                {

                    string consumerKey = YDOpenAPI4N.YDAuthBaseInfo.ConsumerKey;

                    string consumerSecret = YDOpenAPI4N.YDAuthBaseInfo.ConsumerSecret;

                    if (!string.IsNullOrEmpty(consumerKey))

                    {

                        tokenManager = new YDTokenManager(consumerKey, consumerSecret);

                        Session["tokenManager"] = tokenManager;

                    }

                }



                return tokenManager;

            }

        }
 
跑一下是不是成功了。
image
image

有了AccessToken跟AccessSecret我们就可以去访问有道云笔记的操作API了:创建,删除,修改笔记了。这部分接下来我也会实现。

      希望对于需要了解OAUTH跟DOTNETOPENAUTH的同学能有帮助。马上回来

你可能感兴趣的:(open)