feat: allow resetting settings to default (#3935)

Co-authored-by: Sami Mazouz <sychocouldy@gmail.com>
This commit is contained in:
Tristian Kelly 2024-10-21 10:17:24 -04:00 committed by GitHub
parent ee60a7f8ca
commit 084ae6fceb
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 83 additions and 1 deletions

View File

@ -13,6 +13,7 @@ use Flarum\Http\RequestUtil;
use Flarum\Settings\Event;
use Flarum\Settings\SettingsRepositoryInterface;
use Illuminate\Contracts\Events\Dispatcher;
use Illuminate\Support\Arr;
use Laminas\Diactoros\Response\EmptyResponse;
use Psr\Http\Message\ResponseInterface;
use Psr\Http\Message\ServerRequestInterface;
@ -20,6 +21,8 @@ use Psr\Http\Server\RequestHandlerInterface;
class SetSettingsController implements RequestHandlerInterface
{
public static array $resetWhen = [];
public function __construct(
protected SettingsRepositoryInterface $settings,
protected Dispatcher $dispatcher
@ -37,7 +40,11 @@ class SetSettingsController implements RequestHandlerInterface
foreach ($settings as $k => $v) {
$this->dispatcher->dispatch(new Event\Serializing($k, $v));
$this->settings->set($k, $v);
if (! is_null($resetWhen = Arr::get(static::$resetWhen, $k)) && $resetWhen($v)) {
$this->settings->delete($k);
} else {
$this->settings->set($k, $v);
}
}
$this->dispatcher->dispatch(new Event\Saved($settings));

View File

@ -10,12 +10,14 @@
namespace Flarum\Extend;
use Flarum\Admin\WhenSavingSettings;
use Flarum\Api\Controller\SetSettingsController;
use Flarum\Api\Resource\ForumResource;
use Flarum\Api\Schema\Attribute;
use Flarum\Extension\Extension;
use Flarum\Foundation\ContainerUtil;
use Flarum\Settings\SettingsRepositoryInterface;
use Illuminate\Contracts\Container\Container;
use Illuminate\Support\Arr;
use Illuminate\Support\Collection;
class Settings implements ExtenderInterface
@ -24,6 +26,7 @@ class Settings implements ExtenderInterface
private array $defaults = [];
private array $lessConfigs = [];
private array $resetJsCacheFor = [];
private array $resetWhen = [];
/**
* Serialize a setting value to the ForumSerializer attributes.
@ -62,6 +65,20 @@ class Settings implements ExtenderInterface
return $this;
}
/**
* Delete a custom setting value when the callback returns true.
* This allows the setting to be reset to its default value.
*
* @param string $key: The key of the setting.
* @param (callable(mixed $value): bool) $callback: The callback to determine if the setting should be reset.
*/
public function resetWhen(string $key, callable|string $callback): self
{
$this->resetWhen[$key] = $callback;
return $this;
}
/**
* Register a setting as a LESS configuration variable.
*
@ -113,6 +130,16 @@ class Settings implements ExtenderInterface
});
}
if (! empty($this->resetWhen)) {
foreach ($this->resetWhen as $key => $callback) {
Arr::set(
SetSettingsController::$resetWhen,
$key,
ContainerUtil::wrapCallback($callback, $container)
);
}
}
if (! empty($this->settings)) {
(new ApiResource(ForumResource::class))
->fields(function () use ($container) {

View File

@ -187,6 +187,54 @@ class SettingsTest extends TestCase
$this->assertEquals(null, $value);
}
#[Test]
public function resetting_setting_returns_default_value()
{
$this->extend(
(new Extend\Settings())
->default('custom-prefix.filter_this_setting', 'extenderDefault')
->resetWhen('custom-prefix.filter_this_setting', function (mixed $value): bool {
return $value === '';
})
);
$this->send(
$this->request('POST', '/api/settings', [
'authenticatedAs' => 1,
'json' => [
'custom-prefix.filter_this_setting' => ''
]
])
);
$value = $this->app()
->getContainer()
->make('flarum.settings')
->get('custom-prefix.filter_this_setting');
$this->assertEquals('extenderDefault', $value);
}
#[Test]
public function not_resetting_setting_returns_value()
{
$this->send(
$this->request('POST', '/api/settings', [
'authenticatedAs' => 1,
'json' => [
'custom-prefix.filter_this_setting' => ''
]
])
);
$value = $this->app()
->getContainer()
->make('flarum.settings')
->get('custom-prefix.filter_this_setting');
$this->assertEquals('', $value);
}
#[Test]
public function custom_less_var_does_not_work_by_default()
{