0

I developed a custom plugin with the following structure in my folders:

wp-content
--- plugins
------ my-plugin
--------- languages
------------ po and mo files
--------- my-plugin.php

I internationalized it, and the translations all worked successfully. Now, I need that plugin to be a must-use plugin, by using the following structure:

wp-content
--- mu-plugins
------ my-plugin
--------- languages
------------ po and mo files
------ my-plugin.php

(The main plugin file has to be placed directly into the mu-plugins directory to be executed, from what I learned).

I now corrected all the paths in my main plugin file, due to the slight change of the location of the main plugin file (not inside the my-plugin folder anymore, but inside the wp-content/mu-plugins folder, as explained above), and all my functionalities are working, except from the programmed internationalization. I don't get what I'm still missing. Below's what I did:

Code in main plugin file when it was still a normal plugin, with localizations working:

// Callback loading the textdomain 'my-plugin', defined as such in header of main plugin file
public function my_plugin_load_plugin_textdomain() {
      load_plugin_textdomain(
        'my-plugin',
        false,
        basename( dirname( __FILE__ ) ).'//languages/'
      );
}

// Hook of it
add_action(
        'plugins_loaded',
        array( $this, 'my_plugin_load_plugin_textdomain' )
      );

Here everything worked without any problem (I coded my whole main plugin file inside a class, that's why you have array( $this, callback ) above). When switching to a mu-plugin, I tried:

// Callback loading the textdomain 'my-plugin', defined as such in header of main plugin file
public function my_plugin_load_muplugin_textdomain() {
      load_muplugin_textdomain(
        'my-plugin',
        'my-plugin/languages'
      );
}

// Hook of it
add_action(
        'muplugins_loaded',
        array( $this, 'my_plugin_load_muplugin_textdomain' )
      );

I.E.:

  1. changed the function called in the callback from load_plugin_textdomain() to load_muplugin_textdomain(), and adapted parameters as above.

  2. Changed action hook from plugins_loaded to muplugins_loaded

  3. Changed Domain Path in main plugin file header from /languages to /my-muplugin/languages

Yet, the localization of my mu plugin is still not working. I rechecked the locales as well, and I'm using the correct ones (for example, when I change the users language in the wp admin from german to english(UK), my translation file named my-plugin-en_GB.mo is not applied, and everything still appears in german).

Help??

7
  • Would it not be easier to keep it as a plugin, then write an mu plugin that filters the activated plugins so it cannot be removed or deactivated? Or better yet network activate the plugin if it's a multisite? plugins-mu isn't really intended for full blown plugins, think of it more like single file dropins
    – Tom J Nowell
    Jun 17, 2020 at 13:29
  • Well I only needed to employ steps 1-3 mentioned above, by using the init action hook instead of the one I wrote above; and all that's done in like 2 mins (wish I had known that about the init hook earlier). So I'm not sure what you mean by "easier" ..? For me, what you're telling me sounds much more complicated, but may due to my lack of experience in doing what you say. Also, be aware that my plugin doesn't do anything supercomplex, only basic js, ajax, php, and SQL db operations. So I wonder about the benefits of your strategy, if you could may be a lil more precise? It sounds interesting!
    – DevelJoe
    Jun 17, 2020 at 16:12
  • Also, I just noticed that there is actually an additional tab for "file dropins" under the plugins tab in the wp admin; I feel like that's what you're talking about? The thing is that I absolutely need the corresponding js etc. functions to be constantly working, so I cannot take any risk for them to be deactivated, except by explicit FTP deletion. That's why I focused on this mu-plugin switch; just to be more precise with my explanations.
    – DevelJoe
    Jun 17, 2020 at 16:19
  • No, dropins are things like object-cache.php etc that live in the root of wp-content, you can remove the deactivate link via wordpress.stackexchange.com/questions/253902/… you can also network activate it so that only super admins can deactivate. You can also keep the plugin in the plugins folder and load it via mu-plugins, then it won't matter if it's active or not. You can also override the active_plugins option
    – Tom J Nowell
    Jun 17, 2020 at 16:28
  • You can also auto-activate it via code wordpress.stackexchange.com/questions/4041/…
    – Tom J Nowell
    Jun 17, 2020 at 16:31

2 Answers 2

0

Using the init action hook instead of the muplugins_loaded action hook did the job! But I wonder if that's the proper way of doing it..?

0

Determining locale is a crucial step in loading text domain because it decides which .mo file should be loaded.

If we load plugin with muplugins_loaded then current_user_id will be 0, hence .mo will be default language

If we load plugin with init then current_user_id will be the logged_in user id, hence .mo will be user's locale language

This is how it goes when we use load_muplugin_textdomain function

  1. It determines the locale language.
  2. Then it tries to load .mo file like domain-locale.mo
  3. If your site's default language is en_US, so your default .mo and .po files should be saved like my-plugin-en_US.mo and my-plugin-en_US.po
  4. If this is not found then the textdomain won't load.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

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