Использование только php для расшифровки гибрида Zend-Crypt

Я разрабатываю API, который для возврата конфиденциальных данных потребует своего рода рукопожатия, которое вернет клиенту открытый ключ для шифрования информации перед отправкой в ​​API.

Для API я использую выразительный Zend и для выполнения рукопожатия, я использую модуль Zend-Crypt, более конкретно гибридное шифрование.

рабочий процесс более или менее следующий:

Клиентское приложение отправляет открытый ключ в API. API использует этот открытый ключ для шифрования с использованием гибридного шифрования открытого ключа, предоставленного сервером. Открытый ключ зашифрованного сервера возвращается клиенту. Клиент должен расшифровать ключ, чтобы иметь возможность использовать его для криптографии конфиденциальных данных.

Ниже приведен исходный код, который выполняет криптографию с открытым ключом:

$publicKeyStr = $request->getHeader('hello');

try {
    $publicKey = new \Zend\Crypt\PublicKey\Rsa\PublicKey(base64_decode($publicKeyStr[0]));

    $b64Key = base64_encode($this->crypto->getPublicKey());

    $hybridCrypt = new \Zend\Crypt\Hybrid();

    $serverPk = $hybridCrypt->encrypt($b64Key, $publicKey);   

    return new \Zend\Diactoros\Response\JsonResponse(array('hello'=>$serverPk));
} catch (\Zend\Crypt\PublicKey\Rsa\Exception\RuntimeException $ex) {
    return new \Zend\Diactoros\Response\EmptyResponse(\Fig\Http\Message\StatusCodeInterface::STATUS_UNAUTHORIZED);
}

У меня такой вопрос: как мне расшифровать этот открытый ключ на клиенте, который не использует фреймворк, например, только на чистом PHP?

Поскольку этот API можно использовать для разработки мобильных приложений или настольных программ, мне необходимо понять логику расшифровки, чтобы можно было выполнять тесты на разных платформах.

В настоящее время я выполняю интеграционное тестирование этого промежуточного программного обеспечения с использованием Codeception, и тестовый код выглядит так:

public function testPublicKeyAccess(ApiTester $I)
{
    $I->wantTo('Test if API return a valid public key');

    $I->am('Client');
    $I->amBearerAuthenticated($this->token);
    $I->haveHttpHeader('hello', base64_encode($this->publicKey));
    $I->sendGET('/handshake');


    $I->seeResponseCodeIs(200);
    $I->seeResponseContainsJson();

    $response = json_decode($I->grabResponse());

    list($encryptedKeys, $msg) = explode(';', $response->hello);
    $keysArr = explode(':', $encryptedKeys);
    $encryptedKey = base64_decode($keysArr[1]);

    // Decrypt $envKey, this works

    $envKey = '';
    openssl_private_decrypt($encryptedKey, $envKey,  $this->privateKey, OPENSSL_PKCS1_OAEP_PADDING);

    // Decrypt public key, this don't works
    $cipher = 'aes-256-cbc';
    $hmacSize = 46;
    $hmac = mb_substr($msg, 0, $hmacSize, '8bit');

    $ivSize = 32; //openssl_cipher_iv_length($cipher);
    $iv = mb_substr($msg, $hmacSize, $ivSize, '8bit'); // 64

    $cipherText = base64_decode(mb_substr($msg, $hmacSize+$ivSize, null, '8bit'));

    $serverKey = '';

    codecept_debug(var_dump($ivSize));

    openssl_open($cipherText, $serverKey, $envKey, $this->privateKey, $cipher, $ivSize);
    codecept_debug(var_dump($cipherText));
    codecept_debug(var_dump($serverKey));

    $I->assertRegExp('/-----BEGIN PUBLIC KEY-----(.*)-----END PUBLIC KEY-----/s', $serverKey);
}

0 ответов

Другие вопросы по тегам