2

I use a custom storage for translations in Symfony2, but I want to make sure that the translations will be loaded only from my storage, and not from other sources (such as Yaml files). How can I disable the standard loaders? In my custom Translator class I have the following code:

   /**
     * {@inheritdoc}
     */
    protected function loadCatalogue($locale)
    {
        $this->initializeCatalogue($locale);
    }

    /**
     * {@inheritdoc}
     */
    protected function initializeCatalogue($locale)
    {
        $this->addLoader('storageLoader', $this->container->get('my.translation.loader'));
        $this->addResource('storageLoader', $this->container->get('storage.getter'), $locale);

        parent::initializeCatalogue($locale);
    }

But in parent::initializeCatalogue($locale); it loads all standard loaders. I found this post, where how I get guy only delete cache files, to make sure that translation getting only from the database, or did I miss something?

Nic Wortel
  • 11,155
  • 6
  • 60
  • 79
nowiko
  • 2,507
  • 6
  • 38
  • 82

1 Answers1

1

You're missing few things to disable standard translation loaders in your app.

Register service

Add to your services your custom translation loader (remember to replace class with your own):

services:
    my.translation.loader.dbext:
        class: YouApp\CommonBundle\Services\MyTranslationLoader
        arguments: [@doctrine.orm.entity_manager]
        tags:
            - { name: translation.loader, alias: dbext}

dbext - is extension of fake messages files (feel free to change it). When symfony tries to load file with such extension, loader will be replaced with your class.

Create fake message files

Last step is to create those fake messages.en.dbext, messages.fr.dbext and other messages.*.dbext files as it is in sf2 documentation:

If you're loading translations from a database, you'll still need a resource file, but it might either be blank or contain a little bit of information about loading those resources from the database. The file is key to trigger the load method on your custom loader.

That should help you in this case.

EDIT:

If you're not using YAML in your service registration, you can go with XML

<?xml version="1.0" encoding="UTF-8" ?>
<container xmlns="http://symfony.com/schema/dic/services"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://symfony.com/schema/dic/services http://symfony.com/schema/dic/services/services-1.0.xsd">
    <services>
        <service
            id="my.translation.loader.dbext"
            class="YouApp\CommonBundle\Services\MyTranslationLoader">
            <tag name="translation.loader" alias="dbext" />
        </service>
    </services>
</container>

or PHP

$container
    ->register('my.translation.loader.dbext', 'YouApp\CommonBundle\Services\MyTranslationLoader')
    ->addTag('translation.loader', array('alias' => 'dbext'))
;
Paweł Tomkiel
  • 1,974
  • 2
  • 21
  • 39
  • @excluded_once - Did it helped? Is everything working as you wanted? – Paweł Tomkiel Mar 27 '15 at 11:21
  • This actually does not disable standard loaders. Translations are loaded with CustomLoader first and then the xliff loder is still used. If there is an xlf file in your translation folder with the same translation you already retrieved from db, your db ttranslation will be overwritten. (I'm using symfony 4.1) – Thomas Baumgartner Jul 11 '18 at 11:14
  • @thomasbaumgartner - this question goes back to 2015, and is about Symfony 2, probably something's changed in 4.1 – Paweł Tomkiel Jul 13 '18 at 17:50
  • @ThomasBaumgartner If you want to override file translations, make sure the extension (and alias) of db translation loader comes after the file translation loader alphabetically (for example .zzz). See this answer https://stackoverflow.com/a/72819017/4553323 for more details – Faizan Akram Dar Jun 30 '22 at 16:21