vendor/payum/payum-bundle/DependencyInjection/MainConfiguration.php line 137

Open in your IDE?
  1. <?php
  2. namespace Payum\Bundle\PayumBundle\DependencyInjection;
  3. use Payum\Bundle\PayumBundle\DependencyInjection\Factory\Storage\StorageFactoryInterface;
  4. use Payum\Core\Exception\LogicException;
  5. use Symfony\Component\Config\Definition\ConfigurationInterface;
  6. use Symfony\Component\Config\Definition\Builder\TreeBuilder;
  7. use Symfony\Component\Config\Definition\Builder\ArrayNodeDefinition;
  8. use Payum\Core\Model\GatewayConfigInterface;
  9. use Payum\Core\Security\TokenInterface;
  10. class MainConfiguration implements ConfigurationInterface
  11. {
  12.     /**
  13.      * @var StorageFactoryInterface[]
  14.      */
  15.     protected array $storageFactories = array();
  16.     /**
  17.      * @param StorageFactoryInterface[] $storageFactories
  18.      */
  19.     public function __construct(array $storageFactories)
  20.     {
  21.         foreach ($storageFactories as $storageFactory) {
  22.             $this->storageFactories[$storageFactory->getName()] = $storageFactory;
  23.         }
  24.     }
  25.     /**
  26.      * {@inheritDoc}
  27.      */
  28.     public function getConfigTreeBuilder(): TreeBuilder
  29.     {
  30.         $tb = new TreeBuilder('payum');
  31.         $rootNode $tb->getRootNode();
  32.         $securityNode $rootNode->children()
  33.             ->arrayNode('security')->isRequired()
  34.         ;
  35.         $this->addSecuritySection($securityNode);
  36.         $dynamicGatewaysNode $rootNode->children()
  37.             ->arrayNode('dynamic_gateways')
  38.         ;
  39.         $this->addDynamicGatewaysSection($dynamicGatewaysNode);
  40.         $rootNode
  41.             ->children()
  42.             ->arrayNode('gateways')
  43.                 ->useAttributeAsKey('name')
  44.                 ->prototype('variable')
  45.                 ->treatNullLike([])
  46.         ;
  47.         
  48.         $this->addStoragesSection($rootNode);
  49.         return $tb;
  50.     }
  51.     protected function addStoragesSection(ArrayNodeDefinition $rootPrototypeNode): void
  52.     {
  53.         $storageNode $rootPrototypeNode->children()
  54.                 ->arrayNode('storages')
  55.                 ->validate()
  56.                     ->ifTrue(function($v) {
  57.                         $storages $v;
  58.                         unset($storages['extension']);
  59.                         foreach($storages as $key => $value) {
  60.                             if (false === class_exists($key)) {
  61.                                 throw new LogicException(sprintf(
  62.                                     'The storage entry must be a valid model class. It is set %s',
  63.                                     $key
  64.                                 ));
  65.                             }
  66.                         }
  67.                     
  68.                         return false;
  69.                     })
  70.                     ->thenInvalid('A message')
  71.                 ->end()
  72.                 ->useAttributeAsKey('key')
  73.                 ->prototype('array')
  74.         ;
  75.         $storageNode
  76.             ->validate()
  77.                 ->ifTrue(function($v) {
  78.                     $storages $v;
  79.                     unset($storages['extension']);
  80.                     if (count($storages) === 0) {
  81.                         throw new LogicException('At least one storage must be configured.');
  82.                     }
  83.                     if (count($storages) > 1) {
  84.                         throw new LogicException('Only one storage per entry could be selected');
  85.                     }
  86.                     
  87.                     return false;
  88.                 })
  89.                 ->thenInvalid('A message')
  90.             ->end()
  91.         ;
  92.         $storageNode->children()
  93.             ->arrayNode('extension')
  94.                 ->addDefaultsIfNotSet()
  95.                 ->children()
  96.                     ->booleanNode('all')->defaultValue(true)->end()
  97.                     ->arrayNode('gateways')
  98.                         ->useAttributeAsKey('key')
  99.                         ->prototype('scalar')
  100.                     ->end()->end()
  101.                     ->arrayNode('factories')
  102.                         ->useAttributeAsKey('key')
  103.                         ->prototype('scalar')
  104.                     ->end()->end()
  105.                 ->end()
  106.             ->end()
  107.         ->end();
  108.         
  109.         foreach ($this->storageFactories as $factory) {
  110.             $factory->addConfiguration(
  111.                 $storageNode->children()->arrayNode($factory->getName())
  112.             );
  113.         }
  114.     }
  115.     protected function addSecuritySection(ArrayNodeDefinition $securityNode): void
  116.     {
  117.         $storageNode $securityNode->children()
  118.             ->arrayNode('token_storage')
  119.             ->isRequired()
  120.             ->validate()
  121.             ->ifTrue(function($v) {
  122.                 foreach($v as $key => $value) {
  123.                     if (false === class_exists($key)) {
  124.                         throw new LogicException(sprintf(
  125.                             'The storage entry must be a valid model class. It is set %s',
  126.                             $key
  127.                         ));
  128.                     }
  129.                     $rc = new \ReflectionClass($key);
  130.                     if (false === $rc->implementsInterface(TokenInterface::class)) {
  131.                         throw new LogicException('The token class must implement `Payum\Core\Security\TokenInterface` interface');
  132.                     }
  133.                     if (count($v) > 1) {
  134.                         throw new LogicException('Only one token storage could be configured.');
  135.                     }
  136.                 }
  137.                 return false;
  138.             })
  139.             ->thenInvalid('A message')
  140.             ->end()
  141.             ->useAttributeAsKey('key')
  142.             ->prototype('array')
  143.         ;
  144.         $storageNode
  145.             ->validate()
  146.             ->ifTrue(function($v) {
  147.                 if (count($v) === 0) {
  148.                     throw new LogicException('At least one storage must be configured.');
  149.                 }
  150.                 if (count($v) > 1) {
  151.                     throw new LogicException('Only one storage per entry could be selected');
  152.                 }
  153.                 return false;
  154.             })
  155.             ->thenInvalid('A message')
  156.             ->end()
  157.         ;
  158.         foreach ($this->storageFactories as $factory) {
  159.             $factory->addConfiguration(
  160.                 $storageNode->children()->arrayNode($factory->getName())
  161.             );
  162.         }
  163.     }
  164.     protected function addDynamicGatewaysSection(ArrayNodeDefinition $dynamicGatewaysNode): void
  165.     {
  166.         $dynamicGatewaysNode->children()
  167.             ->booleanNode('sonata_admin')->defaultFalse()
  168.         ;
  169.         $storageNode $dynamicGatewaysNode->children()
  170.             ->arrayNode('config_storage')
  171.             ->isRequired()
  172.             ->validate()
  173.             ->ifTrue(function($v) {
  174.                 foreach($v as $key => $value) {
  175.                     if (false === class_exists($key)) {
  176.                         throw new LogicException(sprintf(
  177.                             'The storage entry must be a valid model class. It is set %s',
  178.                             $key
  179.                         ));
  180.                     }
  181.                     $rc = new \ReflectionClass($key);
  182.                     if (false === $rc->implementsInterface(GatewayConfigInterface::class)) {
  183.                         throw new LogicException('The config class must implement `Payum\Core\Model\GatewayConfigInterface` interface');
  184.                     }
  185.                     if (count($v) > 1) {
  186.                         throw new LogicException('Only one config storage could be configured.');
  187.                     }
  188.                 }
  189.                 return false;
  190.             })
  191.             ->thenInvalid('A message')
  192.             ->end()
  193.             ->useAttributeAsKey('key')
  194.             ->prototype('array')
  195.         ;
  196.         $storageNode
  197.             ->validate()
  198.             ->ifTrue(function($v) {
  199.                 if (count($v) === 0) {
  200.                     throw new LogicException('At least one storage must be configured.');
  201.                 }
  202.                 if (count($v) > 1) {
  203.                     throw new LogicException('Only one storage per entry could be selected');
  204.                 }
  205.                 return false;
  206.             })
  207.             ->thenInvalid('A message')
  208.             ->end()
  209.         ;
  210.         $dynamicGatewaysNode->children()
  211.             ->arrayNode('encryption')
  212.                 ->children()
  213.                     ->scalarNode('defuse_secret_key')->cannotBeEmpty()->end()
  214.         ;
  215.         foreach ($this->storageFactories as $factory) {
  216.             $factory->addConfiguration(
  217.                 $storageNode->children()->arrayNode($factory->getName())
  218.             );
  219.         }
  220.     }
  221. }