vendor/symfony-cmf/seo-bundle/src/DependencyInjection/Configuration.php line 35

Open in your IDE?
  1. <?php
  2. /*
  3.  * This file is part of the Symfony CMF package.
  4.  *
  5.  * (c) 2011-2017 Symfony CMF
  6.  *
  7.  * For the full copyright and license information, please view the LICENSE
  8.  * file that was distributed with this source code.
  9.  */
  10. namespace Symfony\Cmf\Bundle\SeoBundle\DependencyInjection;
  11. use Symfony\Cmf\Bundle\RoutingBundle\Routing\DynamicRouter;
  12. use Symfony\Cmf\Bundle\SeoBundle\SeoPresentation;
  13. use Symfony\Component\Config\Definition\Builder\ArrayNodeDefinition;
  14. use Symfony\Component\Config\Definition\Builder\NodeBuilder;
  15. use Symfony\Component\Config\Definition\Builder\TreeBuilder;
  16. use Symfony\Component\Config\Definition\ConfigurationInterface;
  17. /**
  18.  * Validates and merges the configuration for the seo bundle.
  19.  *
  20.  * @author Maximilian Berghoff <Maximilian.Berghoff@gmx.de>
  21.  */
  22. class Configuration implements ConfigurationInterface
  23. {
  24.     /**
  25.      * {@inheritdoc}
  26.      */
  27.     public function getConfigTreeBuilder()
  28.     {
  29.         $treeBuilder = new TreeBuilder();
  30.         $nodeBuilder $treeBuilder->root('cmf_seo')
  31.             ->addDefaultsIfNotSet()
  32.             ->beforeNormalization()
  33.                 ->ifTrue(function ($config) {
  34.                     return isset($config['sitemap'])
  35.                         && (!isset($config['sitemap']['configurations'])
  36.                             || === count($config['sitemap']['configurations'])
  37.                         )
  38.                         && !isset($config['sitemap']['configuration']) // xml configuration
  39.                     ;
  40.                 })
  41.                 ->then(function ($config) {
  42.                     if (true === $config['sitemap']) {
  43.                         $config['sitemap'] = [
  44.                             'enabled' => true,
  45.                             'configurations' => [
  46.                                 'sitemap' => [],
  47.                             ],
  48.                         ];
  49.                     } elseif (is_array($config['sitemap'])) {
  50.                         $config['sitemap']['configurations'] = ['sitemap' => []];
  51.                     }
  52.                     return $config;
  53.                 })
  54.             ->end()
  55.             ->beforeNormalization()
  56.                 ->ifTrue(function ($config) {
  57.                     return isset($config['content_key']) && !isset($config['content_listener']['content_key']);
  58.                 })
  59.                 ->then(function ($config) {
  60.                     $config['content_listener']['content_key'] = $config['content_key'];
  61.                     unset($config['content_key']);
  62.                     return $config;
  63.                 })
  64.             ->end()
  65.             // validation needs to be on top, when no values are set a validation inside the content_listener array node will not be triggered
  66.             ->validate()
  67.                 ->ifTrue(function ($v) {
  68.                     return $v['content_listener']['enabled'] && empty($v['content_listener']['content_key']);
  69.                 })
  70.                 ->thenInvalid('Configure the content_listener.content_key or disable the content_listener when not using the CmfRoutingBundle DynamicRouter.')
  71.             ->end()
  72.             ->children()
  73.                 ->scalarNode('translation_domain')->defaultValue('messages')->end()
  74.                 ->scalarNode('title')->end()
  75.                 ->scalarNode('description')->end()
  76.                 ->scalarNode('original_route_pattern')->defaultValue(SeoPresentation::ORIGINAL_URL_CANONICAL)->end()
  77.         ;
  78.         $this->addPersistenceSection($nodeBuilder);
  79.         $this->addAlternateLocaleSection($nodeBuilder);
  80.         $this->addErrorHandlerSection($nodeBuilder);
  81.         $this->addSitemapSection($nodeBuilder);
  82.         $this->addContentListenerSection($nodeBuilder);
  83.         $this->addFormSection($nodeBuilder);
  84.         $nodeBuilder->end();
  85.         return $treeBuilder;
  86.     }
  87.     /**
  88.      * Attach the persistence node to the tree.
  89.      *
  90.      * @param NodeBuilder $treeBuilder
  91.      */
  92.     private function addPersistenceSection(NodeBuilder $treeBuilder)
  93.     {
  94.         $treeBuilder
  95.             ->arrayNode('persistence')
  96.                 ->addDefaultsIfNotSet()
  97.                 ->children()
  98.                     ->arrayNode('phpcr')
  99.                         ->addDefaultsIfNotSet()
  100.                         ->canBeEnabled()
  101.                         ->children()
  102.                             ->scalarNode('manager_name')->defaultNull()->end()
  103.                             ->scalarNode('content_basepath')->defaultValue('/cms/content')->end()
  104.                         ->end()
  105.                     ->end()
  106.                     ->arrayNode('orm')
  107.                         ->addDefaultsIfNotSet()
  108.                         ->canBeEnabled()
  109.                         ->children()
  110.                             ->scalarNode('manager_name')->defaultNull()->end()
  111.                         ->end()
  112.                     ->end()
  113.                 ->end()
  114.             ->end()
  115.         ;
  116.     }
  117.     /**
  118.      * Attach the alternate locale node to the tree.
  119.      *
  120.      * @param NodeBuilder $nodeBuilder
  121.      */
  122.     private function addAlternateLocaleSection(NodeBuilder $nodeBuilder)
  123.     {
  124.         $nodeBuilder
  125.             ->arrayNode('alternate_locale')
  126.                 ->addDefaultsIfNotSet()
  127.                 ->canBeEnabled()
  128.                 ->children()
  129.                     ->scalarNode('provider_id')->defaultNull()->end()
  130.                 ->end()
  131.             ->end()
  132.         ;
  133.     }
  134.     /**
  135.      * Attach the error node to the tree.
  136.      *
  137.      * @param NodeBuilder $nodeBuilder
  138.      */
  139.     private function addErrorHandlerSection(NodeBuilder $nodeBuilder)
  140.     {
  141.         $nodeBuilder
  142.             ->arrayNode('error')
  143.                 ->fixXmlConfig('template')
  144.                 ->fixXmlConfig('exclusion_rule')
  145.                 ->children()
  146.                     ->booleanNode('enable_parent_provider')->defaultFalse()->end()
  147.                     ->booleanNode('enable_sibling_provider')->defaultFalse()->end()
  148.                     ->arrayNode('templates')
  149.                         ->useAttributeAsKey('format')
  150.                         ->requiresAtLeastOneElement()
  151.                         ->defaultValue(['html' => 'CmfSeoBundle:Exception:error.html.twig'])
  152.                         ->prototype('scalar')->end()
  153.                     ->end()
  154.                     ->arrayNode('exclusion_rules')
  155.                         ->info('Rules to exclude error handling from specific matches.')
  156.                         ->prototype('array')
  157.                             ->children()
  158.                                 ->scalarNode('path')->defaultNull()->info('Path to exclude')->end()
  159.                                 ->scalarNode('host')->defaultNull()->info('Host to exclude')->end()
  160.                                 ->scalarNode('methods')->defaultNull()->info('Methods to exclude')->end()
  161.                                 ->scalarNode('ips')->defaultNull()->info('Ips to exclude')->end()
  162.                                 ->end()
  163.                             ->end()
  164.                         ->end()
  165.                     ->end()
  166.                 ->end()
  167.             ->end()
  168.         ;
  169.     }
  170.     /**
  171.      * Attach the sitemap node to the tree.
  172.      *
  173.      * @param NodeBuilder $nodeBuilder
  174.      */
  175.     private function addSitemapSection(NodeBuilder $nodeBuilder)
  176.     {
  177.         $nodeBuilder
  178.             ->arrayNode('sitemap')
  179.                 ->fixXmlConfig('configuration')
  180.                 ->addDefaultsIfNotSet()
  181.                 ->canBeEnabled()
  182.                 ->children()
  183.                     ->arrayNode('defaults')
  184.                         ->fixXmlConfig('template')
  185.                         ->addDefaultsIfNotSet()
  186.                         ->children()
  187.                             ->scalarNode('default_change_frequency')->defaultValue('always')->end()
  188.                             ->arrayNode('templates')
  189.                                 ->useAttributeAsKey('format')
  190.                                 ->requiresAtLeastOneElement()
  191.                                 ->defaultValue([
  192.                                     'html' => 'CmfSeoBundle:Sitemap:index.html.twig',
  193.                                     'xml' => 'CmfSeoBundle:Sitemap:index.xml.twig',
  194.                                 ])
  195.                                 ->prototype('scalar')->end()
  196.                             ->end()
  197.                             ->append($this->getSitemapHelperNode('loaders', ['_all']))
  198.                             ->append($this->getSitemapHelperNode('guessers', ['_all']))
  199.                             ->append($this->getSitemapHelperNode('voters', ['_all']))
  200.                         ->end()
  201.                     ->end()
  202.                     ->arrayNode('configurations')
  203.                         ->useAttributeAsKey('name')
  204.                         ->prototype('array')
  205.                             ->fixXmlConfig('template')
  206.                             ->fixXmlConfig('loader')
  207.                             ->fixXmlConfig('guesser')
  208.                             ->fixXmlConfig('voter')
  209.                             ->children()
  210.                                 ->scalarNode('default_change_frequency')->defaultNull()->end()
  211.                                 ->arrayNode('templates')
  212.                                     ->useAttributeAsKey('format')
  213.                                     ->requiresAtLeastOneElement()
  214.                                     ->prototype('scalar')->end()
  215.                                 ->end()
  216.                                 ->append($this->getSitemapHelperNode('loaders', []))
  217.                                 ->append($this->getSitemapHelperNode('guessers', []))
  218.                                 ->append($this->getSitemapHelperNode('voters', []))
  219.                             ->end()
  220.                         ->end()
  221.                     ->end()
  222.                 ->end()
  223.             ->end()
  224.         ;
  225.     }
  226.     private function getSitemapHelperNode($type$default)
  227.     {
  228.         $node = new ArrayNodeDefinition($type);
  229.         $node
  230.             ->beforeNormalization()
  231.                 ->ifTrue(function ($config) {
  232.                     return is_string($config);
  233.                 })
  234.                 ->then(function ($config) {
  235.                     return [$config];
  236.                 })
  237.             ->end()
  238.             ->defaultValue($default)
  239.             ->prototype('scalar')->end()
  240.             ->end()
  241.         ;
  242.         return $node;
  243.     }
  244.     /**
  245.      * Attach the content listener node to the tree.
  246.      *
  247.      * @param NodeBuilder $nodeBuilder
  248.      */
  249.     private function addContentListenerSection(NodeBuilder $nodeBuilder)
  250.     {
  251.         $nodeBuilder
  252.             ->arrayNode('content_listener')
  253.                 ->canBeDisabled()
  254.                 ->children()
  255.                     ->scalarNode('content_key')
  256.                     ->defaultValue(class_exists('Symfony\Cmf\Bundle\RoutingBundle\Routing\DynamicRouter') ? DynamicRouter::CONTENT_KEY '')
  257.                 ->end()
  258.             ->end()
  259.         ;
  260.     }
  261.     /**
  262.      * Attach the form node to the tree.
  263.      *
  264.      * @param NodeBuilder $nodeBuilder
  265.      */
  266.     private function addFormSection($nodeBuilder)
  267.     {
  268.         $nodeBuilder
  269.             ->arrayNode('form')
  270.                 ->addDefaultsIfNotSet()
  271.                 ->fixXmlConfig('option')
  272.                 ->children()
  273.                     ->arrayNode('data_class')
  274.                         ->addDefaultsIfNotSet()
  275.                         ->children()
  276.                             ->scalarNode('seo_metadata')->defaultNull()->end()
  277.                         ->end()
  278.                     ->end()
  279.                     ->arrayNode('options')
  280.                         ->addDefaultsIfNotSet()
  281.                         ->children()
  282.                             ->enumNode('generic_metadata')
  283.                                 ->info('Whether to show fields to edit generic SEO information. Needs burgov/key-value-form-bundle.')
  284.                                 ->values([truefalse'auto'])
  285.                                 ->defaultValue('auto')
  286.                             ->end()
  287.                         ->end()
  288.                     ->end()
  289.                 ->end()
  290.             ->end()
  291.        ;
  292.     }
  293. }