WordPress.org

Make WordPress Core

Opened 3 years ago

Closed 17 months ago

#27999 closed defect (bug) (wontfix)

Problem with embedding WordPress Multisite in other PHP applications caused by path difference in ms-settings

Reported by: ivanbajalovic Owned by:
Milestone: Priority: normal
Severity: major Version: 3.9
Component: Networks and Sites Keywords: reporter-feedback close dev-feedback
Focuses: multisite Cc:

Description

I have a website built with Zend FW, and there is a feature for admins to create a new multisite from website admin. As I updated to WP 3.9 I keep getting the Database connection error.

The problem is caused by different paths of blog sites and my application admin path.

I wrote a detailed explanation in discussion: http://wordpress.org/support/topic/wordpress-39-multisite-db-connection-error?replies=6#post-5493763 and http://wordpress.org/support/topic/wordpress-39-multisite-db-connection-error?replies=6#post-5493788

Change History (13)

This ticket was mentioned in IRC in #wordpress-dev by nacin. View the logs.


3 years ago

#2 @jeremyfelt
3 years ago

Hi @ivanbajalovic - I've followed up on the support forum thread. Let's try to establish the issue there and we can continue this ticket as need be.

#3 follow-up: @jeremyfelt
3 years ago

  • Keywords reporter-feedback close added

I think I can reproduce this now.

  1. Install WordPress 3.8.3 in a subfolder /var/www/wordpress/wp38/
  2. Configure multisite. Because WP is in a subfolder, only subdirectories can be chosen.
  3. Setup a script in /var/www/default/index.php to include ../../wordpress/wp38/wp-load.php and do something provided by multisite:
    include '../../wordpress-default/wp38/wp-load.php';
    echo get_user_count();
    
  4. Load that page and see the output.
  5. Upgrade to WordPress 3.9
  6. Load that page and get a database error.

I cannot reproduce this unless WordPress is installed in a subfolder.

Because we now determine the global $path solely on $_SERVER['REQUEST_URI'], it ends up being completely different than the network path of the multisite installation. This is technically different behavior from WordPress 3.8.3, but it is worth noting that the path process there can result in some very unpredictable paths as well due to the logic around $blogname that is used to build the final result.

As an example, my request for http://foo.bar/custom/index.php that includes wp-load.php resulted in a final $blogname of om because WP 3.8.3 strips path from blogname before looking up site details.

I think that this should be a wontfix. That it's worked thus far seems much more accidental than anything.

The multisite bootstrap is different than the standard WordPress bootstrap in that the request needs to be parsed to find a site and network. If it is being loaded inside another application, the effort should be done there to ensure that $current_site and $current_blog are set properly in sunrise.php or the custom application itself. As long as these are set, there is no trouble loading wp-load.php with multisite enabled.

It is also worth noting that faking the request with $_SERVER['REQUEST_URI'] = '/wp38/'; will also work as a shorter term solution.

#4 follow-up: @ivanbajalovic
3 years ago

Jeremy, many thanks for your effort. And yes, that is the way to reproduce the error.

I tried the hack with overriding $_SERVER['REQUEST_URI'] and it is working. It's not the best solution, but it will help for now.

However, I did not quite understood your sentence "That it's worked thus far seems much more accidental than anything.". Does it mean that the ability to include WP inside an app was not planned to exist, that that was a side-effect?

#5 in reply to: ↑ 4 @jeremyfelt
3 years ago

Replying to ivanbajalovic:

However, I did not quite understood your sentence "That it's worked thus far seems much more accidental than anything.". Does it mean that the ability to include WP inside an app was not planned to exist, that that was a side-effect?

I think the accidental portion is the parsing of the request in ms-settings.php to find the proper network and site to boot when WP is included in an app when $current_blog and $current_site are not predefined.

I can't answer the planned/side-effect question, but outside of the logic controlling that lookup, it seems that everything loads as one would expect.

#6 @alexfurr
3 years ago

  • Severity changed from normal to major

Hi,

I have EXACTLY this problem and it has taken me 3 hours to finally find this ticket. Thank you! Glad I'm not going mad and it IS a known issue.

Where exactly , and how exactly do I overwrite the:
"request_uri"
as described above to fix this? Currently I have a broken site. I'll have to downgrade to 3.8.4

I'm bumping this up to 'Major' as upgrading to anything above 3.8.4 completely breaks my site i.e. running multisite in a subfolder alongside other PHP pages in the root. This is a student blog setup and we have approx 8000 people this is affecting :(

#7 @jeremyfelt
3 years ago

Hi @alexfurr, sorry to hear about the site troubles.

Multisite is different from a single site installation in that it relies on the requested URL (by default) to determine what network and site to load from the database. This is the same when included from a different application. There are two ways around this.

  1. In the custom application, before loading wp-load.php, specify $_SERVER['REQUEST_URI'] = '/path-to-lookup/'; so that WordPress knows how to direct the request. Something similar is done in WP-CLI before loading WordPress.
  2. The alternative is to use a custom sunrise.php file in your wp-content/ directory. This file allows any number of things to happen at the beginning of the WordPress multisite bootstrap process. The major use case for this file is to handle the lookup of site and network data so that WordPress will skip its own lookup process in ms-settings.php. IMO, this ends up being the more versatile solution as you can setup your $current_site and $current_blog data completely.

Overall, while this process was tightened up in 3.9, I don't think it is a bug to fix as the behavior was not intentional before.

#8 @alexfurr
3 years ago

Jeremy, THANK YOU.
I know this isn't a troubleshooting forum so apologies for another query.
I've implemented sunrise.php as you suggest and it DOES now work with the rest of the non WP pages. YAY!

The fix I added was simply

$_SERVER['REQUEST_URI'] = '/sites/;

; into the sunrise.php folder.

However, now it seems that EVERY wordpress page reirects to the root (/sites/)
i.e. "/sites/test-page-2/" reverts to "/sites/"
Did I add the wrong code? Clearly I must have done! What is the correct code to add to the sunrise.php? You mention $current_site and $current_blog but not sure how to apply that.

So one step forward, one step back!
Thanks in advance,
Alex

#9 @alexfurr
3 years ago

FIXED!
I'll post the problem / solution in full in case it helps anyone else. Thanks to all who aided me.

The Problem
Running custom php pages that are including the wp-blog-header.php break when upgrading to WP 3.9. This only occurs if you are running a multisite in a subfolder e.g. "www.mysite.com/sites/"

The Solution

  1. Create (if not already exist) the sunrise.php page in the wp-content folder.
  2. Add define( 'SUNRISE', 'on' ); to the wp-config file
  3. Add the following code to the sunrise.php file:
if (strpos($_SERVER['REQUEST_URI'],'/sites') === false)
{
$_SERVER['REQUEST_URI'] = '/sites/';
}

This way it only overrides the request_uri on NON wordpress pages, which enables you to load the wp-blog-header.php correctly and also prevents all regular WP pages from redirecting to the root.

Hope that helps someone else.
Alex

#10 @nacin
3 years ago

#29678 was marked as a duplicate.

#11 @alawatsakima
23 months ago

Bug is still present in WordPress 4.2.2.

Also, solution listed by @alexfurr still works in 4.2.2.

#12 @chriscct7
19 months ago

  • Keywords dev-feedback added

#13 in reply to: ↑ 3 @jeremyfelt
17 months ago

  • Milestone Awaiting Review deleted
  • Resolution set to wontfix
  • Status changed from new to closed

Per my comment above, I'm going to close this as wontfix.

It's still possible to include WordPress multisite in another application, but because REQUEST_URI will likely be different than the domain/path used to lookup information in the wp_blogs table, a custom sunrise.php should be used to populate $current_blog and $current_site with the correct site and network objects.

Note: See TracTickets for help on using tickets.