Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/239.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/azure/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 从Azure Active Directory验证JWT_Php_Azure_Openssl_Cryptography_Jwt - Fatal编程技术网

Php 从Azure Active Directory验证JWT

Php 从Azure Active Directory验证JWT,php,azure,openssl,cryptography,jwt,Php,Azure,Openssl,Cryptography,Jwt,我按照这里的说明获取web API的访问令牌 我有这项工作,但当涉及到如何在PHP中验证令牌时,文档是模糊的 您可以使用响应中返回的访问令牌对受保护的资源(如web API)进行身份验证。通常,令牌在HTTP请求中使用承载方案呈现给web API,如RFC 6750中所述。本规范解释了如何在HTTP请求中使用承载令牌来访问受保护的资源 当web API接收并验证令牌时,它会让本机客户端应用程序访问web API 如何在应用程序中验证JWT?我有一个PHP框架,它使用PHP openssl_ve

我按照这里的说明获取web API的访问令牌

我有这项工作,但当涉及到如何在PHP中验证令牌时,文档是模糊的

您可以使用响应中返回的访问令牌对受保护的资源(如web API)进行身份验证。通常,令牌在HTTP请求中使用承载方案呈现给web API,如RFC 6750中所述。本规范解释了如何在HTTP请求中使用承载令牌来访问受保护的资源

当web API接收并验证令牌时,它会让本机客户端应用程序访问web API

如何在应用程序中验证JWT?我有一个PHP框架,它使用PHP openssl_verify()函数和令牌、符号、密钥和算法,但当我将Azure的私钥与SHA256算法一起使用时,收到错误消息:

openssl_verify(): supplied key param cannot be coerced into a public key
这让我相信我在PHP中用来验证的密钥是不正确的。目前,我正在使用为Active Directory应用程序生成的私钥,它恰好也是我在点击oauth2/令牌url时为“client_secret”参数使用的相同值(任何其他值都不会导致生成令牌,因此这可能是正确的)

该键类似于(但实际上不是):

我认为openssl需要有一个证书。。。如果是这样,我似乎无法在Azure门户中找到此证书的位置

我错过了什么?我应该在openssl_verify()中使用什么密钥来验证JWT?我在Azure中的何处可以找到它

谢谢

--

更新:

我在这里找到了公钥:

但是,我仍然无法使用提供的X5C来验证签名。如何在PHP中实现这一点

--

更新2:

我使用一个转换后的文件为公钥创建了一个.pem文件,该文件使用了“e”和“n”参数。这收到了一个公钥

现在,在使用它进行解密时,我会遇到OPEN SSL错误:

error:0906D06C:PEM routines:PEM_read_bio:no start line

结束这个问题,我从最初的问题开始。更新了我的问题,并添加了说明我进展情况的评论

为新的特定问题创建了新问题:

--

以防万一对其他人有帮助:

有关使用PHP从Microsoft获取公钥的解决方案的更多信息,我执行了以下操作:

$string_microsoftPublicKeyURL = 'https://login.windows.net/common/discovery/keys';

$array_publicKeysWithKIDasArrayKey = loadKeysFromAzure($string_microsoftPublicKeyURL);


function loadKeysFromAzure($string_microsoftPublicKeyURL) {
    $array_keys = array();

    $jsonString_microsoftPublicKeys = file_get_contents($string_microsoftPublicKeyURL);
    $array_microsoftPublicKeys = json_decode($jsonString_microsoftPublicKeys, true);

    foreach($array_microsoftPublicKeys['keys'] as $array_publicKey) {
        $string_certText = "-----BEGIN CERTIFICATE-----\r\n".chunk_split($array_publicKey['x5c'][0],64)."-----END CERTIFICATE-----\r\n";
        $array_keys[$array_publicKey['kid']] = getPublicKeyFromX5C($string_certText);
    }

    return $array_keys;
}


function getPublicKeyFromX5C($string_certText) {
    $object_cert = openssl_x509_read($string_certText);
    $object_pubkey = openssl_pkey_get_public($object_cert);
    $array_publicKey = openssl_pkey_get_details($object_pubkey);
    return $array_publicKey['key'];
}
不过,最好将它们缓存到磁盘,这样您就不会每次都加载它们,但这只是一个简单的示例

然后,使用公钥数组,检查JWT头中的'kid'值,找到要验证的正确公共证书,并在openssl_verify()的参数3中使用它。我使用JWT类来处理这个问题

使用上面创建的公钥数组和JWT类应该允许您验证microsoft JWTs

从firebase链接到JWT类:

使用JWT的参数1、此公钥数组的参数2和仅为“RS256”的数组的参数3调用JWT::Decode

JWT::decode($string_JSONWebToken, $array_publicKeysWithKIDasArrayKey, array('RS256'));

如果JWT无效或返回解密的JWT供您使用(并检查声明),这将引发异常。

如果要验证JWT,请转到JWT.io
这将允许您粘贴JWT,然后它将验证标题、声明,如果您添加公钥或私钥(取决于服务器验证签名的方式),它还将验证JWT的签名。

看起来您已经在解决了问题,如果您可以在此处总结解决方案的要点,则会更好,然后,其他有类似问题的社区将从该线程中受益。
JWT::decode($string_JSONWebToken, $array_publicKeysWithKIDasArrayKey, array('RS256'));