From 3fcaf55d02c124b05d1aa3028e5eb8a69c81a7f1 Mon Sep 17 00:00:00 2001 From: Kevin Papst Date: Mon, 22 Dec 2025 17:55:48 +0100 Subject: [PATCH] merge default currency settings (#5739) --- migrations/Version20251214160001.php | 2 ++ phpstan.neon | 20 ------------- src/Configuration/SystemConfiguration.php | 30 ++++++++++++------- src/Controller/ActivityController.php | 4 +-- src/Controller/ProjectController.php | 4 +-- .../SystemConfigurationController.php | 11 +++---- src/Customer/CustomerService.php | 2 +- src/DependencyInjection/Configuration.php | 3 +- .../UserPreferenceSubscriber.php | 2 +- .../Configuration/SystemConfigurationTest.php | 10 +++---- tests/Controller/ProfileControllerTest.php | 2 +- .../SystemConfigurationControllerTest.php | 7 +---- .../DependencyInjection/ConfigurationTest.php | 3 +- tests/phpstan.neon | 10 ------- translations/tasks.ca.xlf | 2 +- 15 files changed, 41 insertions(+), 71 deletions(-) diff --git a/migrations/Version20251214160001.php b/migrations/Version20251214160001.php index 79bda3e08..087d14b4e 100644 --- a/migrations/Version20251214160001.php +++ b/migrations/Version20251214160001.php @@ -30,6 +30,8 @@ final class Version20251214160001 extends AbstractMigration // used to count the tags for the dropdown (filter and timesheet edit) $table->addIndex(['visible'], 'IDX_27CAF54C7AB0E859'); } + // deleted in this release + $this->addSql("DELETE from kimai2_configuration where name = 'defaults.user.language'"); } public function down(Schema $schema): void diff --git a/phpstan.neon b/phpstan.neon index e48adcb5a..cc2e74f3d 100644 --- a/phpstan.neon +++ b/phpstan.neon @@ -584,11 +584,6 @@ parameters: count: 1 path: src/Configuration/SystemConfiguration.php - - - message: "#^Method App\\\\Configuration\\\\SystemConfiguration\\:\\:getCustomerDefaultCurrency\\(\\) should return string but returns bool\\|float\\|int\\|string\\|null\\.$#" - count: 1 - path: src/Configuration/SystemConfiguration.php - - message: "#^Method App\\\\Configuration\\\\SystemConfiguration\\:\\:getCustomerDefaultTimezone\\(\\) should return string\\|null but returns bool\\|float\\|int\\|string\\|null\\.$#" count: 1 @@ -599,21 +594,6 @@ parameters: count: 1 path: src/Configuration/SystemConfiguration.php - - - message: "#^Method App\\\\Configuration\\\\SystemConfiguration\\:\\:getUserDefaultCurrency\\(\\) should return string but returns bool\\|float\\|int\\|string\\|null\\.$#" - count: 1 - path: src/Configuration/SystemConfiguration.php - - - - message: "#^Method App\\\\Configuration\\\\SystemConfiguration\\:\\:getUserDefaultLanguage\\(\\) should return string but returns bool\\|float\\|int\\|string\\|null\\.$#" - count: 1 - path: src/Configuration/SystemConfiguration.php - - - - message: "#^Method App\\\\Configuration\\\\SystemConfiguration\\:\\:getUserDefaultTheme\\(\\) should return string\\|null but returns bool\\|float\\|int\\|string\\|null\\.$#" - count: 1 - path: src/Configuration/SystemConfiguration.php - - message: "#^Method App\\\\Configuration\\\\SystemConfiguration\\:\\:getUserDefaultTimezone\\(\\) should return string\\|null but returns bool\\|float\\|int\\|string\\|null\\.$#" count: 1 diff --git a/src/Configuration/SystemConfiguration.php b/src/Configuration/SystemConfiguration.php index 0dbfd485d..735fca273 100644 --- a/src/Configuration/SystemConfiguration.php +++ b/src/Configuration/SystemConfiguration.php @@ -323,11 +323,6 @@ final class SystemConfiguration return $this->find('defaults.customer.timezone'); } - public function getCustomerDefaultCurrency(): string - { - return $this->find('defaults.customer.currency'); - } - public function getCustomerDefaultCountry(): string { return $this->find('defaults.customer.country'); @@ -340,20 +335,35 @@ final class SystemConfiguration return $this->find('defaults.user.timezone'); } - public function getUserDefaultTheme(): ?string + public function getUserDefaultTheme(): string { - return $this->find('defaults.user.theme'); + return $this->getString('defaults.user.theme', 'auto'); } public function getUserDefaultLanguage(): string { - return $this->find('defaults.user.language'); + return $this->getString('defaults.user.language', 'en'); } - // TODO this is only used to display the hourly rate in the user profile + public function getDefaultCurrency(): string + { + return $this->getString('defaults.customer.currency', 'EUR'); + } + + /** + * @deprecated use getDefaultCurrency() instead + */ + public function getCustomerDefaultCurrency(): string + { + return $this->getDefaultCurrency(); + } + + /** + * @deprecated use getDefaultCurrency() instead + */ public function getUserDefaultCurrency(): string { - return $this->find('defaults.user.currency'); + return $this->getDefaultCurrency(); } // ========== Timesheet configurations ========== diff --git a/src/Controller/ActivityController.php b/src/Controller/ActivityController.php index 0742d436e..5f0f070f6 100644 --- a/src/Controller/ActivityController.php +++ b/src/Controller/ActivityController.php @@ -111,7 +111,7 @@ final class ActivityController extends AbstractController 'page_setup' => $page, 'dataTable' => $table, 'metaColumns' => $metaColumns, - 'defaultCurrency' => $configuration->getCustomerDefaultCurrency(), + 'defaultCurrency' => $configuration->getDefaultCurrency(), 'now' => $this->getDateTimeFactory()->createDateTime(), ]); } @@ -452,7 +452,7 @@ final class ActivityController extends AbstractController */ private function createEditForm(Activity $activity, SystemConfiguration $configuration): FormInterface { - $currency = $configuration->getCustomerDefaultCurrency(); + $currency = $configuration->getDefaultCurrency(); $url = $this->generateUrl('admin_activity_create'); if ($activity->getProject()?->getId() !== null) { $url = $this->generateUrl('admin_activity_create_with_project', ['project' => $activity->getProject()->getId()]); diff --git a/src/Controller/ProjectController.php b/src/Controller/ProjectController.php index cb0cf69c3..940c5c436 100644 --- a/src/Controller/ProjectController.php +++ b/src/Controller/ProjectController.php @@ -177,7 +177,7 @@ final class ProjectController extends AbstractController { $project = $projectService->createNewProject($customer); - $editForm = $this->createEditForm($project, $configuration->getCustomerDefaultCurrency()); + $editForm = $this->createEditForm($project, $configuration->getDefaultCurrency()); $editForm->handleRequest($request); if ($editForm->isSubmitted() && $editForm->isValid()) { @@ -440,7 +440,7 @@ final class ProjectController extends AbstractController { $projectService->loadMetaFields($project); - $editForm = $this->createEditForm($project, $configuration->getCustomerDefaultCurrency()); + $editForm = $this->createEditForm($project, $configuration->getDefaultCurrency()); $editForm->handleRequest($request); if ($editForm->isSubmitted() && $editForm->isValid()) { diff --git a/src/Controller/SystemConfigurationController.php b/src/Controller/SystemConfigurationController.php index 9355a274a..8be174906 100644 --- a/src/Controller/SystemConfigurationController.php +++ b/src/Controller/SystemConfigurationController.php @@ -467,10 +467,6 @@ final class SystemConfigurationController extends AbstractController ->setLabel('country') ->setType(CountryType::class) ->setOptions(['help' => 'default_value_new']), - (new Configuration('defaults.customer.currency')) - ->setLabel('currency') - ->setType(CurrencyType::class) - ->setOptions(['help' => 'default_value_new']), (new Configuration('customer.choice_pattern')) ->setLabel('choice_pattern') ->setType(CustomerTypePatternType::class), @@ -542,9 +538,6 @@ final class SystemConfigurationController extends AbstractController ->setLabel('skin') ->setType(SkinType::class) ->setOptions(['help' => 'default_value_new']), - (new Configuration('defaults.user.currency')) - ->setLabel('currency') - ->setType(CurrencyType::class), (new Configuration('theme.avatar_url')) ->setRequired(false) ->setLabel('theme.avatar_url') @@ -617,6 +610,10 @@ final class SystemConfigurationController extends AbstractController ->setTranslationDomain('system-configuration') ->setRequired(false) ->setType(TextType::class), + (new Configuration('defaults.customer.currency')) + ->setLabel('currency') + ->setType(CurrencyType::class) + ->setOptions(['help' => 'Can be overwritten per customer']), (new Configuration('company.financial_year')) ->setTranslationDomain('system-configuration') ->setRequired(false) diff --git a/src/Customer/CustomerService.php b/src/Customer/CustomerService.php index aedc02041..d03fb1bad 100644 --- a/src/Customer/CustomerService.php +++ b/src/Customer/CustomerService.php @@ -55,7 +55,7 @@ final class CustomerService $customer = new Customer($name); $customer->setTimezone($this->getDefaultTimezone()); $customer->setCountry($this->configuration->getCustomerDefaultCountry()); - $customer->setCurrency($this->configuration->getCustomerDefaultCurrency()); + $customer->setCurrency($this->configuration->getDefaultCurrency()); $customer->setNumber($this->calculateNextCustomerNumber()); $this->loadMetaFields($customer); diff --git a/src/DependencyInjection/Configuration.php b/src/DependencyInjection/Configuration.php index 0dd86ac14..7733bc5a8 100644 --- a/src/DependencyInjection/Configuration.php +++ b/src/DependencyInjection/Configuration.php @@ -625,8 +625,7 @@ final class Configuration implements ConfigurationInterface ->children() ->scalarNode('timezone')->defaultNull()->end() ->scalarNode('language')->defaultValue(User::DEFAULT_LANGUAGE)->end() - ->scalarNode('theme')->defaultValue('default')->end() - ->scalarNode('currency')->defaultValue(Customer::DEFAULT_CURRENCY)->end() + ->scalarNode('theme')->defaultValue('auto')->end() ->end() ->end() ->end() diff --git a/src/EventSubscriber/UserPreferenceSubscriber.php b/src/EventSubscriber/UserPreferenceSubscriber.php index 934a66c5a..182a9504b 100644 --- a/src/EventSubscriber/UserPreferenceSubscriber.php +++ b/src/EventSubscriber/UserPreferenceSubscriber.php @@ -60,7 +60,7 @@ final class UserPreferenceSubscriber implements EventSubscriberInterface if ($this->voter->isGranted('hourly-rate', $user)) { $enableHourlyRate = true; - $hourlyRateOptions = ['currency' => $this->systemConfiguration->getUserDefaultCurrency()]; + $hourlyRateOptions = ['currency' => $this->systemConfiguration->getDefaultCurrency()]; } return [ diff --git a/tests/Configuration/SystemConfigurationTest.php b/tests/Configuration/SystemConfigurationTest.php index c1382bb26..5463e3c2a 100644 --- a/tests/Configuration/SystemConfigurationTest.php +++ b/tests/Configuration/SystemConfigurationTest.php @@ -19,8 +19,8 @@ use PHPUnit\Framework\TestCase; class SystemConfigurationTest extends TestCase { /** - * @param array $settings - * @param array $loaderSettings + * @param array> $settings + * @param array $loaderSettings * @return SystemConfiguration */ protected function getSut(array $settings, array $loaderSettings = []): SystemConfiguration @@ -207,12 +207,11 @@ class SystemConfigurationTest extends TestCase { $sut = $this->getSut($this->getDefaultSettings(), []); self::assertEquals('Europe/London', $sut->getCustomerDefaultTimezone()); - self::assertEquals('GBP', $sut->getCustomerDefaultCurrency()); + self::assertEquals('GBP', $sut->getDefaultCurrency()); self::assertEquals('FR', $sut->getCustomerDefaultCountry()); self::assertEquals('foo/bar', $sut->getUserDefaultTimezone()); self::assertEquals('blue', $sut->getUserDefaultTheme()); self::assertEquals('IT', $sut->getUserDefaultLanguage()); - self::assertEquals('USD', $sut->getUserDefaultCurrency()); self::assertNull($sut->getFinancialYearStart()); } @@ -220,12 +219,11 @@ class SystemConfigurationTest extends TestCase { $sut = $this->getSut($this->getDefaultSettings(), $this->getDefaultLoaderSettings()); self::assertEquals('Russia/Moscov', $sut->getCustomerDefaultTimezone()); - self::assertEquals('RUB', $sut->getCustomerDefaultCurrency()); + self::assertEquals('RUB', $sut->getDefaultCurrency()); self::assertEquals('FR', $sut->getCustomerDefaultCountry()); self::assertEquals('foo/bar', $sut->getUserDefaultTimezone()); self::assertEquals('blue', $sut->getUserDefaultTheme()); self::assertEquals('IT', $sut->getUserDefaultLanguage()); - self::assertEquals('USD', $sut->getUserDefaultCurrency()); } public function testTimesheetWithoutLoader(): void diff --git a/tests/Controller/ProfileControllerTest.php b/tests/Controller/ProfileControllerTest.php index 74a8c818d..5d433dfef 100644 --- a/tests/Controller/ProfileControllerTest.php +++ b/tests/Controller/ProfileControllerTest.php @@ -449,7 +449,7 @@ class ProfileControllerTest extends AbstractControllerBaseTestCase self::assertEquals($hourlyRateOriginal, $user->getPreferenceValue(UserPreference::HOURLY_RATE)); self::assertNull($user->getPreferenceValue(UserPreference::INTERNAL_RATE)); - self::assertEquals('default', $user->getPreferenceValue(UserPreference::SKIN)); + self::assertEquals('auto', $user->getPreferenceValue(UserPreference::SKIN)); $data = [ UserPreference::TIMEZONE => ['value' => 'America/Creston'], diff --git a/tests/Controller/SystemConfigurationControllerTest.php b/tests/Controller/SystemConfigurationControllerTest.php index a0698d3b6..d29e0608a 100644 --- a/tests/Controller/SystemConfigurationControllerTest.php +++ b/tests/Controller/SystemConfigurationControllerTest.php @@ -208,7 +208,6 @@ class SystemConfigurationControllerTest extends AbstractControllerBaseTestCase 'configuration' => [ ['name' => 'defaults.customer.timezone', 'value' => 'Atlantic/Canary'], ['name' => 'defaults.customer.country', 'value' => 'BB'], - ['name' => 'defaults.customer.currency', 'value' => 'GBP'], ] ] ]); @@ -221,7 +220,6 @@ class SystemConfigurationControllerTest extends AbstractControllerBaseTestCase $configService = $this->getSystemConfiguration(); self::assertEquals('Atlantic/Canary', $configService->find('defaults.customer.timezone')); self::assertEquals('BB', $configService->find('defaults.customer.country')); - self::assertEquals('GBP', $configService->find('defaults.customer.currency')); } public function testUpdateCustomerConfigWithSingleParam(): void @@ -236,7 +234,6 @@ class SystemConfigurationControllerTest extends AbstractControllerBaseTestCase 'configuration' => [ ['name' => 'defaults.customer.timezone', 'value' => 'Atlantic/Canary'], ['name' => 'defaults.customer.country', 'value' => 'BB'], - ['name' => 'defaults.customer.currency', 'value' => 'GBP'], ] ] ]); @@ -254,7 +251,7 @@ class SystemConfigurationControllerTest extends AbstractControllerBaseTestCase $configService = $this->getSystemConfiguration(); self::assertNull($configService->find('defaults.user.timezone')); - self::assertEquals('default', $configService->find('defaults.user.theme')); + self::assertEquals('auto', $configService->find('defaults.user.theme')); self::assertEquals('en', $configService->find('defaults.user.language')); $form = $client->getCrawler()->filter('form[name=system_configuration_form_user]')->form(); @@ -290,14 +287,12 @@ class SystemConfigurationControllerTest extends AbstractControllerBaseTestCase 'configuration' => [ ['name' => 'defaults.customer.timezone', 'value' => 'XX'], ['name' => 'defaults.customer.country', 'value' => 1], - ['name' => 'defaults.customer.currency', 'value' => 'XXX'], ] ] ], [ '#system_configuration_form_customer_configuration_0_value', '#system_configuration_form_customer_configuration_1_value', - '#system_configuration_form_customer_configuration_2_value', ] ); } diff --git a/tests/DependencyInjection/ConfigurationTest.php b/tests/DependencyInjection/ConfigurationTest.php index 1bd2bf014..435aac8da 100644 --- a/tests/DependencyInjection/ConfigurationTest.php +++ b/tests/DependencyInjection/ConfigurationTest.php @@ -364,8 +364,7 @@ class ConfigurationTest extends TestCase 'user' => [ 'timezone' => null, 'language' => 'en', - 'theme' => 'default', - 'currency' => 'EUR', + 'theme' => 'auto', ], ], 'permissions' => [ diff --git a/tests/phpstan.neon b/tests/phpstan.neon index 3f0ddfc52..fad2467b0 100644 --- a/tests/phpstan.neon +++ b/tests/phpstan.neon @@ -426,16 +426,6 @@ parameters: count: 1 path: Configuration/SamlConfigurationTest.php - - - message: "#^Method App\\\\Tests\\\\Configuration\\\\SystemConfigurationTest\\:\\:getSut\\(\\) has parameter \\$loaderSettings with no value type specified in iterable type array\\.$#" - count: 1 - path: Configuration/SystemConfigurationTest.php - - - - message: "#^Method App\\\\Tests\\\\Configuration\\\\SystemConfigurationTest\\:\\:getSut\\(\\) has parameter \\$settings with no value type specified in iterable type array\\.$#" - count: 1 - path: Configuration/SystemConfigurationTest.php - - message: "#^Cannot call method getId\\(\\) on App\\\\Entity\\\\Activity\\|null\\.$#" count: 4 diff --git a/translations/tasks.ca.xlf b/translations/tasks.ca.xlf index 0ef0032fc..73a90880c 100644 --- a/translations/tasks.ca.xlf +++ b/translations/tasks.ca.xlf @@ -5,7 +5,7 @@ - + report_tasks_assigned Tasques per usuari