This is the technical support forum for WPML - the multilingual WordPress plugin.

Everyone can read, but only WPML clients can post here. WPML team is replying on the forum 6 days per week, 22 hours per day.

This thread is resolved. Here is a description of the problem and solution.

Problem: trying to use WPML in a hosting environment that has multiple PHP instances.

Solution: version 4.0.6. introduced the filter hook

wpml_ls_template_paths

that solves the issue

This topic contains 8 replies, has 2 voices.

Last updated by Laura 1 year ago.

Assigned support staff: Laura.

Author Posts
August 11, 2018 at 12:38 pm #2636395

Idealien

I am trying to:
Use WPML in a hosting environment that has multiple PHP instances. When accessing the front-end of the site (either with a default WP theme like 2017 or custom for the site), depending on which instance receives the request to serve the PHP the logs contain the following error. I've simplified the log paths so that you can understand the two instances as being named instance123 and instance456.

Warning: file_exists(): open_basedir restriction in effect. File(/server/path/to/instance123/domain/app/plugins/sitepress-multilingual-cms/templates/language-switchers/legacy-dropdown) is not within the allowed path(s): (/server/path/to/instance456/domain/app:/server/path/to/shared/nfs/domain/wp/uploads:/tmp) in /server/path/to/instance123/domain/app/web/contenthub/app/plugins/sitepress-multilingual-cms/classes/language-switcher/class-wpml-ls-template.php on line 188

The issue relates to:
1) Part of our environment configuration using open_basedir to secure the files that can be accessed by PHP to a set of directory trees particular to that instance and not everything on server. This set is listed in the 'allowed paths' portion of the error message above.

2) When / how the template file list is loaded through the after_setup_theme action as a part of every page load. Specifically how the transient/option wpml_language_switcher_template_objects is updated within sitepress-multilingual-cms plugin function classes/language-switcher/class-wpml-ls-templates.php/init_available_templates function. Whether because of admin ui refresh, or if the transient/option does not exist, the paths stored will be specific to a specific instance. Subsequent page requests served from other instances get the error message above.

3) Of secondary issue is the file_exists check from sitepress-multilingual-cms plugin function classes/language-switcher/class-wpml-ls-template.php function is_path_valid that is encountering the open_basedir restriction.

The potential resolutions to this I have identified:
A) Change when wpml_ls_directories_to_scan filter occurs to be AFTER the inclusion of $wpml_core_path, $theme_path, $child_theme_path, $uploads_path. This would let all the existing logic of the transient continue, but I write a specific filter to re-write the portion of the paths stored which is instance specific. Because wpml_ls_directories_to_scan occurs before the additional templates are added there is no option to customize.

B) Add a new filter to either the are_template_paths_valid or get_templates_from_transient function that would let the list of template paths be adjusted to be instance specific.

C) Ensure that the template paths use WP core function get_home_path instead of writing the full absolute path into the transient/option. This would require more development and testing than A or B, but have the most performance impact to environments that encounter this issue.

D) [Least Desirable] Add a constant that can let environments decide whether the wpml_language_switcher_template_objects transient is used. Not using it implies that the folder structure will be checked on every page load. But right now, I'm having to investigate de-hooking your after_setup_theme_action to build a custom version which is able to appropriately handle the instance specific logic needed OR maintain a custom fork which is never the right/preferred solution.

August 11, 2018 at 1:36 pm #2636405

Idealien

Working example of solution that is closest to B) in original summary

1) Add new filter to beginning of sitepress-multilingual-cms\classes\language-switcher\class-wpml-ls-template.php function is_path_valid()

$this->template_paths = apply_filters( 'wpml_template_paths_verify', $this->template_paths );

2) An example filter that splits the template based on match against ABSPATH and rebuilds with instance specific paths. get_home_path won't work b/c that requires WP admin context.

add_filter( 'wpml_template_paths_verify', 'wpml_templates_instance_aware', 10, 1);
function wpml_templates_instance_aware( $templates ) {
	echo 'BEFORE:';
	echo "<pre>" . print_r( $templates, true ) . "</pre>";
	if( is_array( $templates ) ) {
		$splitter = 'web/contenthub/';
		$server_path = substr( ABSPATH, 0, -3);
		
		foreach( $templates as $template) {
			if ( false !== strpos( $template, $splitter ) ) {
				$path_elements = explode( $splitter, $template );
				$template = $server_path . $splitter . $path_elements[1];
			}
		}
	}

	echo 'AFTER:';
	echo "<pre>" . print_r( $templates, true ) . "</pre>";
	
	return $templates;
}

Would the addition of such a filter be possible?
Or is there a better approach the devs would recommend?

August 13, 2018 at 2:02 pm #2640137

Laura
Supporter

Languages: English (English ) Italian (Italiano ) Portuguese (Brazil) (Português )

Timezone: Europe/Rome (GMT+02:00)

Hi,

Could you please add your WPML debug information? You can find it in:
WPML -> Support -> click on debug information link
Then you can copy/paste the text you see in the Debug box I'll enable for the next answer.
More information here: http://wpml.org/faq/provide-debug-information-faster-support/

August 14, 2018 at 1:02 am #2641518

Idealien

I have provide the subset of debug information which is relevant/appropriate to the WPML aspect to this issue as it clearly does not relate to other plugins on site or active theme. It is specific to the behaviour of WPML in a multi-instance environment and how the absolute paths are stored in the option wpml_language_switcher_template_objects.

August 14, 2018 at 8:02 am #2642552

Laura
Supporter

Languages: English (English ) Italian (Italiano ) Portuguese (Brazil) (Português )

Timezone: Europe/Rome (GMT+02:00)

Ok, but if I asked the debug information is for a reason. The information you provided does not include, for example, the MySQL version you are using and I need to give a clear picture of your full environment.
Anyway, I'm escalating the issue to our second tier, I'll update you as soon as I have news.

August 15, 2018 at 6:35 pm #2647410

Idealien

FYI: The foreach loop inside the filter example should have the template passed as reference.

foreach( $templates as &$template) {
//...
}

instead of

foreach( $templates as $template) {
//...
}
August 16, 2018 at 7:44 am #2648719

Laura
Supporter

Languages: English (English ) Italian (Italiano ) Portuguese (Brazil) (Português )

Timezone: Europe/Rome (GMT+02:00)

Thanks, I reported this information to the developers.

September 18, 2018 at 8:15 pm #2746470

Idealien

Any chance of an ETA or confirmation that the implementation pattern does fit for a coming release of the plugin? As it is right now I have to maintain a private fork to ensure the filter remains through updates.

October 3, 2018 at 6:29 am #2783552

Laura
Supporter

Languages: English (English ) Italian (Italiano ) Portuguese (Brazil) (Português )

Timezone: Europe/Rome (GMT+02:00)

Hi,

version 4.0.6. introduced the filter hook `wpml_ls_template_paths`that should solve your issue.
Please let me know if this works for you.