简体   繁体   English

REST API令牌认证

[英]REST API token authentication

I just started a development of my first REST API in .NET. 我刚刚开始开发.NET中的第一个REST API。 Since it will be stateless I will use tokens for authentication: 由于它将是无状态的,因此我将使用令牌进行身份验证:

Basic idea (System.Security.Cryptography): 基本思想(System.Security.Cryptography):

  • AES for encryption + HMACSHA256 for integrity AES用于加密+ HMACSHA256用于完整性
  • token data will consist object with properties: username, date of issuing and timeout 令牌数据将由具有以下属性的对象组成:用户名,发行日期和超时
  • database will hold username, hashed password and HMAC hash 数据库将保存用户名,哈希密码和HMAC哈希

Login: 登录:

  • check if credentials are valid (username, compare hashed password to db value) 检查凭据是否有效(用户名,将哈希密码与db值进行比较)
  • if true, encrypt data object 如果为true,则加密数据对象
  • use HMAC on generated token and store it to database 在生成的令牌上使用HMAC并将其存储到数据库
  • return token (without HMAC) to user (cookie/string) 向用户返回令牌(无HMAC)(cookie /字符串)

Request to method which requires authentication: 对需要身份验证的方法的请求:

  • user sends token with each request 用户随每个请求发送令牌
  • token is decrypted 令牌已解密
  • if it is expired, error 如果过期,则报错
  • if not expired use HMAC and compare username + generated hash with db values 如果未过期,请使用HMAC并将用户名+生成的哈希与db值进行比较
  • if db check valid, user is authenticated 如果数据库检查有效,则表明用户已通过身份验证

The way I see it, this approach has following pros: 在我看来,这种方法具有以下优点:

  • even if db is comprosmised, it does not contain actual token (hash cannot be reversed...) 即使db被破坏,它也不包含实际的令牌(哈希不能反转...)
  • even if attacker has token, he cannot increase expiration by updating fields since expiration date is in the token itself 即使攻击者拥有令牌,他也无法通过更新字段来增加过期时间,因为过期日期在令牌本身中

Now firstly, I wonder if this is good approach at all. 现在,首先,我想知道这是否是个好方法。

Besides that I still didn't figure out, where to store AES and SHA256 keys on server (should i just hardcode them? If I put them into web.config or use machine key than I have a problem in case of load balanced servers,...). 除此之外,我仍然不知道在服务器上的哪个位置存储AES和SHA256密钥(我应该对它们进行硬编码吗?如果我将它们放入web.config或使用机器密钥,那么在负载均衡服务器的情况下,我会遇到问题, ...)。

And lastly where do I store AES IV vectors, since Crypto.CreateEncryptor requires it for decryption? 最后,由于Crypto.CreateEncryptor要求使用它进行解密,因此我应该将AES IV向量存储在哪里? Does it mean that users have to send token + IV with each request? 这是否意味着用户必须在每个请求中发送令牌+ IV?

I hope this makes any sense and I thank you for answers in advance. 我希望这是有道理的,我先感谢您的回答。

UPDATE: 更新:

Ok, now I did some more research and came down with this solution: 好的,现在我进行了更多研究,并得出了以下解决方案:

  • token will contain originally specified data (username, date of issuing and timeout) 令牌将包含原始指定的数据(用户名,发行日期和超时)
  • token is generated with encrypt-then-mac (it includes AES encrypted data, IV vector + tag of these 2 values for authentication, generated with HMACSHA265) 令牌是使用crypto-then-mac生成的(它包括AES加密数据,IV矢量+这两个用于身份验证的值的标记,是使用HMACSHA265生成的)
  • token tag will be written to db 令牌标记将被写入数据库
  • user will be authenticated if: 在以下情况下,将对用户进行身份验证:
    • tag is valid (token authentication) 标签有效(令牌认证)
    • data can be decrypted 数据可以解密
    • token has not expired yet 令牌尚未过期
    • tag matches the one written in database 标签与数据库中写的标签匹配
    • user is not blocked in database (token invalidation on demand) 用户未在数据库中被阻止(按需令牌无效)
  • keys will be stored in web.config separate section. 密钥将存储在web.config的单独部分中。 Same keys will have to be on every server (per application of course) 每个服务器上必须有相同的密钥(当然,每个应用程序都需要)

I didn't use FormsAuthenticationTicket because in .NET there are following issues: 我没有使用FormsAuthenticationTicket,因为在.NET中存在以下问题:

This is a follow up from the comment thread under the question. 这是该问题下的注释线程的后续操作。

You seem to be a bit confused as to what, exactly, OAuth is, so hopefully I can clarify it here. 您对于OAuth的确切含义似乎有些困惑,因此希望我可以在这里进行澄清。

OAuth is not a web service or something you consume. OAuth不是Web服务或您使用的东西。 It is a protocol that describes the way that a site can authenticate a user against a service, without allowing the site to know what the user's credentials are. 它是一个协议,描述了站点可以针对服务对用户进行身份验证的方式,而又不允许站点知道用户的凭据是什么。 As a side benefit, most OAuth providers also have a web service to query the user's information, and permission to do so can be granted at the same time. 作为附带的好处,大多数OAuth提供程序还具有Web服务来查询用户的信息,并且可以同时授予这样做的权限。

Typically, you are interested in implementing OAuth from the perspective of the site (eg, AcmeWidgets.com) so that a user can log in via Facebook or Google or something. 通常,您会对从网站(例如AcmeWidgets.com)的角度实现OAuth感兴趣,以便用户可以通过Facebook或Google或其他方式登录。 However, you can also implement the service side (eg, where Facebook normally would be), and allow others to authenticate against YOU. 但是,您也可以实现服务端(例如,Facebook通常位于的位置),并允许其他人对您进行身份验证。

So, for example, let's say you have a web service to allow for third-party sites to provision Acme-brand Widgets for users. 例如,假设您有一个Web服务,允许第三方站点为用户提供Acme品牌的窗口小部件。 Your first third-party implementor is the popular MyBook.org. 您的第一个第三方实现者是流行的MyBook.org。 The flow would look something like this: 流看起来像这样:

  1. Someone invites the User to use the "Acme Widgets" app on their MyBook profile. 有人邀请用户在其MyBook个人资料上使用“ Acme Widgets”应用程序。
  2. The user clicks on the button, which redirects to AcmeWidgets.com. 用户单击按钮,该按钮将重定向到AcmeWidgets.com。 The URL looks something like: 该网址看起来像:

    http://acmewidgets.com/oauth/user?r=http%3A%2F%2Fmybook.org%2Foauth%2Fclient&appid=12345

  3. The user is asked if they want to allow MyBook to access their data and provision widgets. 询问用户是否要允许MyBook访问其数据和置备小部件。
  4. The user clicks Yes, whereupon Acme Widgets notes that the user has allowed it. 用户单击“是”,随后Acme Widgets指出该用户已允许它。
  5. The user is redirected back to MyBook, at a URL like this: 用户将通过以下URL重定向回MyBook:

    http://mybook.org/oauth/client?token=ABCDEFG

  6. MyBook, on the server side, now takes that token, and places a web service call BACK to AcmeWidgets: 服务器端的MyBook现在获取该令牌,并将Web服务调用BACK放置到AcmeWidgets:

    http://acmewidgets.com/oauth/validate?token=ABCDEFG&appid=12345&appsecret=67890

  7. AcmeWidgets replies with the final authentication token identifying the user. AcmeWidgets会以最终身份验证令牌进行答复,以标识用户。
  8. Alternately, it fails, which means the user is trying to fake a token, or they denied permission or some other failure condition. 或者,它失败,这意味着用户正在尝试伪造令牌,或者他们拒绝了许可或某些其他失败情况。
  9. MyBook, with the token, can now call AcmeWidgets APIs: 带有令牌的MyBook现在可以调用AcmeWidgets API:

    http://acmewidgets.com/api/provision?appid=12345&token=ABC123&type=etc

This is all known as the OAuth dance. 这就是众所周知的OAuth舞蹈。 Note that there are a number of implementation defined things here, like URLs, the means of encoding the various tokens, whether tokens can expire or be revoked, etc. 请注意,这里有许多实现定义的内容,例如URL,各种令牌的编码方式,令牌是否可以过期或被撤销等。

Hopefully that clears everything up for you! 希望这可以为您清除一切!

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM