Skip to content

Commit 4cc5d7f

Browse files
authored
Merge pull request #23 from MayMeow/dev/fix-22
Update RSA for compatibility with javascript
2 parents bee3cbc + 1deb049 commit 4cc5d7f

File tree

4 files changed

+56
-29
lines changed

4 files changed

+56
-29
lines changed

src/Exceptions/DecryptException.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66

77
class DecryptException extends \Exception
88
{
9-
public function __construct(string $message = "Cannot decrypt text", int $code = 0, Throwable $previous = null)
9+
public function __construct(string $message = "Cannot decrypt text", int $code = 0, ?Throwable $previous = null)
1010
{
1111
parent::__construct($message, $code, $previous);
1212
}

src/RSAParameters.php

Lines changed: 52 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@ class RSAParameters
88
{
99
private string $privateKey;
1010
private string $publicKey;
11-
private string $passphrase;
11+
private ?string $passphrase = 'test_passphrase';
1212

1313
protected array $config = [
14-
'digest_alg' => 'sha512',
14+
'digest_alg' => 'sha256',
1515
'private_key_bits' => 4096,
1616
'private_key_type' => OPENSSL_KEYTYPE_RSA,
1717
];
@@ -31,15 +31,9 @@ public function generateKeys(?string $passphrase = null, ?array $configArgs = nu
3131
{
3232
$keys = openssl_pkey_new($this->config);
3333

34-
if ($passphrase != null) {
35-
$this->passphrase = $passphrase;
36-
} else {
37-
$this->passphrase = (string)rand(100000, 999999);
38-
}
39-
4034
if ($keys) {
41-
openssl_pkey_export($keys, $private, $passphrase, $configArgs);
42-
$this->privateKey = $private;
35+
openssl_pkey_export($keys, $private);
36+
$this->privateKey = $this->encryptPrivateKey(privateKey: $private);
4337

4438
$pub = openssl_pkey_get_details($keys);
4539

@@ -51,22 +45,40 @@ public function generateKeys(?string $passphrase = null, ?array $configArgs = nu
5145
return $this;
5246
}
5347

48+
private function encryptPrivateKey(string $privateKey, string $salt = 'salt'): string
49+
{
50+
$aes = new AESCryptoServiceProvider();
51+
$aes->generateIV();
52+
$k = new CryptoKey();
53+
$key = $k->getCryptographicKey($this->passphrase, $salt);
54+
$aes->setKey($key);
55+
56+
return $aes->encrypt($privateKey);
57+
}
58+
59+
private function decryptPrivateKey(string $privateKey, string $salt = 'salt'): string
60+
{
61+
$aes = new AESCryptoServiceProvider();
62+
$k = new CryptoKey();
63+
$key = $k->getCryptographicKey($this->passphrase, $salt);
64+
$aes->setKey($key);
65+
66+
return $aes->decrypt($privateKey);
67+
}
68+
5469
/**
5570
* Returns Decrypted Key
5671
*
5772
* @return string|\OpenSSLAsymmetricKey
5873
* @throws DecryptPrivateKeyException
5974
*/
60-
public function getPrivateKey(): \OpenSSLAsymmetricKey|string
75+
public function getPrivateKey(string $salt = 'salt', bool $encrypted = false): \OpenSSLAsymmetricKey|string
6176
{
62-
if ($this->passphrase != null && $this->privateKey != null) {
63-
$privateKeyResource = openssl_pkey_get_private($this->privateKey, $this->passphrase);
64-
65-
if ($privateKeyResource == false) {
66-
throw new DecryptPrivateKeyException();
67-
}
68-
69-
return $privateKeyResource;
77+
if (!$encrypted) {
78+
return $this->decryptPrivateKey(
79+
privateKey: $this->privateKey,
80+
salt: $salt
81+
);
7082
}
7183

7284
return $this->privateKey;
@@ -78,7 +90,7 @@ public function getPrivateKey(): \OpenSSLAsymmetricKey|string
7890
* @param string $privateKey
7991
* @param string $passphrase
8092
*/
81-
public function setPrivateKey(string $privateKey, string $passphrase): void
93+
public function setPrivateKey(string $privateKey, string $passphrase, string $salt = 'salt'): void
8294
{
8395
$this->passphrase = $passphrase;
8496
$this->privateKey = $privateKey;
@@ -109,7 +121,7 @@ public function setPublicKey(string $publicKey): void
109121
*
110122
* @return string
111123
*/
112-
public function getPassphrase(): string
124+
public function getPassphrase(): ?string
113125
{
114126
return $this->passphrase;
115127
}
@@ -142,4 +154,23 @@ public function setConfig(array $config): void
142154
{
143155
$this->config = $config;
144156
}
157+
158+
/**
159+
* Returns the fingerprint of the public key.
160+
*
161+
* @param bool $md5 Whether to return the MD5 fingerprint instead of SHA-256.
162+
* @return string The fingerprint of the public key.
163+
*/
164+
public function getFingerprint(bool $md5 = false): string
165+
{
166+
$derData = preg_replace('/-----.*?-----/', '', base64_decode($this->publicKey));
167+
$derData = preg_replace('/\s+/', '', $derData);
168+
$derData = base64_decode($derData);
169+
170+
if ($md5) {
171+
return implode(':', str_split(hash('md5', $derData), 2));
172+
}
173+
174+
return hash('sha256', $derData);
175+
}
145176
}

src/Tools/RsaParametersWriter.php

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -31,12 +31,7 @@ public function __construct(RSAParametersLocatorInterface $locator)
3131
public function write(RSAParameters $RSAParameters): void
3232
{
3333
file_put_contents($this->locator->locatePublicKey(), $RSAParameters->getPublicKey());
34+
file_put_contents($this->locator->locatePrivateKey(), $RSAParameters->getPrivateKey(encrypted: true));
3435
file_put_contents($this->locator->locatePassphrase(), $RSAParameters->getPassphrase());
35-
36-
openssl_pkey_export_to_file(
37-
$RSAParameters->getPrivateKey(),
38-
$this->locator->locatePrivateKey(),
39-
$RSAParameters->getPassphrase()
40-
);
4136
}
4237
}

tests/RSAParametersTest.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,11 +47,12 @@ public function canExportKeysAndImportToFile() : void
4747
$reader = new RsaParametersReader($locator);
4848
$parameters2 = $reader->read();
4949

50+
5051
// create new instance of RSA CSP with imported parameters
5152
$csp2 = new RSACryptoServiceProvider();
5253
$csp2->setParameters($parameters2);
5354

5455
// Check if imported parameters are same as parameters that was exported
5556
$this->assertEquals($text, $csp2->decrypt($encryptedText));
5657
}
57-
}
58+
}

0 commit comments

Comments
 (0)