SodiumChachaPatchTest.php 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101
  1. <?php
  2. /**
  3. * Copyright © Magento, Inc. All rights reserved.
  4. * See COPYING.txt for license details.
  5. */
  6. declare(strict_types=1);
  7. namespace Magento\EncryptionKey\Setup\Patch\Data;
  8. use Magento\Framework\ObjectManagerInterface;
  9. use Magento\Framework\App\DeploymentConfig;
  10. use Magento\Framework\Encryption\Encryptor;
  11. class SodiumChachaPatchTest extends \PHPUnit\Framework\TestCase
  12. {
  13. const PATH_KEY = 'crypt/key';
  14. /**
  15. * @var ObjectManagerInterface
  16. */
  17. private $objectManager;
  18. /**
  19. * @var DeploymentConfig
  20. */
  21. private $deployConfig;
  22. protected function setUp()
  23. {
  24. $this->objectManager = \Magento\TestFramework\Helper\Bootstrap::getObjectManager();
  25. $this->deployConfig = $this->objectManager->get(DeploymentConfig::class);
  26. }
  27. public function testChangeEncryptionKey()
  28. {
  29. $testPath = 'test/config';
  30. $testValue = 'test';
  31. $structureMock = $this->createMock(\Magento\Config\Model\Config\Structure\Proxy::class);
  32. $structureMock->expects($this->once())
  33. ->method('getFieldPathsByAttribute')
  34. ->will($this->returnValue([$testPath]));
  35. $structureMock->expects($this->once())
  36. ->method('getFieldPaths')
  37. ->willReturn([]);
  38. /** @var \Magento\Config\Model\ResourceModel\Config $configModel */
  39. $configModel = $this->objectManager->create(\Magento\Config\Model\ResourceModel\Config::class);
  40. $configModel->saveConfig($testPath, $this->legacyEncrypt($testValue), 'default', 0);
  41. /** @var \Magento\EncryptionKey\Setup\Patch\Data\SodiumChachaPatch $patch */
  42. $patch = $this->objectManager->create(
  43. \Magento\EncryptionKey\Setup\Patch\Data\SodiumChachaPatch::class,
  44. [
  45. 'structure' => $structureMock,
  46. ]
  47. );
  48. $patch->apply();
  49. $connection = $configModel->getConnection();
  50. $values = $connection->fetchPairs(
  51. $connection->select()->from(
  52. $configModel->getMainTable(),
  53. ['config_id', 'value']
  54. )->where(
  55. 'path IN (?)',
  56. [$testPath]
  57. )->where(
  58. 'value NOT LIKE ?',
  59. ''
  60. )
  61. );
  62. /** @var \Magento\Framework\Encryption\EncryptorInterface $encyptor */
  63. $encyptor = $this->objectManager->get(\Magento\Framework\Encryption\EncryptorInterface::class);
  64. $rawConfigValue = array_pop($values);
  65. $this->assertNotEquals($testValue, $rawConfigValue);
  66. $this->assertStringStartsWith('0:' . Encryptor::CIPHER_LATEST . ':', $rawConfigValue);
  67. $this->assertEquals($testValue, $encyptor->decrypt($rawConfigValue));
  68. }
  69. private function legacyEncrypt(string $data): string
  70. {
  71. // @codingStandardsIgnoreStart
  72. $handle = @mcrypt_module_open(MCRYPT_RIJNDAEL_256, '', MCRYPT_MODE_CBC, '');
  73. $initVectorSize = @mcrypt_enc_get_iv_size($handle);
  74. $initVector = str_repeat("\0", $initVectorSize);
  75. @mcrypt_generic_init($handle, $this->deployConfig->get(static::PATH_KEY), $initVector);
  76. $encrpted = @mcrypt_generic($handle, $data);
  77. @mcrypt_generic_deinit($handle);
  78. @mcrypt_module_close($handle);
  79. // @codingStandardsIgnoreEnd
  80. return '0:' . Encryptor::CIPHER_RIJNDAEL_256 . ':' . base64_encode($encrpted);
  81. }
  82. }