From 13d67087aba03b83012414bd033242c9899794af Mon Sep 17 00:00:00 2001 From: SychO9 Date: Thu, 3 Dec 2020 15:18:40 +0100 Subject: [PATCH] Inject provided default values in the repository level --- src/Extend/Settings.php | 9 ++++ src/Settings/DefaultSettingsManager.php | 27 ++++++++++++ .../MemoryCacheSettingsRepository.php | 15 ++++--- src/Settings/SettingsServiceProvider.php | 5 ++- tests/integration/extenders/SettingsTest.php | 41 +++++++++++++++++++ .../MemoryCacheSettingsRepositoryTest.php | 7 +++- 6 files changed, 97 insertions(+), 7 deletions(-) create mode 100644 src/Settings/DefaultSettingsManager.php diff --git a/src/Extend/Settings.php b/src/Extend/Settings.php index 7cdfb312f21..e8d9626be8e 100644 --- a/src/Extend/Settings.php +++ b/src/Extend/Settings.php @@ -13,6 +13,7 @@ use Flarum\Api\Serializer\ForumSerializer; use Flarum\Extension\Extension; use Flarum\Foundation\ContainerUtil; +use Flarum\Settings\DefaultSettingsManager; use Flarum\Settings\SettingsRepositoryInterface; use Illuminate\Contracts\Container\Container; @@ -52,6 +53,14 @@ public function default(string $key, $value) public function extend(Container $container, Extension $extension = null) { + if (! empty($this->defaults)) { + $container->extend(DefaultSettingsManager::class, function (DefaultSettingsManager $manager) { + foreach ($this->defaults as $key => $default) { + $manager->set($key, $default); + } + }); + } + if (! empty($this->settings)) { AbstractSerializer::addMutator( ForumSerializer::class, diff --git a/src/Settings/DefaultSettingsManager.php b/src/Settings/DefaultSettingsManager.php new file mode 100644 index 00000000000..255d27c4e73 --- /dev/null +++ b/src/Settings/DefaultSettingsManager.php @@ -0,0 +1,27 @@ +defaults, $key, $default); + } + + public function set($key, $value) + { + $this->defaults[$key] = $value; + } +} diff --git a/src/Settings/MemoryCacheSettingsRepository.php b/src/Settings/MemoryCacheSettingsRepository.php index 1328e282e36..4f4a41972a3 100644 --- a/src/Settings/MemoryCacheSettingsRepository.php +++ b/src/Settings/MemoryCacheSettingsRepository.php @@ -15,13 +15,16 @@ class MemoryCacheSettingsRepository implements SettingsRepositoryInterface { protected $inner; + protected $defaultSettingsManager; + protected $isCached; protected $cache = []; - public function __construct(SettingsRepositoryInterface $inner) + public function __construct(SettingsRepositoryInterface $inner, DefaultSettingsManager $defaultSettingsManager) { $this->inner = $inner; + $this->defaultSettingsManager = $defaultSettingsManager; } public function all(): array @@ -36,13 +39,15 @@ public function all(): array public function get($key, $default = null) { + $value = $this->defaultSettingsManager->get($key, $default); + if (array_key_exists($key, $this->cache)) { - return $this->cache[$key]; - } elseif (! $this->isCached) { - return Arr::get($this->all(), $key, $default); + $value = $this->cache[$key]; + } else if (! $this->isCached) { + $value = Arr::get($this->all(), $key, $value); } - return $default; + return $value; } public function set($key, $value) diff --git a/src/Settings/SettingsServiceProvider.php b/src/Settings/SettingsServiceProvider.php index 2aa7ade40b7..c596b426743 100644 --- a/src/Settings/SettingsServiceProvider.php +++ b/src/Settings/SettingsServiceProvider.php @@ -26,11 +26,14 @@ class SettingsServiceProvider extends AbstractServiceProvider */ public function register() { + $this->app->singleton(DefaultSettingsManager::class); + $this->app->singleton(SettingsRepositoryInterface::class, function () { return new MemoryCacheSettingsRepository( new DatabaseSettingsRepository( $this->app->make(ConnectionInterface::class) - ) + ), + $this->app->make(DefaultSettingsManager::class) ); }); diff --git a/tests/integration/extenders/SettingsTest.php b/tests/integration/extenders/SettingsTest.php index 53009257e8a..b04269d71d5 100644 --- a/tests/integration/extenders/SettingsTest.php +++ b/tests/integration/extenders/SettingsTest.php @@ -174,6 +174,47 @@ public function custom_setting_callback_works_on_default_value() $this->assertArrayHasKey('customPrefix.unavailableCustomSetting2', $payload['data']['attributes']); $this->assertEquals('defaultModified', $payload['data']['attributes']['customPrefix.unavailableCustomSetting2']); } + + /** + * @test + */ + public function custom_setting_default_prioritizes_extender() + { + $this->extend( + (new Extend\Settings()) + ->serializeToForum('customPrefix.unavailableCustomSetting3', 'custom-prefix.unavailable_custom_setting3') + ->default('custom-prefix.unavailable_custom_setting3', 'extenderDefault') + ); + + $this->prepDb(); + + $value = $this->app() + ->getContainer() + ->make('flarum.settings') + ->get('custom-prefix.unavailable_custom_setting3', 'defaultParameterValue'); + + $this->assertEquals('extenderDefault', $value); + } + + /** + * @test + */ + public function custom_setting_default_falls_back_to_parameter() + { + $this->extend( + (new Extend\Settings()) + ->serializeToForum('customPrefix.unavailableCustomSetting4', 'custom-prefix.unavailable_custom_setting4') + ); + + $this->prepDb(); + + $value = $this->app() + ->getContainer() + ->make('flarum.settings') + ->get('custom-prefix.unavailable_custom_setting4', 'defaultParameterValue'); + + $this->assertEquals('defaultParameterValue', $value); + } } class CustomInvokableClass diff --git a/tests/unit/Settings/MemoryCacheSettingsRepositoryTest.php b/tests/unit/Settings/MemoryCacheSettingsRepositoryTest.php index 4011e4d6bd4..efb69a02f0e 100644 --- a/tests/unit/Settings/MemoryCacheSettingsRepositoryTest.php +++ b/tests/unit/Settings/MemoryCacheSettingsRepositoryTest.php @@ -9,6 +9,7 @@ namespace Flarum\Tests\unit\Settings; +use Flarum\Settings\DefaultSettingsManager; use Flarum\Settings\MemoryCacheSettingsRepository; use Flarum\Settings\SettingsRepositoryInterface; use Flarum\Tests\unit\TestCase; @@ -17,12 +18,14 @@ class MemoryCacheSettingsRepositoryTest extends TestCase { private $baseRepository; + private $defaultSettingsManager; private $repository; protected function setUp(): void { $this->baseRepository = m::mock(SettingsRepositoryInterface::class); - $this->repository = new MemoryCacheSettingsRepository($this->baseRepository); + $this->defaultSettingsManager = m::mock(DefaultSettingsManager::class); + $this->repository = new MemoryCacheSettingsRepository($this->baseRepository, $this->defaultSettingsManager); } public function test_it_should_return_all_settings_when_not_cached() @@ -36,6 +39,7 @@ public function test_it_should_return_all_settings_when_not_cached() public function test_it_should_retrieve_a_specific_value() { $this->baseRepository->shouldReceive('all')->once()->andReturn(['key1' => 'value1', 'key2' => 'value2']); + $this->defaultSettingsManager->shouldReceive('get')->twice(); $this->assertEquals('value2', $this->repository->get('key2')); $this->assertEquals('value2', $this->repository->get('key2')); // Assert twice to ensure we hit the cache @@ -44,6 +48,7 @@ public function test_it_should_retrieve_a_specific_value() public function test_it_should_set_a_key_value_pair() { $this->baseRepository->shouldReceive('set')->once(); + $this->defaultSettingsManager->shouldReceive('get')->once(); $this->repository->set('key', 'value');