基于令牌的身份验证在php

基于令牌的身份验证在php

问题描述:

我在我的web服务器上有一个REST服务,用php编写。我想知道,什么是最好的认证(除了基本的http访问认证)。 我听说过基于令牌的身份验证,并想问问是否有人可以解释主要步骤。基于令牌的身份验证在php

  • 在GET上:令牌是否可见? (是不是不安全?)
  • 如何令标记仅在特定时间有效?
  • ...

客户端:安卓/浏览器;服务器:Apache,PHP5

+0

使其通过POST方法 – 2012-03-01 04:46:26

+6

作为隐藏字段这将是一个问题的REST的服务意识,如果我只能用POST) 我已经实现PUT,POST,GET,DELETE的当然每种http方法都有不同的功能 – 2012-03-01 04:50:32

+0

隐藏您的令牌的可见性 – 2012-03-01 04:52:34

它可以以任何方式完成,GET请求中的值实际上比POST请求中的值更加可见。如果有人可以“看到”(即拦截)请求,他可以看到你发送的所有内容。最后,HTTP请求只是一堆HTTP头,可能跟一个主体。该URL将在第一行GET /foo/bar HTTP/1.1行中发送,其他值仅在不同的行中发送。

因此,您希望您的身份验证令牌发送。你可以要求它是附加到每个请求的查询参数:

GET /foo/bar?user=123456&token=abcde... 

要真正使用如同预期的HTTP协议,你应该使用Authorization HTTP标头:

Authorization: MyScheme 123456:abcde... 

内容这个标题的完全取决于你。它通常指定一个授权方法,如Basic,然后是您想要验证的任何内容。这可以简单地是用户名和密码,它们的散列,客户端在某个点或其他任何地方获得的不透明令牌。

我推荐一个令牌系统或请求签名系统,后者是非常受欢迎的。在请求签名系统中,客户端必须从您那里获取令牌。然后它发送该令牌的散列和该请求的某些特征以验证该请求,例如, sha1(Token + Timestamp + Request URL + Request Body)。您的服务器可以验证这一点,而无需客户端在每个请求上以纯文本形式发送令牌。

如何令令牌仅在特定时间有效?

您使用过期时间戳保存令牌服务器端并检查它。

+0

谢谢,我想我现在已经有了基本的想法。只有几个问题:1.当客户端获得令牌时 - 例如,这将是一个“简单的json文件”,包含“TOKEN_A”? 2.如果客户端只发送散列(包括时间戳),如何在服务器端检查散列是否有效?循环遍历las X ms的可能哈希? – 2012-03-01 05:56:04

+3

1.是的,无论你最适合你的模型。也许用户需要在网站上注册并从那里复制并粘贴令牌。也许你也是通过API来做到的,在这种情况下,JSON响应就没有问题。 2. Authorization标头需要包含用户标识和令牌散列。该请求还必须包含时间戳,例如在Date标头中,这是非常标准的。哈希将基于该文字“Date”标题。您的服务器只是为用户查找令牌,确保Date在当前时间的±几分钟内,并重新创建相同的散列。 – deceze 2012-03-01 06:00:39

+1

所以基本的想法是:而不是简单地发送令牌,我发送散列和信息A,B,C。服务器从UID获取令牌,并将其与信息A,B,C进行哈希处理。并检查哈希是否相同?! - (+时间验证人员) - 这很聪明:D谢谢你的很多 – 2012-03-01 06:08:45

这是关于基于令牌的认证的question。我认为今天最常见的基于令牌的认证是OAuth。但要回答您的问题:

在GET上:令牌是否可见? (是不是不安全?)

你可以通过HTTP头传递你的标记,所以他们不容易看到。 OAuth allows this。请注意,令牌仍然可见,它们只是不在GET查询参数中。

如何令令牌仅在特定时间有效?

由于您控制(创建)令牌,您可以设置每个令牌的到期日期。在API的每个请求中,如果给定的令牌仍然有效,您应该只检查令牌存储(例如数据库)。如果不是,则可以中止请求(可能会返回HTTP 401错误)。

+0

感谢,我将会对OAuth的看看。我想我现在有了基本的想法:) – 2012-03-01 05:49:10

+0

POST和GET都是等价的不安全。为了保证其安全,你需要在顶部的另一个加密层,如SSL。 – 2014-01-06 18:49:48

您可以使用基于火线的php JWT(JSON Web令牌)进行基于令牌的验证。

1)运行作曲家命令作曲家安装PHP JWT需要火力/ PHP的智威汤逊

require_once('vendor/autoload.php'); 
    use \Firebase\JWT\JWT; 
    define('SECRET_KEY','Your-Secret-Key') // secret key can be a random string and keep in secret from anyone 
    define('ALGORITHM','HS512') 

之后生成的令牌

$tokenId = base64_encode(mcrypt_create_iv(32)); 
       $issuedAt = time(); 
       $notBefore = $issuedAt + 10; //Adding 10 seconds 
       $expire  = $notBefore + 7200; // Adding 60 seconds 
       $serverName = 'http://localhost/php-json/'; /// set your domain name 


       /* 
       * Create the token as an array 
       */ 
       $data = [ 
        'iat' => $issuedAt,   // Issued at: time when the token was generated 
        'jti' => $tokenId,   // Json Token Id: an unique identifier for the token 
        'iss' => $serverName,  // Issuer 
        'nbf' => $notBefore,  // Not before 
        'exp' => $expire,   // Expire 
        'data' => [     // Data related to the logged user you can set your required data 
       'id' => "set your current logged user-id", // id from the users table 
       'name' => "logged user name", // name 
           ] 
       ]; 
       $secretKey = base64_decode(SECRET_KEY); 
       /// Here we will transform this array into JWT: 
       $jwt = JWT::encode(
         $data, //Data to be encoded in the JWT 
         $secretKey, // The signing key 
         ALGORITHM 
         ); 
      $unencodedArray = ['jwt' => $jwt]; 

提供此令牌用户“$ jwt“。在每个请求上,用户需要为每个请求发送令牌值以验证用户。

try { 
      $secretKey = base64_decode(SECRET_KEY); 
      $DecodedDataArray = JWT::decode($_REQUEST['tokVal'], $secretKey, array(ALGORITHM)); 

      echo "{'status' : 'success' ,'data':".json_encode($DecodedDataArray)." }";die(); 

      } catch (Exception $e) { 
      echo "{'status' : 'fail' ,'msg':'Unauthorized'}";die(); 
      } 

You can get step by step full configurations for php token based authentication