Bri*_*chi 121

我是作者everyauth.

我写的everyauth是因为我发现connect-auth缺乏以下方面:

  1. 简单而强大的配置

    特别是,在可配置性方面缺乏的一个领域是动态设置facebook的"范围"安全设置.

  2. 良好的调试支持

    我发现connect-auth在精确定位auth过程的部分失败方面,调试并不那么直接.这主要是由于connect-auth设置其嵌套回调的方式.

通过everyauth,我尝试创建一个系统来解决我使用connect-auth遇到的问题.

  • 在配置上 - 每个everyauth auth模块都被定义为一系列步骤和可配置参数.因此,对于您想要更改的参数(例如,主机名,回调URL等)或步骤(例如,getAccessToken,addToSession),您具有类似手术的精确度.有了connect-auth,如果你想改变除了每个auth策略提供的少数内置可配置参数之外的东西,你必须重新编写this.authenticate定义所有策略逻辑的整个函数.换句话说,它的可配置性精度低于everyauth.在其他情况下,您不能使用connect-auth- 例如,实现动态Facebook"范围"可配置性 - 即,当他们到达需要更多权限的应用程序部分时,逐渐要求用户获得更多的Facebook权限.

    除了可配置的步骤和参数之外,您还可以利用everyauthauth模块继承.所有模块都从每个模块auth模块继承原型.所有基于OAuth2的模块都继承自oauth2模块.假设您希望所有oauth2模块的行为都不同.您需要做的就是修改oauth2 auth模块,所有基于oauth2的模块都将从中继承新的行为.

  • 在调试时 - everyauth在我看来,它具有更好的调试可见性,因为它将每个模块明确地分成了它组成的步骤.通过设置

    everyauth.debug = true;
    
    Run Code Online (Sandbox Code Playgroud)

    您将获得身份验证过程中已完成哪些步骤以及哪些步骤失败的输出.您还可以精确控制每个身份验证策略中的每个步骤在超时之前的时间长度.

  • 在可扩展性方面 - 我设计了everyauth以最大化代码重用.如前所述,所有模块都从每个模块auth模块继承原型.这意味着您可以实现非常模块化的系统,同时在从祖先模块中覆盖特定步骤方面具有细粒度控制.要了解使用您自己的auth模块扩展Everyauth是多么容易,只需查看everyauth源中的任何特定auth模块.

  • 关于可读性 - 我发现everyauth源代码更易于阅读.有了connect-auth,我发现自己跳过几个文件,以了解在什么情况下(即,在什么步骤,在everyauth用语中)由策略配置的每个嵌套回调运行.有了everyauth,你确切地知道哪个逻辑与哪个上下文相关联(也就是步骤).例如,以下是描述oauth2提供程序重定向回服务时会发生什么的代码:

    .get('callbackPath',                                                                                                                                               
         'the callback path that the 3rd party OAuth provider redirects to after an OAuth authorization result - e.g., "/auth/facebook/callback"')                     
      .step('getCode')
        .description('retrieves a verifier code from the url query')                                                                                                   
        .accepts('req res')  
        .promises('code')                                                       
        .canBreakTo('authCallbackErrorSteps')
      .step('getAccessToken')
        .accepts('code')
        .promises('accessToken extra')                                                                                                                                 
      .step('fetchOAuthUser')
        .accepts('accessToken')                                                                                                                                        
        .promises('oauthUser')
      .step('getSession')
        .accepts('req')
        .promises('session')
      .step('findOrCreateUser')                                                                                                                                        
        .accepts('session accessToken extra oauthUser')                                                                                                                
        .promises('user')
      .step('compile')
        .accepts('accessToken extra oauthUser user')
        .promises('auth')
      .step('addToSession')
        .accepts('session auth')                                                                                                                                       
        .promises(null)
      .step('sendResponse')
        .accepts('res')
        .promises(null)
    
    Run Code Online (Sandbox Code Playgroud)

    无需解释这是如何工作的,看看oauth2策略的作用非常简单.想知道getCode的作用吗?来源再次非常简单:

    .getCode( function (req, res) {
      var parsedUrl = url.parse(req.url, true);
      if (this._authCallbackDidErr(req)) {
        return this.breakTo('authCallbackErrorSteps', req, res);
      }
      return parsedUrl.query && parsedUrl.query.code;
    })
    
    Run Code Online (Sandbox Code Playgroud)

    将这一切与connect-auth我们的Facebook代码进行比较,至少对我来说,花费的时间比我想象的还要多,以便弄清楚什么时候会被执行.这主要是因为代码跨文件传播的方式,以及使用单个authenticate方法和嵌套回调来定义身份验证逻辑(everyauth使用promises将逻辑分解为易于理解的步骤):

    that.authenticate= function(request, response, callback) {
      //todo: makw the call timeout ....
      var parsedUrl= url.parse(request.url, true);
      var self= this;
      if( parsedUrl.query && parsedUrl.query.code  ) {
        my._oAuth.getOAuthAccessToken(parsedUrl.query && parsedUrl.query.code ,
           {redirect_uri: my._redirectUri}, function( error, access_token, refresh_token ){
             if( error ) callback(error)
             else {
               request.session["access_token"]= access_token;
               if( refresh_token ) request.session["refresh_token"]= refresh_token;
                 my._oAuth.getProtectedResource("https://graph.facebook.com/me", request.session["access_token"], function (error, data, response) {
                   if( error ) {
                     self.fail(callback);
                   }else {
                     self.success(JSON.parse(data), callback)
                   }
                 })
             }
        });
      }
      else {
         request.session['facebook_redirect_url']= request.url;
         var redirectUrl= my._oAuth.getAuthorizeUrl({redirect_uri : my._redirectUri, scope: my.scope })
         self.redirect(response, redirectUrl, callback);
       }
    }
    
    Run Code Online (Sandbox Code Playgroud)

其他一些差异:

  • everyauth支持传统的基于密码的身份验证 connect-auth在撰写本文时,并非如此.
  • connect-auth中的foursquare和google支持基于较旧的OAuth1.a规范.everyauth的foursquare和谷歌模块基于他们对更新的OAuth2规范的实现.
  • OpenId支持everyauth.
  • everyauth的文档比connect-auth更全面.

最后,评论Nathan的答案,该答案不确定同时everyauth支持多个提供商,everyauth是否支持多个并发提供商.在everyauthgithub页面上的README 提供了有关如何使用它everyauth来实现此目的的说明.

总而言之,我认为库的选择取决于开发人员.我和其他人everyauth从他们的角度发现更强大.正如内森的回答所示,但其他人发现connect-auth他们更喜欢自己的偏好.无论你的选择是什么,我希望这篇关于我写作原因的文章everyauth可以帮助你做出决定.

  • 谢了哥们.非常信息和伟大,开发人员不仅关心你提到的所有事情,而且关心它.道具给你:) (12认同)

Nat*_*eyn 18

两个库在功能集方面都非常接近,特别是在支持的提供程序方面.connect-auth提供开箱即用的支持,使您自己的oAuth提供商,所以如果您需要这样的东西,这可以很好地帮助您.

我在两者之间注意到的主要问题是,我发现connect-auth它创建和接受中间件的方式更加清晰; 你只需要查看中间件所需的预配置量,everyauth看看它会变得混乱.

另一件不明确的事情是,是否同时everyauth支持多个提供商; 有connect-auth,似乎有可能/更简单,虽然我还没有这个尝试自己.