2016-08-09 00:31:26 +03:00
< ? php
/**
* @ copyright Copyright ( c ) 2016 Arthur Schiwon < blizzz @ arthur - schiwon . de >
*
* @ author Arthur Schiwon < blizzz @ arthur - schiwon . de >
2019-12-03 21:57:53 +03:00
* @ author Christoph Wurst < christoph @ winzerhof - wurst . at >
2017-11-06 17:56:42 +03:00
* @ author Joas Schilling < coding @ schilljs . com >
2019-12-03 21:57:53 +03:00
* @ author Julius Härtl < jus @ bitgrid . net >
2017-11-06 17:56:42 +03:00
* @ author Lukas Reschke < lukas @ statuscode . ch >
* @ author Morris Jobke < hey @ morrisjobke . de >
* @ author Robin Appelman < robin @ icewind . nl >
* @ author Roeland Jago Douma < roeland @ famdouma . nl >
2019-12-03 21:57:53 +03:00
* @ author sualko < klaus @ jsxc . org >
2016-08-09 00:31:26 +03:00
*
* @ license GNU AGPL version 3 or any later version
*
* This program is free software : you can redistribute it and / or modify
* it under the terms of the GNU Affero General Public License as
* published by the Free Software Foundation , either version 3 of the
* License , or ( at your option ) any later version .
*
* This program is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
* GNU Affero General Public License for more details .
*
* You should have received a copy of the GNU Affero General Public License
2019-12-03 21:57:53 +03:00
* along with this program . If not , see < http :// www . gnu . org / licenses />.
2016-08-09 00:31:26 +03:00
*
*/
namespace OC\Settings ;
2019-05-22 11:48:51 +03:00
use Closure ;
2016-08-09 00:31:26 +03:00
use OCP\AppFramework\QueryException ;
use OCP\IL10N ;
use OCP\ILogger ;
2018-09-26 17:46:35 +03:00
use OCP\IServerContainer ;
2017-01-19 12:37:17 +03:00
use OCP\IURLGenerator ;
2019-05-21 23:25:11 +03:00
use OCP\L10N\IFactory ;
2016-08-09 00:31:26 +03:00
use OCP\Settings\IManager ;
use OCP\Settings\ISection ;
2019-11-22 22:52:10 +03:00
use OCP\Settings\ISettings ;
2019-05-22 11:48:51 +03:00
use OCP\Settings\ISubAdminSettings ;
2016-08-09 00:31:26 +03:00
class Manager implements IManager {
2018-09-26 17:46:35 +03:00
2016-08-09 00:31:26 +03:00
/** @var ILogger */
private $log ;
2018-09-26 17:46:35 +03:00
2016-08-09 00:31:26 +03:00
/** @var IL10N */
private $l ;
2018-09-26 17:46:35 +03:00
2019-05-21 23:25:11 +03:00
/** @var IFactory */
private $l10nFactory ;
2017-01-19 12:37:17 +03:00
/** @var IURLGenerator */
private $url ;
2016-08-12 17:52:20 +03:00
2018-09-26 17:46:35 +03:00
/** @var IServerContainer */
private $container ;
2016-08-09 00:31:26 +03:00
public function __construct (
ILogger $log ,
2019-05-21 23:25:11 +03:00
IFactory $l10nFactory ,
2017-05-16 03:46:42 +03:00
IURLGenerator $url ,
2018-09-26 17:46:35 +03:00
IServerContainer $container
2016-08-09 00:31:26 +03:00
) {
$this -> log = $log ;
2019-05-21 23:25:11 +03:00
$this -> l10nFactory = $l10nFactory ;
2017-01-19 12:37:17 +03:00
$this -> url = $url ;
2018-09-26 17:46:35 +03:00
$this -> container = $container ;
2016-08-09 00:31:26 +03:00
}
2018-01-29 15:14:56 +03:00
/** @var array */
protected $sectionClasses = [];
/** @var array */
protected $sections = [];
2016-08-09 00:31:26 +03:00
/**
2018-01-29 15:14:56 +03:00
* @ param string $type 'admin' or 'personal'
* @ param string $section Class must implement OCP\Settings\ISection
2018-09-26 17:46:35 +03:00
*
2018-01-29 15:14:56 +03:00
* @ return void
2016-08-09 00:31:26 +03:00
*/
2018-01-29 15:14:56 +03:00
public function registerSection ( string $type , string $section ) {
2018-08-25 17:48:37 +03:00
if ( ! isset ( $this -> sectionClasses [ $type ])) {
$this -> sectionClasses [ $type ] = [];
}
$this -> sectionClasses [ $type ][] = $section ;
2016-08-09 00:31:26 +03:00
}
2016-08-15 21:03:19 +03:00
/**
2018-01-29 15:14:56 +03:00
* @ param string $type 'admin' or 'personal'
2018-09-26 17:46:35 +03:00
*
2018-01-29 15:14:56 +03:00
* @ return ISection []
2016-08-15 21:03:19 +03:00
*/
2018-01-29 15:14:56 +03:00
protected function getSections ( string $type ) : array {
if ( ! isset ( $this -> sections [ $type ])) {
$this -> sections [ $type ] = [];
2017-05-19 13:11:07 +03:00
}
2018-08-25 17:48:37 +03:00
if ( ! isset ( $this -> sectionClasses [ $type ])) {
return $this -> sections [ $type ];
}
2020-08-28 18:06:48 +03:00
foreach ( array_unique ( $this -> sectionClasses [ $type ]) as $index => $class ) {
2018-01-29 15:14:56 +03:00
try {
/** @var ISection $section */
$section = \OC :: $server -> query ( $class );
} catch ( QueryException $e ) {
2018-04-25 16:22:28 +03:00
$this -> log -> logException ( $e , [ 'level' => ILogger :: INFO ]);
2018-01-29 15:14:56 +03:00
continue ;
2017-10-04 17:35:10 +03:00
}
2016-08-15 21:03:19 +03:00
2018-01-29 15:14:56 +03:00
if ( ! $section instanceof ISection ) {
2018-04-25 16:22:28 +03:00
$this -> log -> logException ( new \InvalidArgumentException ( 'Invalid settings section registered' ), [ 'level' => ILogger :: INFO ]);
2018-01-29 15:14:56 +03:00
continue ;
2016-08-16 01:52:41 +03:00
}
2018-08-25 17:48:37 +03:00
$sectionID = $section -> getID ();
2020-09-23 13:23:06 +03:00
if ( $sectionID !== 'connected-accounts' && isset ( $this -> sections [ $type ][ $sectionID ])) {
2020-08-28 18:06:48 +03:00
$this -> log -> logException ( new \InvalidArgumentException ( 'Section with the same ID already registered: ' . $sectionID . ', class: ' . $class ), [ 'level' => ILogger :: INFO ]);
2018-08-25 17:48:37 +03:00
continue ;
}
$this -> sections [ $type ][ $sectionID ] = $section ;
2016-08-09 00:31:26 +03:00
2018-08-25 17:48:37 +03:00
unset ( $this -> sectionClasses [ $type ][ $index ]);
2016-08-09 00:31:26 +03:00
}
2018-01-29 15:14:56 +03:00
return $this -> sections [ $type ];
2016-08-09 00:31:26 +03:00
}
2018-01-29 15:14:56 +03:00
/** @var array */
protected $settingClasses = [];
2016-08-09 00:31:26 +03:00
2018-01-29 15:14:56 +03:00
/** @var array */
protected $settings = [];
2016-08-11 02:41:18 +03:00
/**
2018-01-29 15:14:56 +03:00
* @ param string $type 'admin' or 'personal'
* @ param string $setting Class must implement OCP\Settings\ISetting
2018-09-26 17:46:35 +03:00
*
2018-01-29 15:14:56 +03:00
* @ return void
2016-08-11 02:41:18 +03:00
*/
2018-01-29 15:14:56 +03:00
public function registerSetting ( string $type , string $setting ) {
$this -> settingClasses [ $setting ] = $type ;
2016-08-11 02:41:18 +03:00
}
/**
2018-01-29 15:14:56 +03:00
* @ param string $type 'admin' or 'personal'
* @ param string $section
2019-05-22 11:48:51 +03:00
* @ param Closure $filter optional filter to apply on all loaded ISettings
2018-09-26 17:46:35 +03:00
*
2018-01-29 15:14:56 +03:00
* @ return ISettings []
2016-08-11 02:41:18 +03:00
*/
2019-05-22 11:48:51 +03:00
protected function getSettings ( string $type , string $section , Closure $filter = null ) : array {
2018-01-29 15:14:56 +03:00
if ( ! isset ( $this -> settings [ $type ])) {
$this -> settings [ $type ] = [];
2016-08-09 00:31:26 +03:00
}
2018-01-29 15:14:56 +03:00
if ( ! isset ( $this -> settings [ $type ][ $section ])) {
$this -> settings [ $type ][ $section ] = [];
2016-08-09 00:31:26 +03:00
}
2018-01-29 15:14:56 +03:00
foreach ( $this -> settingClasses as $class => $settingsType ) {
2019-05-22 11:48:51 +03:00
if ( $type !== $settingsType ) {
continue ;
}
2018-01-29 15:14:56 +03:00
try {
/** @var ISettings $setting */
2020-01-30 15:30:45 +03:00
$setting = $this -> container -> query ( $class );
2018-01-29 15:14:56 +03:00
} catch ( QueryException $e ) {
2018-04-25 16:22:28 +03:00
$this -> log -> logException ( $e , [ 'level' => ILogger :: INFO ]);
2018-01-29 15:14:56 +03:00
continue ;
}
2016-08-09 00:31:26 +03:00
2018-01-29 15:14:56 +03:00
if ( ! $setting instanceof ISettings ) {
2018-11-14 20:04:52 +03:00
$this -> log -> logException ( new \InvalidArgumentException ( 'Invalid settings setting registered (' . $class . ')' ), [ 'level' => ILogger :: INFO ]);
2018-01-29 15:14:56 +03:00
continue ;
}
2017-05-19 13:11:07 +03:00
2019-05-22 11:48:51 +03:00
if ( $filter !== null && ! $filter ( $setting )) {
continue ;
}
2019-05-20 19:07:24 +03:00
if ( $setting -> getSection () === null ) {
continue ;
}
2018-01-29 15:14:56 +03:00
if ( ! isset ( $this -> settings [ $settingsType ][ $setting -> getSection ()])) {
$this -> settings [ $settingsType ][ $setting -> getSection ()] = [];
}
$this -> settings [ $settingsType ][ $setting -> getSection ()][] = $setting ;
2017-05-19 13:11:07 +03:00
2018-01-29 15:14:56 +03:00
unset ( $this -> settingClasses [ $class ]);
2016-08-09 00:31:26 +03:00
}
2018-01-29 15:14:56 +03:00
return $this -> settings [ $type ][ $section ];
2016-08-09 00:31:26 +03:00
}
/**
2016-08-15 17:24:56 +03:00
* @ inheritdoc
2016-08-09 00:31:26 +03:00
*/
2018-01-29 15:14:56 +03:00
public function getAdminSections () : array {
2016-08-09 00:31:26 +03:00
// built-in sections
2020-01-28 14:38:11 +03:00
$sections = [];
2016-08-09 00:31:26 +03:00
2018-01-29 15:14:56 +03:00
$appSections = $this -> getSections ( 'admin' );
2016-08-19 18:52:33 +03:00
2018-01-29 15:14:56 +03:00
foreach ( $appSections as $section ) {
/** @var ISection $section */
if ( ! isset ( $sections [ $section -> getPriority ()])) {
$sections [ $section -> getPriority ()] = [];
2016-08-09 00:31:26 +03:00
}
2018-01-29 15:14:56 +03:00
$sections [ $section -> getPriority ()][] = $section ;
2016-08-09 00:31:26 +03:00
}
ksort ( $sections );
2016-12-28 18:58:02 +03:00
2016-08-09 00:31:26 +03:00
return $sections ;
}
2016-12-28 18:58:02 +03:00
/**
* @ inheritdoc
*/
2019-05-22 11:48:51 +03:00
public function getAdminSettings ( $section , bool $subAdminOnly = false ) : array {
if ( $subAdminOnly ) {
2020-04-09 14:53:40 +03:00
$subAdminSettingsFilter = function ( ISettings $settings ) {
2019-05-22 11:48:51 +03:00
return $settings instanceof ISubAdminSettings ;
};
$appSettings = $this -> getSettings ( 'admin' , $section , $subAdminSettingsFilter );
} else {
$appSettings = $this -> getSettings ( 'admin' , $section );
}
2016-08-09 00:31:26 +03:00
2020-01-31 18:55:17 +03:00
$settings = [];
2018-01-29 15:14:56 +03:00
foreach ( $appSettings as $setting ) {
if ( ! isset ( $settings [ $setting -> getPriority ()])) {
$settings [ $setting -> getPriority ()] = [];
2016-08-09 00:31:26 +03:00
}
2018-01-29 15:14:56 +03:00
$settings [ $setting -> getPriority ()][] = $setting ;
2016-08-09 00:31:26 +03:00
}
ksort ( $settings );
return $settings ;
}
2017-05-16 02:40:36 +03:00
/**
* @ inheritdoc
*/
2018-01-29 15:14:56 +03:00
public function getPersonalSections () : array {
2019-05-21 23:25:11 +03:00
if ( $this -> l === null ) {
$this -> l = $this -> l10nFactory -> get ( 'lib' );
}
2020-01-27 22:47:41 +03:00
$sections = [];
2017-05-19 18:34:57 +03:00
2017-06-22 16:19:01 +03:00
$legacyForms = \OC_App :: getForms ( 'personal' );
2020-09-04 16:21:48 +03:00
if (( ! empty ( $legacyForms ) && $this -> hasLegacyPersonalSettingsToRender ( $legacyForms ))
|| count ( $this -> getPersonalSettings ( 'additional' )) > 1 ) {
2017-06-22 16:19:01 +03:00
$sections [ 98 ] = [ new Section ( 'additional' , $this -> l -> t ( 'Additional settings' ), 0 , $this -> url -> imagePath ( 'core' , 'actions/settings-dark.svg' ))];
}
2018-01-29 15:14:56 +03:00
$appSections = $this -> getSections ( 'personal' );
2017-05-19 18:34:57 +03:00
2018-01-29 15:14:56 +03:00
foreach ( $appSections as $section ) {
/** @var ISection $section */
if ( ! isset ( $sections [ $section -> getPriority ()])) {
$sections [ $section -> getPriority ()] = [];
2017-05-19 18:34:57 +03:00
}
2018-01-29 15:14:56 +03:00
$sections [ $section -> getPriority ()][] = $section ;
2017-05-19 18:34:57 +03:00
}
ksort ( $sections );
2017-05-16 02:40:36 +03:00
return $sections ;
}
2017-06-22 16:19:01 +03:00
/**
2018-01-29 15:14:56 +03:00
* @ param string [] $forms
2018-09-26 17:46:35 +03:00
*
2017-06-22 16:19:01 +03:00
* @ return bool
*/
2018-01-29 15:14:56 +03:00
private function hasLegacyPersonalSettingsToRender ( array $forms ) : bool {
2017-06-22 16:19:01 +03:00
foreach ( $forms as $form ) {
2018-09-26 17:46:35 +03:00
if ( trim ( $form ) !== '' ) {
2017-06-22 16:19:01 +03:00
return true ;
}
}
return false ;
}
2017-05-16 02:40:36 +03:00
/**
* @ inheritdoc
*/
2018-01-29 15:14:56 +03:00
public function getPersonalSettings ( $section ) : array {
2020-01-30 15:30:45 +03:00
$settings = [];
2018-01-29 15:14:56 +03:00
$appSettings = $this -> getSettings ( 'personal' , $section );
2017-05-19 18:34:57 +03:00
2018-01-29 15:14:56 +03:00
foreach ( $appSettings as $setting ) {
if ( ! isset ( $settings [ $setting -> getPriority ()])) {
$settings [ $setting -> getPriority ()] = [];
2017-05-19 18:34:57 +03:00
}
2018-01-29 15:14:56 +03:00
$settings [ $setting -> getPriority ()][] = $setting ;
2017-05-19 18:34:57 +03:00
}
ksort ( $settings );
2017-05-16 02:40:36 +03:00
return $settings ;
}
2016-08-09 00:31:26 +03:00
}