Files
2026-06-29 13:00:18 +06:00

145 lines
4.9 KiB
PHP

<?php
namespace App\Services;
class Encryption
{
private $pubkey = '';
private $privkey = '';
//Block size for encryption block cipher
private $ENCRYPT_BLOCK_SIZE = 200;// this for 2048 bit key for example, leaving some room
//Block size for decryption block cipher
private $DECRYPT_BLOCK_SIZE = 256;// this again for 2048 bit key
public function __construct()
{
// $this->pubkey = file_get_contents(config('keys.public_key'));
// $this->privkey = file_get_contents(config('keys.private_key'));
}
public function encryptByPublicKey($plaintext)
{
$plaintext = gzcompress($plaintext);
// Get the public Key of the recipient
$publicKey = openssl_pkey_get_public('file://' . config('keys.public_key'));
$a_key = openssl_pkey_get_details($publicKey);
// Encrypt the data in small chunks and then combine and send it.
$chunkSize = ceil($a_key['bits'] / 8) - 11;
$output = '';
while ($plaintext) {
$chunk = substr($plaintext, 0, $chunkSize);
$plaintext = substr($plaintext, $chunkSize);
$encrypted = '';
if (!openssl_public_encrypt($chunk, $encrypted, $publicKey)) {
die('Failed to encrypt data');
}
$output .= $encrypted;
}
openssl_free_key($publicKey);
// This is the final encrypted data to be sent to the recipient
return bin2hex($output);
}
public function decryptByPrivateKey($encrypted)
{
if (!$privateKey = openssl_pkey_get_private('file://' . config('keys.private_key'))) {
die('Private Key failed');
}
$encrypted = hex2bin($encrypted);
$a_key = openssl_pkey_get_details($privateKey);
// Decrypt the data in the small chunks
$chunkSize = ceil($a_key['bits'] / 8);
$output = '';
while ($encrypted) {
$chunk = substr($encrypted, 0, $chunkSize);
$encrypted = substr($encrypted, $chunkSize);
$decrypted = '';
if (!openssl_private_decrypt($chunk, $decrypted, $privateKey)) {
die('Failed to decrypt data');
}
$output .= $decrypted;
}
openssl_free_key($privateKey);
// Uncompress the unencrypted data.
return gzuncompress($output);
}
public function decryptByPublicKey($data)
{
$decrypted = '';
//decode must be done before spliting for getting the binary String
$data = str_split(base64_decode($data), $this->DECRYPT_BLOCK_SIZE);
foreach ($data as $chunk) {
$partial = '';
//be sure to match padding
$decryptionOK = openssl_public_decrypt($chunk, $partial, $this->pubkey, OPENSSL_PKCS1_PADDING);
if ($decryptionOK === false) {
return false;
}//here also processed errors in decryption. If too big this will be false
$decrypted .= $partial;
}
return $decrypted;
}
public function encryptByPrivateKey($plainData)
{
$encrypted = '';
$plainData = str_split($plainData, $this->ENCRYPT_BLOCK_SIZE);
foreach ($plainData as $chunk) {
$partialEncrypted = '';
//using for example OPENSSL_PKCS1_PADDING as padding
$encryptionOk = openssl_private_encrypt($chunk, $partialEncrypted, $this->privkey, OPENSSL_PKCS1_PADDING);
if ($encryptionOk === false) {
return false;
}//also you can return and error. If too big this will be false
$encrypted .= $partialEncrypted;
}
return base64_encode($encrypted);//encoding the whole binary String as MIME base 64
}
public function generateKeys()
{
if(!is_dir(storage_path("app/public/keys"))){
mkdir(storage_path("app/public/keys"));
}
$config = array(
"config"=>storage_path("app/openssl.cnf"),
"private_key_bits" => 2048,
"private_key_type" => OPENSSL_KEYTYPE_RSA,
);
$privateKey = openssl_pkey_new($config);
// Save the private key to private.key file. Never share this file with anyone.
//openssl_pkey_export_to_file($privateKey, storage_path("app/public/keys/oauth-private1.key"));
// Get private key
openssl_pkey_export($privateKey, $privKey,NULL,$config);
file_put_contents(storage_path("app/public/keys/oauth-private.key"), $privKey);
// Generate the public key for the private key
$a_key = openssl_pkey_get_details($privateKey);
// Save the public key in public.key file. Send this file to anyone who want to send you the encrypted data.
file_put_contents(storage_path("app/public/keys/oauth-public.key"), $a_key['key']);
//uploadFile(config('keys.public_key'),'oauth-public.key', $a_key['key']);
// Free the private Key.
//dd(openssl_free_key($privateKey),$privateKey);
}
}