diff --git a/app/code/Magento/Store/Model/Store.php b/app/code/Magento/Store/Model/Store.php index 05c762cce5164..4bb376b89d954 100644 --- a/app/code/Magento/Store/Model/Store.php +++ b/app/code/Magento/Store/Model/Store.php @@ -911,6 +911,9 @@ public function setCurrentCurrencyCode($code) : $this->_storeManager->getWebsite()->getDefaultStore()->getDefaultCurrency()->getCode(); $this->_httpContext->setValue(Context::CONTEXT_CURRENCY, $code, $defaultCode); + + // Force reload of current currency on currency code change + $this->unsetData('current_currency'); } return $this; } diff --git a/app/code/Magento/Store/Test/Unit/Model/StoreTest.php b/app/code/Magento/Store/Test/Unit/Model/StoreTest.php index 95c21a95e7643..0dfb0937da75d 100644 --- a/app/code/Magento/Store/Test/Unit/Model/StoreTest.php +++ b/app/code/Magento/Store/Test/Unit/Model/StoreTest.php @@ -819,6 +819,107 @@ public static function currencyCodeDataProvider(): array ]; } + /** + * Test that setCurrentCurrencyCode clears cached currency + * + * @return void + */ + public function testSetCurrentCurrencyCodeClearsCachedCurrency(): void + { + $currencyCodeFirst = 'USD'; + $currencyCodeSecond = 'EUR'; + + $sessionMock = $this->getMockBuilder(SessionManagerInterface::class) + ->getMockForAbstractClass(); + $sessionMock->expects($this->exactly(2)) + ->method('setCurrencyCode') + ->willReturnCallback(function ($code) use ($currencyCodeFirst, $currencyCodeSecond) { + static $callCount = 0; + $callCount++; + if ($callCount === 1) { + $this->assertEquals($currencyCodeFirst, $code); + } else { + $this->assertEquals($currencyCodeSecond, $code); + } + }); + + $httpContextMock = $this->getMockBuilder(\Magento\Framework\App\Http\Context::class) + ->disableOriginalConstructor() + ->getMock(); + + $currencyFactoryMock = $this->getMockBuilder(CurrencyFactory::class) + ->disableOriginalConstructor() + ->getMock(); + + $currencyMockFirst = $this->getMockBuilder(Currency::class) + ->disableOriginalConstructor() + ->getMock(); + $currencyMockFirst->expects($this->any()) + ->method('getCode') + ->willReturn($currencyCodeFirst); + + $currencyMockSecond = $this->getMockBuilder(Currency::class) + ->disableOriginalConstructor() + ->getMock(); + $currencyMockSecond->expects($this->any()) + ->method('getCode') + ->willReturn($currencyCodeSecond); + + $storeManagerMock = $this->getMockBuilder(StoreManagerInterface::class) + ->getMockForAbstractClass(); + $storeManagerMock->expects($this->any()) + ->method('getStore') + ->willReturn(null); + + $websiteMock = $this->getMockBuilder(WebsiteInterface::class) + ->getMockForAbstractClass(); + $websiteMock->expects($this->any()) + ->method('getDefaultStore') + ->willReturnSelf(); + $websiteMock->expects($this->any()) + ->method('getDefaultCurrency') + ->willReturn($currencyMockFirst); + + $storeManagerMock->expects($this->any()) + ->method('getWebsite') + ->willReturn($websiteMock); + + $storeMock = $this->getMockBuilder(Store::class) + ->setConstructorArgs([ + $this->createMock(\Magento\Framework\Model\Context::class), + $this->createMock(\Magento\Framework\Registry::class), + $this->createMock(\Magento\Framework\App\Cache\Type\Config::class), + $this->createMock(\Magento\Framework\Url::class), + $this->requestMock, + $this->createMock(\Magento\Config\Model\ResourceModel\Config\Data::class), + $this->configMock, + $storeManagerMock, + $this->filesystemMock, + $this->createMock(\Magento\Framework\Url\ModifierInterface::class), + $sessionMock, + $httpContextMock, + $this->createMock(\Magento\Framework\App\Config::class), + $currencyFactoryMock + ]) + ->onlyMethods(['getAvailableCurrencyCodes', 'getData', 'unsetData', 'setData']) + ->getMock(); + + $storeMock->expects($this->any()) + ->method('getAvailableCurrencyCodes') + ->willReturn([$currencyCodeFirst, $currencyCodeSecond]); + + // Expect unsetData to be called when currency code changes + $storeMock->expects($this->exactly(2)) + ->method('unsetData') + ->with('current_currency'); + + // First currency change + $storeMock->setCurrentCurrencyCode($currencyCodeFirst); + + // Second currency change - should clear cached currency + $storeMock->setCurrentCurrencyCode($currencyCodeSecond); + } + /** * @param Store $model */