tmaste
Forum Replies Created
-
Thanks for the follow-up!
I will add the diff here as reference:
@wfpeter I can reproduce this bug also in WP Engine with a fresh WP installation.
This is because Wordfence itself always forces the
WFWAF_STORAGE_ENGINE=mysqlisetting to be used in WP Engine.- Create a new WP Engine site
- Convert the site to WP multisite (e.g. sub-directory network)
- Create a new subsite, so that you have two blogs: the main blog (e.g.
*****.wpenginepowered.com) and the subsite blog (e.g.*****.wpenginepowered.com/subsite) - Install Wordfence to the site
- Result: the subsite blog is a lot slower than the main blog
Testing:
- When I visit the main site URL
*****.wpenginepowered.com/wp-admin/admin-ajax.php, the HTTP response arrives in 0.2 seconds - When I visit the subsite URL
*****.wpenginepowered.com/subsite/wp-admin/admin-ajax.php, the HTTP response arrives in 1.1 seconds
I have double-checked that in the subsite on WP Engine, the line
$wfWAFStorageEngine->installing = !get_option('wordfenceActivated');in Wordfence is alwaystrue, which is a bug (explained in more detail earlier in this thread).Therefore it looks like all subsites in all multisites that use Wordfence in WP Engine (or any environment that uses
WFWAF_STORAGE_ENGINE=mysqli) currently have a performance issue caused by this Wordfence bug.@wfpeter I have now sent site diagnostics + a
debug.logfile to the email wftest @ wordfence . com from a fresh WP installation, with only Wordfence installed.(I am able to reproduce the problem in that fresh WP installation.)
Based on the debugging in my previous post, I tried adding the option
wordfenceActivatedto my non-main blog manually:insert into wp_7_options values (NULL, 'wordfenceActivated', 1, 'yes');After this, Wordfence doesn’t try to re-run the migrations anymore after every page load of a non-main blog.
@wfpeter I did some further debugging on this:
- I deactivated other plugins
- I removed HyperDB (
wp-content/db.php)
The problem still happens after those changes.
Could your developers please check if there is a bug in
waf/bootstrap.phpon line 916 in WP multisite installations?That line is trying to determine whether Wordfence has been installed already. Wordfence calls
get_option('wordfenceActivated'), but it returns empty for me, since WP is running in the context of a non-main blog, not the main blog, when I visit any non-main blog.get_option()returns data from a blog-specificwp_#_optionstable.To me it’s starting to look like the code should instead use
get_network_option()andupdate_network_option(), at least in WP multisite.————————–
Details:
After debugging further, my problem seems to be caused by this code in
waf/bootstrap.phpon line 916:if (function_exists('get_option')) { // This prints "Blog ID: 7", for example error_log('Blog ID: '. get_current_blog_id()); $wfWAFStorageEngine->installing = !get_option('wordfenceActivated'); $wfWAFStorageEngine->getDb()->installing = $wfWAFStorageEngine->installing; }When I visit a non-main blog, the
get_option('wordfenceActivated')row tries to find thewordfenceActivatedoption from the tablewp_7_options, for example.I only have the
wordfenceActivatedoption in the main blog’s tablewp_options, though:MySQL [wordpress]> select * from wp_options where option_name = 'wordfenceActivated'; +-----------+--------------------+--------------+----------+ | option_id | option_name | option_value | autoload | +-----------+--------------------+--------------+----------+ | 89243 | wordfenceActivated | 1 | yes | +-----------+--------------------+--------------+----------+I don’t have
wordfenceActivatedit in the non-main blog tables (wp_#_options). For example:MySQL [wordpress]> select * from wp_7_options where option_name = 'wordfenceActivated'; Empty set (0.001 sec)Therefore it looks to me like Wordfence only sees itself as installed in the main blog, but doesn’t realize it has been installed in non-main blogs, and therefore Wordfence tries to run its installation/migration logic on every WP page load.
I have network-activated Wordfence so that it’s active in all blogs.
I deactivated Wordfence and then network-activated it again, hoping that all WP blogs would receive the
wordfenceActivatedoption. No luck: only the main blog’swp_optionstable has thewordfenceActivatedoption.Note: I have not optimized the firewall.
Hi Peter, thanks for the reply.
We’ve run some tests on a multisite with MySQLi enabled and we see the correct version being detected in
runMigrations()when visiting sub-sites.Interesting that you couldn’t reproduce the problem.
Since I’m not only setting the
WFWAF_STORAGE_ENGINEconstant, but also setting the following constants, I was wondering if one of those constants is the cause of the problem:WORDFENCE_ALLOW_DIRECT_MYSQLIWFWAF_DB_*WFWAF_TABLE_PREFIX
But if you tried with those constants defined as well, perhaps the root cause is somewhere else.
Note that I’m also using HyperDB, i.e.
wp-content/db.php, with one read-only DB instance and one read-write DB instance, which is why I set this tofalseas instructed.Are
DB_HOST,DB_NAME,$table_prefix, or any other database-related values being set differently for the non-main blogs?No, those values are the same for all blogs. This is what my
wp-config.phpbasically contains:define( 'DB_NAME', [redacted] ); define( 'DB_USER', [redacted] ); define( 'DB_PASSWORD', [redacted] ); define( 'DB_HOST', [redacted] ); define( 'DB_CHARSET', 'utf8mb4' ); define( 'DB_COLLATE', 'utf8mb4_swedish_ci' ); $table_prefix = 'wp_'; if ( !defined( 'WFWAF_STORAGE_ENGINE' ) ) { define( 'WFWAF_STORAGE_ENGINE', 'mysqli' ); // For HyperDB define( 'WORDFENCE_ALLOW_DIRECT_MYSQLI', false ); define( 'WFWAF_DB_NAME', DB_NAME ); define( 'WFWAF_DB_USER', DB_USER ); define( 'WFWAF_DB_PASSWORD', DB_PASSWORD ); define( 'WFWAF_DB_HOST', DB_HOST ); define( 'WFWAF_DB_CHARSET', DB_CHARSET ); define( 'WFWAF_DB_COLLATE', DB_COLLATE ); define( 'WFWAF_TABLE_PREFIX', $table_prefix ); } if ( !defined('ABSPATH') ) define('ABSPATH', dirname(__FILE__) . '/'); require_once(ABSPATH . 'wp-settings.php');If you could send a diagnostic to wftest @ wordfence . com directly from the link at the top of the Wordfence > Tools > Diagnostics page, that may help. Then click on “Send Report by Email”. Please add your forum username where indicated and respond here after you have sent it.
If the “Send Report by Email” button creates the same diagnostics output as the “Export” button, then unfortunately it sends too much data for my liking (in terms of security). I might sanitize the data by hand first and send it to you manually.
The
debug.logfile does not contain any Wordfence-specific errors.I’ll get back to this next week.
The following is the slowest callstack that is being run in every WP page load (in non-main WP blogs) when using
WFWAF_STORAGE_ENGINEmysqli, with the configuration I mentioned earlier:wfWAF::run
-> wfWAF::runMigrations
-> wfWAFCronFetchRulesEvent::fire
-> wfWAFHTTP::get
-> wfWAFHTTP::send
-> wfWAFHTTPTransportCurl::send
-> curl_exec