src/CoreBundle/Settings/SettingsManager.php line 216

  1. <?php
  2. declare(strict_types=1);
  3. /* For licensing terms, see /license.txt */
  4. namespace Chamilo\CoreBundle\Settings;
  5. use Chamilo\CoreBundle\Entity\AccessUrl;
  6. use Chamilo\CoreBundle\Entity\Course;
  7. use Chamilo\CoreBundle\Entity\SettingsCurrent;
  8. use Doctrine\ORM\EntityManager;
  9. use Doctrine\ORM\EntityRepository;
  10. use InvalidArgumentException;
  11. use Sylius\Bundle\SettingsBundle\Event\SettingsEvent;
  12. use Sylius\Bundle\SettingsBundle\Manager\SettingsManagerInterface;
  13. use Sylius\Bundle\SettingsBundle\Model\Settings;
  14. use Sylius\Bundle\SettingsBundle\Model\SettingsInterface;
  15. use Sylius\Bundle\SettingsBundle\Registry\ServiceRegistryInterface;
  16. use Sylius\Bundle\SettingsBundle\Schema\SchemaInterface;
  17. use Sylius\Bundle\SettingsBundle\Schema\SettingsBuilder;
  18. use Symfony\Component\EventDispatcher\EventDispatcherInterface;
  19. use Symfony\Component\HttpFoundation\RequestStack;
  20. use Symfony\Component\Validator\ConstraintViolationListInterface;
  21. use Symfony\Component\Validator\Exception\ValidatorException;
  22. /**
  23.  * Handles the platform settings.
  24.  */
  25. class SettingsManager implements SettingsManagerInterface
  26. {
  27.     protected ?AccessUrl $url null;
  28.     protected ServiceRegistryInterface $schemaRegistry;
  29.     protected EntityManager $manager;
  30.     protected EntityRepository $repository;
  31.     protected EventDispatcherInterface $eventDispatcher;
  32.     /**
  33.      * Runtime cache for resolved parameters.
  34.      *
  35.      * @var Settings[]
  36.      */
  37.     protected array $resolvedSettings = [];
  38.     /**
  39.      * @var null|array<string, Settings>|mixed[]
  40.      */
  41.     protected ?array $schemaList;
  42.     protected RequestStack $request;
  43.     public function __construct(
  44.         ServiceRegistryInterface $schemaRegistry,
  45.         EntityManager $manager,
  46.         EntityRepository $repository,
  47.         EventDispatcherInterface $eventDispatcher,
  48.         RequestStack $request
  49.     ) {
  50.         $this->schemaRegistry $schemaRegistry;
  51.         $this->manager $manager;
  52.         $this->repository $repository;
  53.         $this->eventDispatcher $eventDispatcher;
  54.         $this->request $request;
  55.         $this->schemaList = [];
  56.     }
  57.     public function getUrl(): ?AccessUrl
  58.     {
  59.         return $this->url;
  60.     }
  61.     public function setUrl(AccessUrl $url): void
  62.     {
  63.         $this->url $url;
  64.     }
  65.     public function updateSchemas(AccessUrl $url): void
  66.     {
  67.         $this->url $url;
  68.         $schemas array_keys($this->getSchemas());
  69.         foreach ($schemas as $schema) {
  70.             $settings $this->load($this->convertServiceToNameSpace($schema));
  71.             $this->update($settings);
  72.         }
  73.     }
  74.     public function installSchemas(AccessUrl $url): void
  75.     {
  76.         $this->url $url;
  77.         $schemas array_keys($this->getSchemas());
  78.         foreach ($schemas as $schema) {
  79.             $settings $this->load($this->convertServiceToNameSpace($schema));
  80.             $this->save($settings);
  81.         }
  82.     }
  83.     /**
  84.      * @return array|AbstractSettingsSchema[]
  85.      */
  86.     public function getSchemas(): array
  87.     {
  88.         return $this->schemaRegistry->all();
  89.     }
  90.     public function convertNameSpaceToService(string $category): string
  91.     {
  92.         return 'chamilo_core.settings.'.$category;
  93.     }
  94.     public function convertServiceToNameSpace(string $category): string
  95.     {
  96.         return str_replace('chamilo_core.settings.'''$category);
  97.     }
  98.     public function updateSetting(string $name$value): void
  99.     {
  100.         $name $this->validateSetting($name);
  101.         [$category$name] = explode('.'$name);
  102.         $settings $this->load($category);
  103.         if (!$settings->has($name)) {
  104.             $message sprintf("Parameter %s doesn't exists."$name);
  105.             throw new InvalidArgumentException($message);
  106.         }
  107.         $settings->set($name$value);
  108.         $this->update($settings);
  109.     }
  110.     /**
  111.      * Get a specific configuration setting, getting from the previously stored
  112.      * PHP session data whenever possible.
  113.      *
  114.      * @param string $name       The setting name (composed if in a category, i.e. 'platform.theme')
  115.      * @param bool   $loadFromDb Whether to load from the database
  116.      */
  117.     public function getSetting(string $namebool $loadFromDb false): mixed
  118.     {
  119.         $name $this->validateSetting($name);
  120.         [$category$name] = explode('.'$name);
  121.         if ($loadFromDb) {
  122.             $settings $this->load($category$name);
  123.             if ($settings->has($name)) {
  124.                 return $settings->get($name);
  125.             } else {
  126.                 return null;
  127.             }
  128.         }
  129.         $this->loadAll();
  130.         if (!empty($this->schemaList) && isset($this->schemaList[$category])) {
  131.             $settings $this->schemaList[$category];
  132.             if ($settings->has($name)) {
  133.                 return $settings->get($name);
  134.             } else {
  135.                 error_log("Attempted to access undefined setting '$name' in category '$category'.");
  136.                 return null;
  137.             }
  138.         }
  139.         throw new InvalidArgumentException(sprintf('Category %s not found'$category));
  140.     }
  141.     public function loadAll(): void
  142.     {
  143.         $session null;
  144.         if ($this->request->getCurrentRequest()) {
  145.             $session $this->request->getCurrentRequest()->getSession();
  146.             $schemaList $session->get('schemas');
  147.             if (!empty($schemaList)) {
  148.                 $this->schemaList $schemaList;
  149.                 return;
  150.             }
  151.         }
  152.         $schemas array_keys($this->getSchemas());
  153.         $schemaList = [];
  154.         $settingsBuilder = new SettingsBuilder();
  155.         $all $this->getAllParametersByCategory();
  156.         foreach ($schemas as $schema) {
  157.             $schemaRegister $this->schemaRegistry->get($schema);
  158.             $schemaRegister->buildSettings($settingsBuilder);
  159.             $name $this->convertServiceToNameSpace($schema);
  160.             $settings = new Settings();
  161.             $parameters $all[$name] ?? [];
  162.             $knownParameters array_filter($parameters, function ($key) use ($settingsBuilder) {
  163.                 return $settingsBuilder->isDefined($key);
  164.             }, ARRAY_FILTER_USE_KEY);
  165.             $transformers $settingsBuilder->getTransformers();
  166.             foreach ($transformers as $parameter => $transformer) {
  167.                 if (\array_key_exists($parameter$knownParameters)) {
  168.                     if ('course_creation_use_template' === $parameter) {
  169.                         if (empty($knownParameters[$parameter])) {
  170.                             $knownParameters[$parameter] = null;
  171.                         }
  172.                     } else {
  173.                         $knownParameters[$parameter] = $transformer->reverseTransform($knownParameters[$parameter]);
  174.                     }
  175.                 }
  176.             }
  177.             $parameters $settingsBuilder->resolve($knownParameters);
  178.             $settings->setParameters($parameters);
  179.             $schemaList[$name] = $settings;
  180.         }
  181.         $this->schemaList $schemaList;
  182.         if ($session && $this->request->getCurrentRequest()) {
  183.             $session->set('schemas'$schemaList);
  184.         }
  185.     }
  186.     public function load(string $schemaAlias, ?string $namespace nullbool $ignoreUnknown true): SettingsInterface
  187.     {
  188.         $settings = new Settings();
  189.         $schemaAliasNoPrefix $schemaAlias;
  190.         $schemaAlias 'chamilo_core.settings.'.$schemaAlias;
  191.         if ($this->schemaRegistry->has($schemaAlias)) {
  192.             /** @var SchemaInterface $schema */
  193.             $schema $this->schemaRegistry->get($schemaAlias);
  194.         } else {
  195.             return $settings;
  196.         }
  197.         $settings->setSchemaAlias($schemaAlias);
  198.         // We need to get a plain parameters array since we use the options resolver on it
  199.         $parameters $this->getParameters($schemaAliasNoPrefix);
  200.         $settingsBuilder = new SettingsBuilder();
  201.         $schema->buildSettings($settingsBuilder);
  202.         // Remove unknown settings' parameters (e.g. From a previous version of the settings schema)
  203.         if (true === $ignoreUnknown) {
  204.             foreach ($parameters as $name => $value) {
  205.                 if (!$settingsBuilder->isDefined($name)) {
  206.                     unset($parameters[$name]);
  207.                 }
  208.             }
  209.         }
  210.         foreach ($settingsBuilder->getTransformers() as $parameter => $transformer) {
  211.             if (\array_key_exists($parameter$parameters)) {
  212.                 if ('course_creation_use_template' === $parameter) {
  213.                     if (empty($parameters[$parameter])) {
  214.                         $parameters[$parameter] = null;
  215.                     }
  216.                 } else {
  217.                     $parameters[$parameter] = $transformer->reverseTransform($parameters[$parameter]);
  218.                 }
  219.             }
  220.         }
  221.         $parameters $settingsBuilder->resolve($parameters);
  222.         $settings->setParameters($parameters);
  223.         return $settings;
  224.     }
  225.     public function update(SettingsInterface $settings): void
  226.     {
  227.         $namespace $settings->getSchemaAlias();
  228.         /** @var SchemaInterface $schema */
  229.         $schema $this->schemaRegistry->get($settings->getSchemaAlias());
  230.         $settingsBuilder = new SettingsBuilder();
  231.         $schema->buildSettings($settingsBuilder);
  232.         $parameters $settingsBuilder->resolve($settings->getParameters());
  233.         // Transform value. Example array to string using transformer. Example:
  234.         // 1. Setting "tool_visible_by_default_at_creation" it's a multiple select
  235.         // 2. Is defined as an array in class DocumentSettingsSchema
  236.         // 3. Add transformer for that variable "ArrayToIdentifierTransformer"
  237.         // 4. Here we recover the transformer and convert the array to string
  238.         foreach ($settingsBuilder->getTransformers() as $parameter => $transformer) {
  239.             if (\array_key_exists($parameter$parameters)) {
  240.                 $parameters[$parameter] = $transformer->transform($parameters[$parameter]);
  241.             }
  242.         }
  243.         $settings->setParameters($parameters);
  244.         $category $this->convertServiceToNameSpace($settings->getSchemaAlias());
  245.         $persistedParameters $this->repository->findBy([
  246.             'category' => $category,
  247.         ]);
  248.         $persistedParametersMap = [];
  249.         /** @var SettingsCurrent $parameter */
  250.         foreach ($persistedParameters as $parameter) {
  251.             $persistedParametersMap[$parameter->getVariable()] = $parameter;
  252.         }
  253.         $url $this->getUrl();
  254.         $simpleCategoryName str_replace('chamilo_core.settings.'''$namespace);
  255.         foreach ($parameters as $name => $value) {
  256.             if (isset($persistedParametersMap[$name])) {
  257.                 $parameter $persistedParametersMap[$name];
  258.                 $parameter->setSelectedValue($value);
  259.                 $parameter->setCategory($simpleCategoryName);
  260.                 $this->manager->persist($parameter);
  261.             } else {
  262.                 $parameter = (new SettingsCurrent())
  263.                     ->setVariable($name)
  264.                     ->setCategory($simpleCategoryName)
  265.                     ->setTitle($name)
  266.                     ->setSelectedValue($value)
  267.                     ->setUrl($url)
  268.                     ->setAccessUrlChangeable(1)
  269.                     ->setAccessUrlLocked(1)
  270.                 ;
  271.                 // @var ConstraintViolationListInterface $errors
  272.                 /*$errors = $this->validator->validate($parameter);
  273.                 if (0 < $errors->count()) {
  274.                     throw new ValidatorException($errors->get(0)->getMessage());
  275.                 }*/
  276.                 $this->manager->persist($parameter);
  277.             }
  278.         }
  279.         $this->manager->flush();
  280.     }
  281.     /**
  282.      * @throws ValidatorException
  283.      */
  284.     public function save(SettingsInterface $settings): void
  285.     {
  286.         $namespace $settings->getSchemaAlias();
  287.         /** @var SchemaInterface $schema */
  288.         $schema $this->schemaRegistry->get($settings->getSchemaAlias());
  289.         $settingsBuilder = new SettingsBuilder();
  290.         $schema->buildSettings($settingsBuilder);
  291.         $parameters $settingsBuilder->resolve($settings->getParameters());
  292.         // Transform value. Example array to string using transformer. Example:
  293.         // 1. Setting "tool_visible_by_default_at_creation" it's a multiple select
  294.         // 2. Is defined as an array in class DocumentSettingsSchema
  295.         // 3. Add transformer for that variable "ArrayToIdentifierTransformer"
  296.         // 4. Here we recover the transformer and convert the array to string
  297.         foreach ($settingsBuilder->getTransformers() as $parameter => $transformer) {
  298.             if (\array_key_exists($parameter$parameters)) {
  299.                 $parameters[$parameter] = $transformer->transform($parameters[$parameter]);
  300.             }
  301.         }
  302.         $settings->setParameters($parameters);
  303.         $persistedParameters $this->repository->findBy([
  304.             'category' => $this->convertServiceToNameSpace($settings->getSchemaAlias()),
  305.         ]);
  306.         $persistedParametersMap = [];
  307.         foreach ($persistedParameters as $parameter) {
  308.             $persistedParametersMap[$parameter->getVariable()] = $parameter;
  309.         }
  310.         // @var SettingsEvent $event
  311.         /*$event = $this->eventDispatcher->dispatch(
  312.             SettingsEvent::PRE_SAVE,
  313.             new SettingsEvent($settings, $parameters)
  314.         );*/
  315.         $url $this->getUrl();
  316.         $simpleCategoryName str_replace('chamilo_core.settings.'''$namespace);
  317.         foreach ($parameters as $name => $value) {
  318.             if (isset($persistedParametersMap[$name])) {
  319.                 $parameter $persistedParametersMap[$name];
  320.                 $parameter->setSelectedValue($value);
  321.             } else {
  322.                 $parameter = (new SettingsCurrent())
  323.                     ->setVariable($name)
  324.                     ->setCategory($simpleCategoryName)
  325.                     ->setTitle($name)
  326.                     ->setSelectedValue($value)
  327.                     ->setUrl($url)
  328.                     ->setAccessUrlChangeable(1)
  329.                     ->setAccessUrlLocked(1)
  330.                 ;
  331.                 // @var ConstraintViolationListInterface $errors
  332.                 /*$errors = $this->validator->validate($parameter);
  333.                 if (0 < $errors->count()) {
  334.                     throw new ValidatorException($errors->get(0)->getMessage());
  335.                 }*/
  336.                 $this->manager->persist($parameter);
  337.             }
  338.             $this->manager->persist($parameter);
  339.         }
  340.         $this->manager->flush();
  341.         //        $schemaAlias = $settings->getSchemaAlias();
  342.         //        $schemaAliasChamilo = str_replace('chamilo_core.settings.', '', $schemaAlias);
  343.         //
  344.         //        $schema = $this->schemaRegistry->get($schemaAlias);
  345.         //
  346.         //        $settingsBuilder = new SettingsBuilder();
  347.         //        $schema->buildSettings($settingsBuilder);
  348.         //
  349.         //        $parameters = $settingsBuilder->resolve($settings->getParameters());
  350.         //
  351.         //        foreach ($settingsBuilder->getTransformers() as $parameter => $transformer) {
  352.         //            if (array_key_exists($parameter, $parameters)) {
  353.         //                $parameters[$parameter] = $transformer->transform($parameters[$parameter]);
  354.         //            }
  355.         //        }
  356.         //
  357.         //        /** @var \Sylius\Bundle\SettingsBundle\Event\SettingsEvent $event */
  358.         //        $event = $this->eventDispatcher->dispatch(
  359.         //            SettingsEvent::PRE_SAVE,
  360.         //            new SettingsEvent($settings)
  361.         //        );
  362.         //
  363.         //        /** @var SettingsCurrent $url */
  364.         //        $url = $event->getSettings()->getAccessUrl();
  365.         //
  366.         //        foreach ($parameters as $name => $value) {
  367.         //            if (isset($persistedParametersMap[$name])) {
  368.         //                if ($value instanceof Course) {
  369.         //                    $value = $value->getId();
  370.         //                }
  371.         //                $persistedParametersMap[$name]->setValue($value);
  372.         //            } else {
  373.         //                $setting = new Settings();
  374.         //                $setting->setSchemaAlias($schemaAlias);
  375.         //
  376.         //                $setting
  377.         //                    ->setNamespace($schemaAliasChamilo)
  378.         //                    ->setName($name)
  379.         //                    ->setValue($value)
  380.         //                    ->setUrl($url)
  381.         //                    ->setAccessUrlLocked(0)
  382.         //                    ->setAccessUrlChangeable(1)
  383.         //                ;
  384.         //
  385.         //                /** @var ConstraintViolationListInterface $errors */
  386.         //                /*$errors = $this->->validate($parameter);
  387.         //                if (0 < $errors->count()) {
  388.         //                    throw new ValidatorException($errors->get(0)->getMessage());
  389.         //                }*/
  390.         //                $this->manager->persist($setting);
  391.         //                $this->manager->flush();
  392.         //            }
  393.         //        }
  394.         /*$parameters = $settingsBuilder->resolve($settings->getParameters());
  395.         $settings->setParameters($parameters);
  396.         $this->eventDispatcher->dispatch(SettingsEvent::PRE_SAVE, new SettingsEvent($settings));
  397.         $this->manager->persist($settings);
  398.         $this->manager->flush();
  399.         $this->eventDispatcher->dispatch(SettingsEvent::POST_SAVE, new SettingsEvent($settings));*/
  400.     }
  401.     /**
  402.      * @param string $keyword
  403.      */
  404.     public function getParametersFromKeywordOrderedByCategory($keyword): array
  405.     {
  406.         $query $this->repository->createQueryBuilder('s')
  407.             ->where('s.variable LIKE :keyword OR s.title LIKE :keyword')
  408.             ->setParameter('keyword'"%{$keyword}%")
  409.         ;
  410.         $parametersFromDb $query->getQuery()->getResult();
  411.         $parameters = [];
  412.         /** @var SettingsCurrent $parameter */
  413.         foreach ($parametersFromDb as $parameter) {
  414.             $parameters[$parameter->getCategory()][] = $parameter;
  415.         }
  416.         return $parameters;
  417.     }
  418.     /**
  419.      * @param string $namespace
  420.      * @param string $keyword
  421.      * @param bool   $returnObjects
  422.      *
  423.      * @return array
  424.      */
  425.     public function getParametersFromKeyword($namespace$keyword ''$returnObjects false)
  426.     {
  427.         if (empty($keyword)) {
  428.             $criteria = [
  429.                 'category' => $namespace,
  430.             ];
  431.             $parametersFromDb $this->repository->findBy($criteria);
  432.         } else {
  433.             $query $this->repository->createQueryBuilder('s')
  434.                 ->where('s.variable LIKE :keyword')
  435.                 ->setParameter('keyword'"%{$keyword}%")
  436.             ;
  437.             $parametersFromDb $query->getQuery()->getResult();
  438.         }
  439.         if ($returnObjects) {
  440.             return $parametersFromDb;
  441.         }
  442.         $parameters = [];
  443.         /** @var SettingsCurrent $parameter */
  444.         foreach ($parametersFromDb as $parameter) {
  445.             $parameters[$parameter->getVariable()] = $parameter->getSelectedValue();
  446.         }
  447.         return $parameters;
  448.     }
  449.     private function validateSetting(string $name): string
  450.     {
  451.         if (!str_contains($name'.')) {
  452.             // throw new \InvalidArgumentException(sprintf('Parameter must be in format "namespace.name", "%s" given.', $name));
  453.             // This code allows the possibility of calling
  454.             // api_get_setting('allow_skills_tool') instead of
  455.             // the "correct" way api_get_setting('platform.allow_skills_tool')
  456.             $items $this->getVariablesAndCategories();
  457.             if (isset($items[$name])) {
  458.                 $originalName $name;
  459.                 $name $this->renameVariable($name);
  460.                 $category $this->fixCategory(
  461.                     strtolower($name),
  462.                     strtolower($items[$originalName])
  463.                 );
  464.                 $name $category.'.'.$name;
  465.             } else {
  466.                 $message sprintf('Parameter must be in format "category.name", "%s" given.'$name);
  467.                 throw new InvalidArgumentException($message);
  468.             }
  469.         }
  470.         return $name;
  471.     }
  472.     /**
  473.      * Load parameter from database.
  474.      *
  475.      * @param string $namespace
  476.      *
  477.      * @return array
  478.      */
  479.     private function getParameters($namespace)
  480.     {
  481.         $parameters = [];
  482.         $category $this->repository->findBy(['category' => $namespace]);
  483.         /** @var SettingsCurrent $parameter */
  484.         foreach ($category as $parameter) {
  485.             $parameters[$parameter->getVariable()] = $parameter->getSelectedValue();
  486.         }
  487.         return $parameters;
  488.     }
  489.     private function getAllParametersByCategory()
  490.     {
  491.         $parameters = [];
  492.         $all $this->repository->findAll();
  493.         /** @var SettingsCurrent $parameter */
  494.         foreach ($all as $parameter) {
  495.             $parameters[$parameter->getCategory()][$parameter->getVariable()] = $parameter->getSelectedValue();
  496.         }
  497.         return $parameters;
  498.     }
  499.     /*private function transformParameters(SettingsBuilder $settingsBuilder, array $parameters)
  500.     {
  501.         $transformedParameters = $parameters;
  502.         foreach ($settingsBuilder->getTransformers() as $parameter => $transformer) {
  503.             if (array_key_exists($parameter, $parameters)) {
  504.                 $transformedParameters[$parameter] = $transformer->reverseTransform($parameters[$parameter]);
  505.             }
  506.         }
  507.         return $transformedParameters;
  508.     }*/
  509.     /**
  510.      * Get variables and categories as in 1.11.x.
  511.      */
  512.     private function getVariablesAndCategories(): array
  513.     {
  514.         return [
  515.             'Institution' => 'Platform',
  516.             'InstitutionUrl' => 'Platform',
  517.             'siteName' => 'Platform',
  518.             'site_name' => 'Platform',
  519.             'emailAdministrator' => 'admin',
  520.             // 'emailAdministrator' => 'Platform',
  521.             'administratorSurname' => 'admin',
  522.             'administratorTelephone' => 'admin',
  523.             'administratorName' => 'admin',
  524.             'show_administrator_data' => 'Platform',
  525.             'show_tutor_data' => 'Session',
  526.             'show_teacher_data' => 'Platform',
  527.             'show_toolshortcuts' => 'Course',
  528.             'allow_group_categories' => 'Course',
  529.             'server_type' => 'Platform',
  530.             'platformLanguage' => 'Language',
  531.             'showonline' => 'Platform',
  532.             'profile' => 'User',
  533.             'default_document_quotum' => 'Course',
  534.             'registration' => 'User',
  535.             'default_group_quotum' => 'Course',
  536.             'allow_registration' => 'Platform',
  537.             'allow_registration_as_teacher' => 'Platform',
  538.             'allow_lostpassword' => 'Platform',
  539.             'allow_user_headings' => 'Course',
  540.             'allow_personal_agenda' => 'agenda',
  541.             'display_coursecode_in_courselist' => 'Platform',
  542.             'display_teacher_in_courselist' => 'Platform',
  543.             'permanently_remove_deleted_files' => 'Tools',
  544.             'dropbox_allow_overwrite' => 'Tools',
  545.             'dropbox_max_filesize' => 'Tools',
  546.             'dropbox_allow_just_upload' => 'Tools',
  547.             'dropbox_allow_student_to_student' => 'Tools',
  548.             'dropbox_allow_group' => 'Tools',
  549.             'dropbox_allow_mailing' => 'Tools',
  550.             'extended_profile' => 'User',
  551.             'student_view_enabled' => 'Platform',
  552.             'show_navigation_menu' => 'Course',
  553.             'enable_tool_introduction' => 'course',
  554.             'page_after_login' => 'Platform',
  555.             'time_limit_whosonline' => 'Platform',
  556.             'breadcrumbs_course_homepage' => 'Course',
  557.             'example_material_course_creation' => 'Platform',
  558.             'account_valid_duration' => 'Platform',
  559.             'use_session_mode' => 'Session',
  560.             'allow_email_editor' => 'Tools',
  561.             // 'registered' => null',
  562.             // 'donotlistcampus' =>'null',
  563.             'show_email_addresses' => 'Platform',
  564.             'service_ppt2lp' => 'NULL',
  565.             'stylesheets' => 'stylesheets',
  566.             'upload_extensions_list_type' => 'Security',
  567.             'upload_extensions_blacklist' => 'Security',
  568.             'upload_extensions_whitelist' => 'Security',
  569.             'upload_extensions_skip' => 'Security',
  570.             'upload_extensions_replace_by' => 'Security',
  571.             'show_number_of_courses' => 'Platform',
  572.             'show_empty_course_categories' => 'Platform',
  573.             'show_back_link_on_top_of_tree' => 'Platform',
  574.             'show_different_course_language' => 'Platform',
  575.             'split_users_upload_directory' => 'Tuning',
  576.             'hide_dltt_markup' => 'Languages',
  577.             'display_categories_on_homepage' => 'Platform',
  578.             'permissions_for_new_directories' => 'Security',
  579.             'permissions_for_new_files' => 'Security',
  580.             'show_tabs' => 'Platform',
  581.             'default_forum_view' => 'Course',
  582.             'platform_charset' => 'Languages',
  583.             'noreply_email_address' => 'Platform',
  584.             'survey_email_sender_noreply' => 'Course',
  585.             'gradebook_enable' => 'Gradebook',
  586.             'gradebook_score_display_coloring' => 'Gradebook',
  587.             'gradebook_score_display_custom' => 'Gradebook',
  588.             'gradebook_score_display_colorsplit' => 'Gradebook',
  589.             'gradebook_score_display_upperlimit' => 'Gradebook',
  590.             'gradebook_number_decimals' => 'Gradebook',
  591.             'user_selected_theme' => 'Platform',
  592.             'allow_course_theme' => 'Course',
  593.             'show_closed_courses' => 'Platform',
  594.             'extendedprofile_registration' => 'User',
  595.             'extendedprofile_registrationrequired' => 'User',
  596.             'add_users_by_coach' => 'Session',
  597.             'extend_rights_for_coach' => 'Security',
  598.             'extend_rights_for_coach_on_survey' => 'Security',
  599.             'course_create_active_tools' => 'Tools',
  600.             'show_session_coach' => 'Session',
  601.             'allow_users_to_create_courses' => 'Platform',
  602.             'allow_message_tool' => 'Tools',
  603.             'allow_social_tool' => 'Tools',
  604.             'allow_students_to_browse_courses' => 'Platform',
  605.             'show_session_data' => 'Session',
  606.             'allow_use_sub_language' => 'language',
  607.             'show_glossary_in_documents' => 'Course',
  608.             'allow_terms_conditions' => 'Platform',
  609.             'search_enabled' => 'Search',
  610.             'search_prefilter_prefix' => 'Search',
  611.             'search_show_unlinked_results' => 'Search',
  612.             'show_courses_descriptions_in_catalog' => 'Course',
  613.             'allow_coach_to_edit_course_session' => 'Session',
  614.             'show_glossary_in_extra_tools' => 'Course',
  615.             'send_email_to_admin_when_create_course' => 'Platform',
  616.             'go_to_course_after_login' => 'Course',
  617.             'math_asciimathML' => 'Editor',
  618.             'enabled_asciisvg' => 'Editor',
  619.             'include_asciimathml_script' => 'Editor',
  620.             'youtube_for_students' => 'Editor',
  621.             'block_copy_paste_for_students' => 'Editor',
  622.             'more_buttons_maximized_mode' => 'Editor',
  623.             'students_download_folders' => 'Document',
  624.             'users_copy_files' => 'Tools',
  625.             'allow_students_to_create_groups_in_social' => 'Tools',
  626.             'allow_send_message_to_all_platform_users' => 'Message',
  627.             'message_max_upload_filesize' => 'Tools',
  628.             'use_users_timezone' => 'profile',
  629.             // 'use_users_timezone' => 'Timezones',
  630.             'timezone_value' => 'platform',
  631.             // 'timezone_value' => 'Timezones',
  632.             'allow_user_course_subscription_by_course_admin' => 'Security',
  633.             'show_link_bug_notification' => 'Platform',
  634.             'show_link_ticket_notification' => 'Platform',
  635.             'course_validation' => 'course',
  636.             // 'course_validation' => 'Platform',
  637.             'course_validation_terms_and_conditions_url' => 'Platform',
  638.             'enabled_wiris' => 'Editor',
  639.             'allow_spellcheck' => 'Editor',
  640.             'force_wiki_paste_as_plain_text' => 'Editor',
  641.             'enabled_googlemaps' => 'Editor',
  642.             'enabled_imgmap' => 'Editor',
  643.             'enabled_support_svg' => 'Tools',
  644.             'pdf_export_watermark_enable' => 'Platform',
  645.             'pdf_export_watermark_by_course' => 'Platform',
  646.             'pdf_export_watermark_text' => 'Platform',
  647.             'enabled_insertHtml' => 'Editor',
  648.             'students_export2pdf' => 'Document',
  649.             'exercise_min_score' => 'Course',
  650.             'exercise_max_score' => 'Course',
  651.             'show_users_folders' => 'Tools',
  652.             'show_default_folders' => 'Tools',
  653.             'show_chat_folder' => 'Tools',
  654.             'enabled_text2audio' => 'Tools',
  655.             'course_hide_tools' => 'Course',
  656.             'enabled_support_pixlr' => 'Tools',
  657.             'show_groups_to_users' => 'Session',
  658.             'accessibility_font_resize' => 'Platform',
  659.             'hide_courses_in_sessions' => 'Session',
  660.             'enable_quiz_scenario' => 'Course',
  661.             'filter_terms' => 'Security',
  662.             'header_extra_content' => 'Tracking',
  663.             'footer_extra_content' => 'Tracking',
  664.             'show_documents_preview' => 'Tools',
  665.             'htmlpurifier_wiki' => 'Editor',
  666.             'cas_activate' => 'CAS',
  667.             'cas_server' => 'CAS',
  668.             'cas_server_uri' => 'CAS',
  669.             'cas_port' => 'CAS',
  670.             'cas_protocol' => 'CAS',
  671.             'cas_add_user_activate' => 'CAS',
  672.             'update_user_info_cas_with_ldap' => 'CAS',
  673.             'student_page_after_login' => 'Platform',
  674.             'teacher_page_after_login' => 'Platform',
  675.             'drh_page_after_login' => 'Platform',
  676.             'sessionadmin_page_after_login' => 'Session',
  677.             'student_autosubscribe' => 'Platform',
  678.             'teacher_autosubscribe' => 'Platform',
  679.             'drh_autosubscribe' => 'Platform',
  680.             'sessionadmin_autosubscribe' => 'Session',
  681.             'scorm_cumulative_session_time' => 'Course',
  682.             'allow_hr_skills_management' => 'Gradebook',
  683.             'enable_help_link' => 'Platform',
  684.             'teachers_can_change_score_settings' => 'Gradebook',
  685.             'allow_users_to_change_email_with_no_password' => 'User',
  686.             'show_admin_toolbar' => 'display',
  687.             'allow_global_chat' => 'Platform',
  688.             'languagePriority1' => 'language',
  689.             'languagePriority2' => 'language',
  690.             'languagePriority3' => 'language',
  691.             'languagePriority4' => 'language',
  692.             'login_is_email' => 'Platform',
  693.             'courses_default_creation_visibility' => 'Course',
  694.             'gradebook_enable_grade_model' => 'Gradebook',
  695.             'teachers_can_change_grade_model_settings' => 'Gradebook',
  696.             'gradebook_default_weight' => 'Gradebook',
  697.             'ldap_description' => 'LDAP',
  698.             'shibboleth_description' => 'Shibboleth',
  699.             'facebook_description' => 'Facebook',
  700.             'gradebook_locking_enabled' => 'Gradebook',
  701.             'gradebook_default_grade_model_id' => 'Gradebook',
  702.             'allow_session_admins_to_manage_all_sessions' => 'Session',
  703.             'allow_skills_tool' => 'Platform',
  704.             'allow_public_certificates' => 'Course',
  705.             'platform_unsubscribe_allowed' => 'Platform',
  706.             'enable_iframe_inclusion' => 'Editor',
  707.             'show_hot_courses' => 'Platform',
  708.             'enable_webcam_clip' => 'Tools',
  709.             'use_custom_pages' => 'Platform',
  710.             'tool_visible_by_default_at_creation' => 'Tools',
  711.             'prevent_session_admins_to_manage_all_users' => 'Session',
  712.             'documents_default_visibility_defined_in_course' => 'Tools',
  713.             'enabled_mathjax' => 'Editor',
  714.             'meta_twitter_site' => 'Tracking',
  715.             'meta_twitter_creator' => 'Tracking',
  716.             'meta_title' => 'Tracking',
  717.             'meta_description' => 'Tracking',
  718.             'meta_image_path' => 'Tracking',
  719.             'allow_teachers_to_create_sessions' => 'Session',
  720.             'institution_address' => 'Platform',
  721.             'chamilo_database_version' => 'null',
  722.             'cron_remind_course_finished_activate' => 'Crons',
  723.             'cron_remind_course_expiration_frequency' => 'Crons',
  724.             'cron_remind_course_expiration_activate' => 'Crons',
  725.             'allow_coach_feedback_exercises' => 'Session',
  726.             'allow_my_files' => 'Platform',
  727.             'ticket_allow_student_add' => 'Ticket',
  728.             'ticket_send_warning_to_all_admins' => 'Ticket',
  729.             'ticket_warn_admin_no_user_in_category' => 'Ticket',
  730.             'ticket_allow_category_edition' => 'Ticket',
  731.             'load_term_conditions_section' => 'Platform',
  732.             'show_terms_if_profile_completed' => 'Ticket',
  733.             'hide_home_top_when_connected' => 'Platform',
  734.             'hide_global_announcements_when_not_connected' => 'Platform',
  735.             'course_creation_use_template' => 'Course',
  736.             'allow_strength_pass_checker' => 'Security',
  737.             'allow_captcha' => 'Security',
  738.             'captcha_number_mistakes_to_block_account' => 'Security',
  739.             'captcha_time_to_block' => 'Security',
  740.             'drh_can_access_all_session_content' => 'Session',
  741.             'display_groups_forum_in_general_tool' => 'Tools',
  742.             'allow_tutors_to_assign_students_to_session' => 'Session',
  743.             'allow_lp_return_link' => 'Course',
  744.             'hide_scorm_export_link' => 'Course',
  745.             'hide_scorm_copy_link' => 'Course',
  746.             'hide_scorm_pdf_link' => 'Course',
  747.             'session_days_before_coach_access' => 'Session',
  748.             'session_days_after_coach_access' => 'Session',
  749.             'pdf_logo_header' => 'Course',
  750.             'order_user_list_by_official_code' => 'Platform',
  751.             'email_alert_manager_on_new_quiz' => 'exercise',
  752.             'show_official_code_exercise_result_list' => 'Tools',
  753.             'course_catalog_hide_private' => 'Platform',
  754.             'catalog_show_courses_sessions' => 'Platform',
  755.             'auto_detect_language_custom_pages' => 'Platform',
  756.             'lp_show_reduced_report' => 'Course',
  757.             'allow_session_course_copy_for_teachers' => 'Session',
  758.             'hide_logout_button' => 'Platform',
  759.             'redirect_admin_to_courses_list' => 'Platform',
  760.             'course_images_in_courses_list' => 'Course',
  761.             'student_publication_to_take_in_gradebook' => 'Gradebook',
  762.             'certificate_filter_by_official_code' => 'Gradebook',
  763.             'exercise_max_ckeditors_in_page' => 'Tools',
  764.             'document_if_file_exists_option' => 'Tools',
  765.             'add_gradebook_certificates_cron_task_enabled' => 'Gradebook',
  766.             'openbadges_backpack' => 'Gradebook',
  767.             'cookie_warning' => 'Tools',
  768.             'hide_course_group_if_no_tools_available' => 'Tools',
  769.             'catalog_allow_session_auto_subscription' => 'Session',
  770.             'registration.soap.php.decode_utf8' => 'Platform',
  771.             'allow_delete_attendance' => 'Tools',
  772.             'gravatar_enabled' => 'Platform',
  773.             'gravatar_type' => 'Platform',
  774.             'limit_session_admin_role' => 'Session',
  775.             'show_session_description' => 'Session',
  776.             'hide_certificate_export_link_students' => 'Gradebook',
  777.             'hide_certificate_export_link' => 'Gradebook',
  778.             'dropbox_hide_course_coach' => 'Tools',
  779.             'dropbox_hide_general_coach' => 'Tools',
  780.             'session_course_ordering' => 'Session',
  781.             'gamification_mode' => 'Platform',
  782.             'prevent_multiple_simultaneous_login' => 'Security',
  783.             'gradebook_detailed_admin_view' => 'Gradebook',
  784.             'course_catalog_published' => 'Course',
  785.             'user_reset_password' => 'Security',
  786.             'user_reset_password_token_limit' => 'Security',
  787.             'my_courses_view_by_session' => 'Session',
  788.             'show_full_skill_name_on_skill_wheel' => 'Platform',
  789.             'messaging_allow_send_push_notification' => 'WebServices',
  790.             'messaging_gdc_project_number' => 'WebServices',
  791.             'messaging_gdc_api_key' => 'WebServices',
  792.             'teacher_can_select_course_template' => 'Course',
  793.             'enable_record_audio' => 'Tools',
  794.             'allow_show_skype_account' => 'Platform',
  795.             'allow_show_linkedin_url' => 'Platform',
  796.             'enable_profile_user_address_geolocalization' => 'User',
  797.             'show_official_code_whoisonline' => 'Profile',
  798.             'icons_mode_svg' => 'display',
  799.             'user_name_order' => 'display',
  800.             'user_name_sort_by' => 'display',
  801.             'default_calendar_view' => 'agenda',
  802.             'exercise_invisible_in_session' => 'exercise',
  803.             'configure_exercise_visibility_in_course' => 'exercise',
  804.             'allow_download_documents_by_api_key' => 'Webservices',
  805.             'profiling_filter_adding_users' => 'profile',
  806.             'donotlistcampus' => 'platform',
  807.             'course_creation_splash_screen' => 'Course',
  808.             'translate_html' => 'Editor',
  809.             'enable_bootstrap_in_documents_html' => 'Course',
  810.         ];
  811.     }
  812.     /**
  813.      * Rename old variable with variable used in Chamilo 2.0.
  814.      *
  815.      * @param string $variable
  816.      */
  817.     private function renameVariable($variable)
  818.     {
  819.         $list = [
  820.             'timezone_value' => 'timezone',
  821.             'Institution' => 'institution',
  822.             'SiteName' => 'site_name',
  823.             'siteName' => 'site_name',
  824.             'InstitutionUrl' => 'institution_url',
  825.             'registration' => 'required_profile_fields',
  826.             'stylesheets' => 'theme',
  827.             'platformLanguage' => 'platform_language',
  828.             'languagePriority1' => 'language_priority_1',
  829.             'languagePriority2' => 'language_priority_2',
  830.             'languagePriority3' => 'language_priority_3',
  831.             'languagePriority4' => 'language_priority_4',
  832.             'gradebook_score_display_coloring' => 'my_display_coloring',
  833.             'ProfilingFilterAddingUsers' => 'profiling_filter_adding_users',
  834.             'course_create_active_tools' => 'active_tools_on_create',
  835.             'emailAdministrator' => 'administrator_email',
  836.             'administratorSurname' => 'administrator_surname',
  837.             'administratorName' => 'administrator_name',
  838.             'administratorTelephone' => 'administrator_phone',
  839.             'registration.soap.php.decode_utf8' => 'decode_utf8',
  840.             'profile' => 'changeable_options',
  841.         ];
  842.         return $list[$variable] ?? $variable;
  843.     }
  844.     /**
  845.      * Replace old Chamilo 1.x category with 2.0 version.
  846.      *
  847.      * @param string $variable
  848.      * @param string $defaultCategory
  849.      */
  850.     private function fixCategory($variable$defaultCategory)
  851.     {
  852.         $settings = [
  853.             'cookie_warning' => 'platform',
  854.             'donotlistcampus' => 'platform',
  855.             'administrator_email' => 'admin',
  856.             'administrator_surname' => 'admin',
  857.             'administrator_name' => 'admin',
  858.             'administrator_phone' => 'admin',
  859.             'exercise_max_ckeditors_in_page' => 'exercise',
  860.             'allow_hr_skills_management' => 'skill',
  861.             'accessibility_font_resize' => 'display',
  862.             'account_valid_duration' => 'profile',
  863.             'allow_global_chat' => 'chat',
  864.             'allow_lostpassword' => 'registration',
  865.             'allow_registration' => 'registration',
  866.             'allow_registration_as_teacher' => 'registration',
  867.             'required_profile_fields' => 'registration',
  868.             'allow_skills_tool' => 'skill',
  869.             'allow_students_to_browse_courses' => 'display',
  870.             'allow_terms_conditions' => 'registration',
  871.             'allow_users_to_create_courses' => 'course',
  872.             'auto_detect_language_custom_pages' => 'language',
  873.             'platform_language' => 'language',
  874.             'course_validation' => 'course',
  875.             'course_validation_terms_and_conditions_url' => 'course',
  876.             'display_categories_on_homepage' => 'display',
  877.             'display_coursecode_in_courselist' => 'course',
  878.             'display_teacher_in_courselist' => 'course',
  879.             'drh_autosubscribe' => 'registration',
  880.             'drh_page_after_login' => 'registration',
  881.             'enable_help_link' => 'display',
  882.             'example_material_course_creation' => 'course',
  883.             'login_is_email' => 'profile',
  884.             'noreply_email_address' => 'mail',
  885.             'page_after_login' => 'registration',
  886.             'pdf_export_watermark_by_course' => 'document',
  887.             'pdf_export_watermark_enable' => 'document',
  888.             'pdf_export_watermark_text' => 'document',
  889.             'platform_unsubscribe_allowed' => 'registration',
  890.             'send_email_to_admin_when_create_course' => 'course',
  891.             'show_admin_toolbar' => 'display',
  892.             'show_administrator_data' => 'display',
  893.             'show_back_link_on_top_of_tree' => 'display',
  894.             'show_closed_courses' => 'display',
  895.             'show_different_course_language' => 'display',
  896.             'show_email_addresses' => 'display',
  897.             'show_empty_course_categories' => 'display',
  898.             'show_full_skill_name_on_skill_wheel' => 'skill',
  899.             'show_hot_courses' => 'display',
  900.             'show_link_bug_notification' => 'display',
  901.             'show_number_of_courses' => 'display',
  902.             'show_teacher_data' => 'display',
  903.             'showonline' => 'display',
  904.             'student_autosubscribe' => 'registration',
  905.             'student_page_after_login' => 'registration',
  906.             'student_view_enabled' => 'course',
  907.             'teacher_autosubscribe' => 'registration',
  908.             'teacher_page_after_login' => 'registration',
  909.             'time_limit_whosonline' => 'display',
  910.             'user_selected_theme' => 'profile',
  911.             'hide_global_announcements_when_not_connected' => 'announcement',
  912.             'hide_home_top_when_connected' => 'display',
  913.             'hide_logout_button' => 'display',
  914.             'institution_address' => 'platform',
  915.             'redirect_admin_to_courses_list' => 'admin',
  916.             'use_custom_pages' => 'platform',
  917.             'allow_group_categories' => 'group',
  918.             'allow_user_headings' => 'display',
  919.             'default_document_quotum' => 'document',
  920.             'default_forum_view' => 'forum',
  921.             'default_group_quotum' => 'document',
  922.             'enable_quiz_scenario' => 'exercise',
  923.             'exercise_max_score' => 'exercise',
  924.             'exercise_min_score' => 'exercise',
  925.             'pdf_logo_header' => 'platform',
  926.             'show_glossary_in_documents' => 'document',
  927.             'show_glossary_in_extra_tools' => 'glossary',
  928.             'survey_email_sender_noreply' => 'survey',
  929.             'allow_coach_feedback_exercises' => 'exercise',
  930.             'sessionadmin_autosubscribe' => 'registration',
  931.             'sessionadmin_page_after_login' => 'registration',
  932.             'show_tutor_data' => 'display',
  933.             'allow_social_tool' => 'social',
  934.             'allow_message_tool' => 'message',
  935.             'allow_email_editor' => 'editor',
  936.             'show_link_ticket_notification' => 'display',
  937.             'permissions_for_new_directories' => 'document',
  938.             'enable_profile_user_address_geolocalization' => 'profile',
  939.             'allow_show_skype_account' => 'profile',
  940.             'allow_show_linkedin_url' => 'profile',
  941.             'allow_students_to_create_groups_in_social' => 'social',
  942.             'default_calendar_view' => 'agenda',
  943.             'documents_default_visibility_defined_in_course' => 'document',
  944.             'message_max_upload_filesize' => 'message',
  945.             'course_create_active_tools' => 'course',
  946.             'tool_visible_by_default_at_creation' => 'document',
  947.             'show_users_folders' => 'document',
  948.             'show_default_folders' => 'document',
  949.             'show_chat_folder' => 'chat',
  950.             'enabled_support_svg' => 'editor',
  951.             'enabled_support_pixlr' => 'editor',
  952.             'enable_webcam_clip' => 'document',
  953.             'enable_record_audio' => 'course',
  954.             'enabled_text2audio' => 'document',
  955.             'permanently_remove_deleted_files' => 'document',
  956.             'allow_delete_attendance' => 'attendance',
  957.             'display_groups_forum_in_general_tool' => 'forum',
  958.             'dropbox_allow_overwrite' => 'dropbox',
  959.             'allow_user_course_subscription_by_course_admin' => 'course',
  960.             'hide_course_group_if_no_tools_available' => 'group',
  961.             'extend_rights_for_coach_on_survey' => 'survey',
  962.             'show_official_code_exercise_result_list' => 'exercise',
  963.             'dropbox_max_filesize' => 'dropbox',
  964.             'dropbox_allow_just_upload' => 'dropbox',
  965.             'dropbox_allow_student_to_student' => 'dropbox',
  966.             'dropbox_allow_group' => 'dropbox',
  967.             'dropbox_allow_mailing' => 'dropbox',
  968.             'upload_extensions_list_type' => 'document',
  969.             'upload_extensions_blacklist' => 'document',
  970.             'upload_extensions_skip' => 'document',
  971.             'changeable_options' => 'profile',
  972.             'users_copy_files' => 'document',
  973.             'document_if_file_exists_option' => 'document',
  974.             'permissions_for_new_files' => 'document',
  975.             'extended_profile' => 'profile',
  976.             'split_users_upload_directory' => 'profile',
  977.             'show_documents_preview' => 'document',
  978.             'messaging_allow_send_push_notification' => 'webservice',
  979.             'messaging_gdc_project_number' => 'webservice',
  980.             'messaging_gdc_api_key' => 'webservice',
  981.             'allow_download_documents_by_api_key' => 'webservice',
  982.             'profiling_filter_adding_users' => 'profile',
  983.             'hide_dltt_markup' => 'language',
  984.             'active_tools_on_create' => 'course',
  985.         ];
  986.         return $settings[$variable] ?? $defaultCategory;
  987.     }
  988. }