0

I need to update the allowed locale list with my custom language in magento 2.3.3. For that, I have overridden the Magento\Framework\Locale\Config class in my custom module.

di.xml:

<preference for="Magento\Framework\Locale\Config" type="Vendor\Module\Locale\Config" />

Config.php:

<?php

namespace Vendor\Module\Locale;

class Config extends \Magento\Framework\Locale\Config
{
    protected $_test = [
        'es_US'
    ];

    public function __construct(array $data = [])
    {
        $data['allowedLocales'] = $this->_test;
        parent::__construct($data);
    }

}

The problem is both the core and overridden files executing. When I print the variable $this->_allowedLocales, I get the results twice, the first result don't has my custom locale and the second result has my custom locale. What I want here is I need a single result which includes my custom locale. Please see the following result I get

Array
(
    [0] => af_ZA
    [1] => ar_DZ
    [2] => ar_EG
    [3] => ar_KW
    [4] => ar_MA
    [5] => ar_SA
    [6] => az_Latn_AZ
    [7] => be_BY
    [8] => bg_BG
    [9] => bn_BD
    [10] => bs_Latn_BA
    [11] => ca_ES
    [12] => cs_CZ
    [13] => cy_GB
    [14] => da_DK
    [15] => de_AT
    [16] => de_CH
    [17] => de_DE
    [18] => de_LU
    [19] => el_GR
    [20] => en_AU
    [21] => en_CA
    [22] => en_GB
    [23] => en_NZ
    [24] => en_US
    [25] => es_AR
    [26] => es_CO
    [27] => es_PA
    [28] => gl_ES
    [29] => es_CR
    [30] => es_ES
    [31] => es_MX
    [32] => eu_ES
    [33] => es_PE
    [34] => et_EE
    [35] => fa_IR
    [36] => fi_FI
    [37] => fil_PH
    [38] => fr_BE
    [39] => fr_CA
    [40] => fr_CH
    [41] => fr_FR
    [42] => fr_LU
    [43] => gu_IN
    [44] => he_IL
    [45] => hi_IN
    [46] => hr_HR
    [47] => hu_HU
    [48] => id_ID
    [49] => is_IS
    [50] => it_CH
    [51] => it_IT
    [52] => ja_JP
    [53] => ka_GE
    [54] => km_KH
    [55] => ko_KR
    [56] => lo_LA
    [57] => lt_LT
    [58] => lv_LV
    [59] => mk_MK
    [60] => mn_Cyrl_MN
    [61] => ms_MY
    [62] => ms_Latn_MY
    [63] => nl_BE
    [64] => nl_NL
    [65] => nb_NO
    [66] => nn_NO
    [67] => pl_PL
    [68] => pt_BR
    [69] => pt_PT
    [70] => ro_RO
    [71] => ru_RU
    [72] => sk_SK
    [73] => sl_SI
    [74] => sq_AL
    [75] => sr_Cyrl_RS
    [76] => sv_SE
    [77] => sv_FI
    [78] => sw_KE
    [79] => th_TH
    [80] => tr_TR
    [81] => uk_UA
    [82] => vi_VN
    [83] => zh_Hans_CN
    [84] => zh_Hant_HK
    [85] => zh_Hant_TW
    [86] => es_CL
    [87] => lo_LA
    [88] => es_VE
    [89] => en_IE
    [90] => es_BO
)
Array
(
    [0] => af_ZA
    [1] => ar_DZ
    [2] => ar_EG
    [3] => ar_KW
    [4] => ar_MA
    [5] => ar_SA
    [6] => az_Latn_AZ
    [7] => be_BY
    [8] => bg_BG
    [9] => bn_BD
    [10] => bs_Latn_BA
    [11] => ca_ES
    [12] => cs_CZ
    [13] => cy_GB
    [14] => da_DK
    [15] => de_AT
    [16] => de_CH
    [17] => de_DE
    [18] => de_LU
    [19] => el_GR
    [20] => en_AU
    [21] => en_CA
    [22] => en_GB
    [23] => en_NZ
    [24] => en_US
    [25] => es_AR
    [26] => es_CO
    [27] => es_PA
    [28] => gl_ES
    [29] => es_CR
    [30] => es_ES
    [31] => es_MX
    [32] => eu_ES
    [33] => es_PE
    [34] => et_EE
    [35] => fa_IR
    [36] => fi_FI
    [37] => fil_PH
    [38] => fr_BE
    [39] => fr_CA
    [40] => fr_CH
    [41] => fr_FR
    [42] => fr_LU
    [43] => gu_IN
    [44] => he_IL
    [45] => hi_IN
    [46] => hr_HR
    [47] => hu_HU
    [48] => id_ID
    [49] => is_IS
    [50] => it_CH
    [51] => it_IT
    [52] => ja_JP
    [53] => ka_GE
    [54] => km_KH
    [55] => ko_KR
    [56] => lo_LA
    [57] => lt_LT
    [58] => lv_LV
    [59] => mk_MK
    [60] => mn_Cyrl_MN
    [61] => ms_MY
    [62] => ms_Latn_MY
    [63] => nl_BE
    [64] => nl_NL
    [65] => nb_NO
    [66] => nn_NO
    [67] => pl_PL
    [68] => pt_BR
    [69] => pt_PT
    [70] => ro_RO
    [71] => ru_RU
    [72] => sk_SK
    [73] => sl_SI
    [74] => sq_AL
    [75] => sr_Cyrl_RS
    [76] => sv_SE
    [77] => sv_FI
    [78] => sw_KE
    [79] => th_TH
    [80] => tr_TR
    [81] => uk_UA
    [82] => vi_VN
    [83] => zh_Hans_CN
    [84] => zh_Hant_HK
    [85] => zh_Hant_TW
    [86] => es_CL
    [87] => lo_LA
    [88] => es_VE
    [89] => en_IE
    [90] => es_BO
    ***[91] => es_US***
)
2
  • Actually also running into this problem. I can add en_SG just fine using the preference method above or a plugin around (after) getAllowedLocales, works fine for developer mode and allows me to set the store locale to English (Singapore), however the language is not reflected in command line info:language:list or when I try to deploy staitc content for the language in production mode. Some debugging seems it creates the List object (and Config object in constructor) twice, once without and once with the preference, only the first one survives – cygnus digital Jul 28 '20 at 16:52
  • I've since tried setting the additional locales via di.xmlk. Again this works fine in Dev mode but the CLI does not recognize the preference/plugin/di config. It's very strange, like the CLI is loading the base class and "holding on to it" then when its time to run the CLI command it loads the Interceptor or preference class but having already constructed Lists its too late. I also tried preferencing the Magento\Framework\Setup\Lists class to no joy.... – cygnus digital Jul 29 '20 at 12:29
1

Doesn't feel quite right offering this as an answer, as it violates every rule in the book about not touching core code (well not every rule).

I have figured it out I think (please excuse errors, but do point them out!), essentially the above (either a plugin around getAllowedLocales, a preference for a replacement to the Config class or using di.xml to inject $data['allowedLocales'] into the origional Config class) all work for anything using the /index.php bootstrap, the default application we use to view the website.

So in Developer mode (sans any cache) we can use this new locale (as long as its recognized by the root Resource bundle). I am using it to expose en_SG which is a real locale but just not in the $_allowedLocales list.

Problem is bin/magento info:languages:list does not report the language, this is because the CLI bootstrap is different, it essentially runs `Magento\Setup\Application in the command line. This also means it does not pick up the locale when your in Production mode and try to deploy static content.

Now in Magento\Setup\Module there's a function getConfig() that is called on any CLI command, and it loads config files from a hard coded path. One of interest is setup\config\di.config.php which seems to define some preferences for the applications Dependency Injection :

<?php
/**
 * Copyright © Magento, Inc. All rights reserved.
 * See COPYING.txt for license details.
 */

return [
    'di' => [
        'instance' => [
            'preference' => [
                \Laminas\EventManager\EventManagerInterface::class => 'EventManager',
                \Laminas\ServiceManager\ServiceLocatorInterface::class => \Laminas\ServiceManager\ServiceManager::class,
                \Magento\Framework\DB\LoggerInterface::class => \Magento\Framework\DB\Logger\Quiet::class,
                \Magento\Framework\Locale\ConfigInterface::class => \Magento\Framework\Locale\Config::class,
                \Magento\Framework\Filesystem\DriverInterface::class =>
                    \Magento\Framework\Filesystem\Driver\File::class,
                \Magento\Framework\Component\ComponentRegistrarInterface::class =>
                    \Magento\Framework\Component\ComponentRegistrar::class,
            ],
            \Magento\Framework\Setup\Declaration\Schema\SchemaConfig::class => [
                'parameters' => [
                    'connectionScopes' => [
                        'default',
                        'checkout',
                        'sales'
                    ]
                ]
            ],
        ],
    ],
];

Note the preference for the \Magento\Framework\Locale\ConfigInterface. Because this is loaded early in command (before the commands themselves are loaded) this object already exists then the Lists class that takes the ConfigInterface as a parameter and calls getAllowedLocales() on it in its constructor always gets the original one.

The fix, is not a fix, however if I update line :

 \Magento\Framework\Locale\ConfigInterface::class => \Magento\Framework\Locale\Config::class,

with my Preference :

 \Magento\Framework\Locale\ConfigInterface::class => \Vendor\Module\Locale\Config::class,

it all works fine and Magento CLI is aware of my preference.

I'm using v 2.3.5-p1 so not sure if 2.4 fixes this or effects it. If anyone can suggest a safer way to ensure our preference is exposed to Magento\Setup I'm all ears!

Thats all I got to offer apart from maybe just adding it to the vendor\magento\framework\Locale\Config.php file (modify core file so just as bad as above).

I tried adding preference or plugin around Magento\Setup\Module::getConfig() to see if I could update the PHP config array via my module (much safer!) but it would not play fair.

0

In your Config.php file in the class __constructor you're making the following call: parent::__construct($data);. If you take a look at it you will see that the parent constructor merges the existing _allowedLocales and _allowedCurrencies with the array of data you're passing to it (in your case $data).

I'm curious what other locale are you trying to append to the existing set Magento 2 provides (the default set should cover most of them).

P.S. Extending (overwriting) classes not is considered a best practice in M2 but more of a last resort option when it comes adding custom logic.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.