Skip to content

Commit

Permalink
Add new configuration-key to migrate to
Browse files Browse the repository at this point in the history
  • Loading branch information
Zombaya committed Nov 30, 2024
1 parent 1e1731f commit 93c6424
Show file tree
Hide file tree
Showing 17 changed files with 197 additions and 32 deletions.
4 changes: 3 additions & 1 deletion TODO-6.0.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
# Things we need to do before we can release 6.0
* [ ] Remove \Ambta\DoctrineEncryptBundle\DependencyInjection\DoctrineEncryptExtension::$wrapExceptions
* [ ] Remove wrap_exceptions from configuration of the bundle
* [ ] Remove wrap_exceptions from configuration of the bundle
* [ ] Remove DeprecatedDoctrineEncryptExtension
* [ ] Remove tests and demo using old `ambta_doctrine_encrypt` as configuration-key
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
ambta_doctrine_encrypt:
doctrine_encrypt_bundle:
enable_secret_generation: false
secret: '%env(HALITE_SECRET)%'
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
ambta_doctrine_encrypt:
doctrine_encrypt_bundle:
enable_secret_generation: false
secret: '%env(HALITE_SECRET)%'
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
ambta_doctrine_encrypt:
doctrine_encrypt_bundle:
enable_secret_generation: false
secret: '%env(HALITE_SECRET)%'
10 changes: 10 additions & 0 deletions src/AmbtaDoctrineEncryptBundle.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@

namespace Ambta\DoctrineEncryptBundle;

use Ambta\DoctrineEncryptBundle\DependencyInjection\DeprecatedDoctrineEncryptExtension;
use Ambta\DoctrineEncryptBundle\DependencyInjection\DoctrineEncryptExtension;
use JetBrains\PhpStorm\Pure;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\Extension\ExtensionInterface;
use Symfony\Component\HttpKernel\Bundle\Bundle;

Expand All @@ -14,4 +16,12 @@ public function getContainerExtension(): ?ExtensionInterface
{
return new DoctrineEncryptExtension();
}

public function build(ContainerBuilder $container)
{
parent::build($container);

// TODO-6.0 Remove the old extension again
$container->registerExtension(new DeprecatedDoctrineEncryptExtension());
}
}
14 changes: 12 additions & 2 deletions src/DependencyInjection/Configuration.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,15 +14,25 @@
*/
class Configuration implements ConfigurationInterface
{
/**
* @var string
*/
private $rootName;

public function __construct($rootName)
{
$this->rootName = $rootName;
}

public function getConfigTreeBuilder(): TreeBuilder
{
// Create tree builder
$treeBuilder = new TreeBuilder('ambta_doctrine_encrypt');
$treeBuilder = new TreeBuilder($this->rootName);
if (\method_exists($treeBuilder, 'getRootNode')) {
$rootNode = $treeBuilder->getRootNode();
} else {
// BC layer for symfony/config 4.1 and older
$rootNode = $treeBuilder->root('ambta_doctrine_encrypt');
$rootNode = $treeBuilder->root($this->rootName);
}

// Grammar of config tree
Expand Down
36 changes: 36 additions & 0 deletions src/DependencyInjection/DeprecatedDoctrineEncryptExtension.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
<?php

namespace Ambta\DoctrineEncryptBundle\DependencyInjection;

use Symfony\Component\DependencyInjection\ContainerBuilder;

/**
* Initialization of bundle.
*
* This is the class that loads and manages your bundle configuration
*
* To learn more see {@link http://symfony.com/doc/current/cookbook/bundles/extension.html}
*/
class DeprecatedDoctrineEncryptExtension extends DoctrineEncryptExtension
{
public function getAlias(): string
{
return 'ambta_doctrine_encrypt';
}

public function load(array $configs, ContainerBuilder $container): void
{
if (!empty($configs)) {
trigger_deprecation(
'doctrineencryptbundle/doctrine-encrypt-bundle',
'5.4.2',
<<<'EOF'
Using `ambta_doctrine_encrypt` as the configuration-key is deprecated and you should replace this with `doctrine_encrypt_bundle`.
Starting from 6.0, only `doctrine_encrypt_bundle` will be supported.
EOF
);

parent::load($configs, $container);
}
}
}
38 changes: 28 additions & 10 deletions src/DependencyInjection/DoctrineEncryptExtension.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@
use Ambta\DoctrineEncryptBundle\Encryptors\HaliteEncryptor;
use Symfony\Component\Config\FileLocator;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\Extension\Extension;
use Symfony\Component\DependencyInjection\Loader;
use Symfony\Component\HttpKernel\DependencyInjection\Extension;
use Symfony\Component\HttpKernel\Kernel;

/**
Expand All @@ -24,7 +24,19 @@ class DoctrineEncryptExtension extends Extension
*
* @internal
*/
public static $wrapExceptions = false;
private static $wrapExceptions = false;

/**
* @internal
*/
public static function wrapExceptions(?bool $wrapExceptions = null): bool
{
if ($wrapExceptions !== null) {
self::$wrapExceptions = $wrapExceptions;
}

return self::$wrapExceptions;
}

public const SupportedEncryptorClasses = [
'Defuse' => DefuseEncryptor::class,
Expand All @@ -33,9 +45,7 @@ class DoctrineEncryptExtension extends Extension

public function load(array $configs, ContainerBuilder $container): void
{
// Create configuration object
$configuration = new Configuration();
$config = $this->processConfiguration($configuration, $configs);
$config = $this->processConfiguration(new Configuration($this->getAlias()), $configs);

// If empty encryptor class, use Halite encryptor
if (array_key_exists($config['encryptor_class'], self::SupportedEncryptorClasses)) {
Expand All @@ -46,11 +56,15 @@ public function load(array $configs, ContainerBuilder $container): void

// Set parameters
$container->setParameter('ambta_doctrine_encrypt.encryptor_class_name', $config['encryptor_class_full']);
$container->setParameter('ambta_doctrine_encrypt.secret_directory_path', $config['secret_directory_path']);
$container->setParameter('ambta_doctrine_encrypt.enable_secret_generation', $config['enable_secret_generation']);

if (isset($config['secret'])) {
$container->setParameter('ambta_doctrine_encrypt.secret', $config['secret']);
} else {
$container->setParameter(
'ambta_doctrine_encrypt.enable_secret_generation',
$config['enable_secret_generation']
);
$container->setParameter('ambta_doctrine_encrypt.secret_directory_path', $config['secret_directory_path']);
}

// Load service file
Expand All @@ -77,7 +91,11 @@ public function load(array $configs, ContainerBuilder $container): void
// PHP 8.x (annotations and attributes)
} else {
// Doctrine 3.0 - no annotations
if (\Composer\InstalledVersions::satisfies(new \Composer\Semver\VersionParser(), 'doctrine/orm', '^3.0')) {
if (\Composer\InstalledVersions::satisfies(
new \Composer\Semver\VersionParser(),
'doctrine/orm',
'^3.0'
)) {
$loader->load('service_listeners_with_attributes.yml');
} else {
$loader->load('services_subscriber_with_annotations_and_attributes.yml');
Expand All @@ -90,7 +108,7 @@ public function load(array $configs, ContainerBuilder $container): void

// Wrap exceptions
if ($config['wrap_exceptions']) {
self::$wrapExceptions = true;
self::wrapExceptions(true);
} else {
trigger_deprecation(
'doctrineencryptbundle/doctrine-encrypt-bundle',
Expand All @@ -108,6 +126,6 @@ public function load(array $configs, ContainerBuilder $container): void
*/
public function getAlias(): string
{
return 'ambta_doctrine_encrypt';
return 'doctrine_encrypt_bundle';
}
}
4 changes: 2 additions & 2 deletions src/Encryptors/DefuseEncryptor.php
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ public function encrypt(string $data): string
try {
return \Defuse\Crypto\Crypto::encryptWithPassword($data, $this->secret);
} catch (\Throwable $e) {
if (DoctrineEncryptExtension::$wrapExceptions) {
if (DoctrineEncryptExtension::wrapExceptions()) {
throw new UnableToEncryptException($e->getMessage(), $e->getCode(), $e);
}
throw $e;
Expand All @@ -51,7 +51,7 @@ public function decrypt(string $data): string
try {
return \Defuse\Crypto\Crypto::decryptWithPassword($data, $this->secret);
} catch (\Throwable $e) {
if (DoctrineEncryptExtension::$wrapExceptions) {
if (DoctrineEncryptExtension::wrapExceptions()) {
throw new UnableToDecryptException($e->getMessage(), $e->getCode(), $e);
}
throw $e;
Expand Down
4 changes: 2 additions & 2 deletions src/Encryptors/HaliteEncryptor.php
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ public function encrypt(string $data): string
try {
return Crypto::encrypt(new HiddenString($data), $this->getKey());
} catch (\Throwable $e) {
if (DoctrineEncryptExtension::$wrapExceptions) {
if (DoctrineEncryptExtension::wrapExceptions()) {
throw new UnableToEncryptException($e->getMessage(), $e->getCode(), $e);
}
throw $e;
Expand All @@ -58,7 +58,7 @@ public function decrypt(string $data): string
try {
return Crypto::decrypt($data, $this->getKey())->getString();
} catch (\Throwable $e) {
if (DoctrineEncryptExtension::$wrapExceptions) {
if (DoctrineEncryptExtension::wrapExceptions()) {
throw new UnableToDecryptException($e->getMessage(), $e->getCode(), $e);
}
throw $e;
Expand Down
2 changes: 1 addition & 1 deletion src/Subscribers/DoctrineEncryptSubscriber.php
Original file line number Diff line number Diff line change
Expand Up @@ -310,7 +310,7 @@ public function processFields(object $entity, EntityManagerInterface $entityMana
} catch (DoctrineEncryptBundleException $e) {
throw $e;
} catch (\Throwable $e) {
if (DoctrineEncryptExtension::$wrapExceptions) {
if (DoctrineEncryptExtension::wrapExceptions()) {
throw new DoctrineEncryptBundleException('Something went wrong encrypting/decrypting a secret', 0, $e);
}
throw $e;
Expand Down
80 changes: 80 additions & 0 deletions tests/Unit/AmbtaDoctrineEncryptBundleTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
<?php

declare(strict_types=1);

namespace Ambta\DoctrineEncryptBundle\Tests\Unit;

use Ambta\DoctrineEncryptBundle\AmbtaDoctrineEncryptBundle;
use Ambta\DoctrineEncryptBundle\DependencyInjection\DoctrineEncryptExtension;
use PHPUnit\Framework\TestCase;
use Symfony\Bridge\PhpUnit\ExpectDeprecationTrait;
use Symfony\Component\Config\FileLocator;
use Symfony\Component\DependencyInjection\Compiler\MergeExtensionConfigurationPass;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\Loader\YamlFileLoader;
use Symfony\Component\DependencyInjection\ParameterBag\ParameterBag;

class AmbtaDoctrineEncryptBundleTest extends TestCase
{
use ExpectDeprecationTrait;

private function createContainer(): ContainerBuilder
{
return new ContainerBuilder(
new ParameterBag(['kernel.debug' => false])
);
}

protected function tearDown(): void
{
parent::tearDown();

DoctrineEncryptExtension::wrapExceptions(false);
}

/**
* @group legacy
*/
public function testContainerIsAbleToConfigFromOldNamespace(): void
{
$container = $this->createContainer();

$bundle = new AmbtaDoctrineEncryptBundle();

$container->registerExtension($bundle->getContainerExtension());
$bundle->build($container);

$yamlLoader = new YamlFileLoader($container, new FileLocator(__DIR__.'/../_data'));
$yamlLoader->load('ambta_doctrine_encrypt.yaml');

$container->addCompilerPass(new MergeExtensionConfigurationPass());

$this->expectDeprecation('Since doctrineencryptbundle/doctrine-encrypt-bundle 5.4.2: Using `ambta_doctrine_encrypt` as the configuration-key is deprecated and you should replace this with `doctrine_encrypt_bundle`.
Starting from 6.0, only `doctrine_encrypt_bundle` will be supported.');

$container->compile();

$this->assertTrue($container->hasParameter('ambta_doctrine_encrypt.secret'));
$this->assertEquals('ambta_doctrine_encrypt.yaml', $container->getParameter('ambta_doctrine_encrypt.secret'));
}

public function testContainerIsAbleToConfigFromNewNamespace(): void
{
$container = $this->createContainer();

$bundle = new AmbtaDoctrineEncryptBundle();

$container->registerExtension($bundle->getContainerExtension());
$bundle->build($container);

$yamlLoader = new YamlFileLoader($container, new FileLocator(__DIR__.'/../_data'));
$yamlLoader->load('doctrine_encrypt_bundle.yaml');

$container->addCompilerPass(new MergeExtensionConfigurationPass());

$container->compile();

$this->assertTrue($container->hasParameter('ambta_doctrine_encrypt.secret'));
$this->assertEquals('doctrine_encrypt_bundle.yaml', $container->getParameter('ambta_doctrine_encrypt.secret'));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -214,7 +214,7 @@ public function testWrapExceptionsTriggersDeprecationWarningWhenNotDefiningTheOp
$this->expectDeprecation('Since doctrineencryptbundle/doctrine-encrypt-bundle 5.4.2: Starting from 6.0, all exceptions thrown by this library will be wrapped by \Ambta\DoctrineEncryptBundle\Exception\DoctrineEncryptBundleException or a child-class of it.
You can start using these exceptions today by setting \'ambta_doctrine_encrypt.wrap_exceptions\' to TRUE.');
$this->extension->load([$config], $container);
$this->assertFalse(DoctrineEncryptExtension::$wrapExceptions);
$this->assertFalse(DoctrineEncryptExtension::wrapExceptions());
}

/**
Expand All @@ -228,7 +228,7 @@ public function testWrapExceptionsTriggersDeprecationWarningWhenDisabled(): void
$this->expectDeprecation('Since doctrineencryptbundle/doctrine-encrypt-bundle 5.4.2: Starting from 6.0, all exceptions thrown by this library will be wrapped by \Ambta\DoctrineEncryptBundle\Exception\DoctrineEncryptBundleException or a child-class of it.
You can start using these exceptions today by setting \'ambta_doctrine_encrypt.wrap_exceptions\' to TRUE.');
$this->extension->load([$config], $container);
$this->assertFalse(DoctrineEncryptExtension::$wrapExceptions);
$this->assertFalse(DoctrineEncryptExtension::wrapExceptions());
}

/**
Expand All @@ -240,7 +240,7 @@ public function testWrapExceptionsDoesNotTriggerDeprecationWarningWhenEnabled():
$config = ['wrap_exceptions' => true];

$this->extension->load([$config], $container);
$this->assertTrue(DoctrineEncryptExtension::$wrapExceptions);
$this->assertTrue(DoctrineEncryptExtension::wrapExceptions());
}

private function createContainer(): ContainerBuilder
Expand Down
9 changes: 5 additions & 4 deletions tests/Unit/Encryptors/DefuseEncryptorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -10,17 +10,18 @@
class DefuseEncryptorTest extends TestCase
{
private const DATA = 'foobar';

/** @var bool */
private $originalWrapExceptions;

protected function setUp(): void
{
$this->originalWrapExceptions = DoctrineEncryptExtension::$wrapExceptions;
$this->originalWrapExceptions = DoctrineEncryptExtension::wrapExceptions();
}

protected function tearDown(): void
{
DoctrineEncryptExtension::$wrapExceptions = $this->originalWrapExceptions;
DoctrineEncryptExtension::wrapExceptions($this->originalWrapExceptions);
}

public function testEncrypt(): void
Expand All @@ -40,7 +41,7 @@ public function testEncrypt(): void

public function testEncryptorThrowsOwnExceptionWhenExceptionsAreNotWrapped(): void
{
DoctrineEncryptExtension::$wrapExceptions = false;
DoctrineEncryptExtension::wrapExceptions(false);

try {
(new DefuseEncryptor('not-a-valid-key'))->decrypt('foo');
Expand All @@ -54,7 +55,7 @@ public function testEncryptorThrowsOwnExceptionWhenExceptionsAreNotWrapped(): vo

public function testEncryptorThrowsBundleExceptionWhenExceptionsAreWrapped(): void
{
DoctrineEncryptExtension::$wrapExceptions = true;
DoctrineEncryptExtension::wrapExceptions(true);

try {
(new DefuseEncryptor('not-a-valid-key'))->decrypt('foo');
Expand Down
Loading

0 comments on commit 93c6424

Please sign in to comment.