Как зашифровать данные в php с помощью открытых / закрытых ключей? - PullRequest
11 голосов
/ 07 января 2011

У меня есть небольшая строка данных (менее 1 КБ), которую я хотел бы, чтобы пользовательские агенты передавали на другие сайты, когда они отправляются с моего сайта. Чтобы другие сайты могли убедиться, что именно я создал строку, у меня есть два варианта.

  1. Сервер отправляет мне запрос на подтверждение (например, PayPal, OpenID и т. Д.)
  2. Я использую открытый / закрытый ключи, чтобы доказать, что отправил сообщение (например, PGP, DKIM и т. Д.)

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

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

Итак, как настроить криптографию с открытым / закрытым ключом с помощью PHP и есть ли недостатки?

Ответы [ 5 ]

16 голосов
/ 09 февраля 2016

Создание пары закрытых и открытых ключей с использованием функций PHP Openssl:

// Configuration settings for the key
$config = array(
    "digest_alg" => "sha512",
    "private_key_bits" => 4096,
    "private_key_type" => OPENSSL_KEYTYPE_RSA,
);

// Create the private and public key
$res = openssl_pkey_new($config);

// Extract the private key into $private_key
openssl_pkey_export($res, $private_key);

// Extract the public key into $public_key
$public_key = openssl_pkey_get_details($res);
$public_key = $public_key["key"];

Затем вы можете шифровать и дешифровать с использованием закрытых и открытых ключей, например:

// Something to encrypt
$text = 'This is the text to encrypt';

echo "This is the original text: $text\n\n";

// Encrypt using the public key
openssl_public_encrypt($text, $encrypted, $public_key);

$encrypted_hex = bin2hex($encrypted);
echo "This is the encrypted text: $encrypted_hex\n\n";

// Decrypt the data using the private key
openssl_private_decrypt($encrypted, $decrypted, $private_key);

echo "This is the decrypted text: $decrypted\n\n";
10 голосов
/ 14 января 2011

Я бы создал открытые / закрытые пары ключей S / MIME с использованием OpenSSL, а затем использовал команду OpenSSL для шифрования и дешифрования.Я считаю, что это лучше, чем использование PGP, потому что openssl включен в большинство операционных систем Linux, а PGP - нет.OpenSSL также основан на стандартах и, как правило, с ним легче работать, если у вас нет команд.

Я рекомендовал использовать «чистое PHP» решение (под чистым PHP я имею в виду делать шифрование на PHP, скореечем использование PHP для вызова существующей библиотеки или отдельного исполняемого файла).Вы не хотите делать массовое шифрование в PHP.Слишком медленно.И вы хотите использовать OpenSSL, потому что он высокопроизводителен и безопасность понятна.

Вот волшебство.

Чтобы создать ключ X.509:

$subj="/C=US/ST=California/L=Remote/O=Country Govt./OU=My Dept/CN=Mr. Agent/emailAddress=agent@investiations.com"
openssl req -x509 -newkey rsa:1024 -keyout mycert.key -out mycert.pem -nodes -subj $subj

Это помещает закрытый ключ в mycert.key и открытый ключ в mycert.pem.Закрытый ключ не защищен паролем.

Теперь, чтобы подписать сообщение с помощью S / MIME:

openssl smime -sign -signer mycert.pem -inkey mycert.key <input >output

Чтобы зашифровать сообщение с помощью S / MIME:

openssl smime -encrypt -recip yourcert.pem <input >output

Чтобы расшифровать сообщение с помощью S / MIME:

openssl smime -decrypt -inkey mycert.key -certfile mycert.pem <input >output

У меня также есть несколько демонстраций по использованию OpenSSL из привязок языка C, но не из PHP.

3 голосов
/ 09 декабря 2015

Правило 1: не реализуйте это самостоятельно, используйте библиотеку.

Какая библиотека? Вот мои рекомендуемые библиотеки криптографии с открытым ключом PHP :

  1. Halite , зависит от libsodium (но подчеркивает простоту и простоту использования в дополнение к безопасности).
  2. libsodium , от PECL
  3. EasyRSA , который реализует безопасное шифрование с открытым ключом и подписи с открытым ключом с использованием RSA в наиболее безопасных режимах (НЕ PKCS1v1.5, никогда!)
  4. phpseclib , от которого EasyRSA пользуется.

В общем, вам понадобится libsodium, если ваша цель - безопасность. Используете ли вы Halite или нет, это вопрос вкуса.

2 голосов
/ 07 января 2011

PGP - хороший вариант - он реализован правильно и полностью (т.е. у вас мало места для ошибок безопасности с PGP).Я думаю этот ТАК вопрос поможет вам взаимодействовать с GnuPG.Вопрос в том, будут ли и как другие сайты проверять вашу подпись.Вам необходимо либо соответствовать требованиям их механизма проверки, либо предоставить свой собственный модуль, который эти сайты будут использовать для проверки.

Также возможно, что вы можете использовать OAuth или OpenID для идентификации пользователей на других сайтах, но я не эксперт в этих технологиях.

1 голос
/ 20 октября 2013

Я написал пример шифрования и дешифрования с помощью openSSL на PHP и Python

http://glynrob.com/php/hashing-and-public-key-encryption/

Доступен исходный код Github.

Не забывайте, что закрытый ключ должен быть доступен в месте расшифровки, чтобы это работало.

...