search_update_totals() should be more robust

andypost - June 29, 2009 - 20:22
Project:Drupal
Version:7.x-dev
Component:search.module
Category:bug report
Priority:normal
Assigned:Unassigned
Status:duplicate
Description

Here is a host with replicatable errors

console 2 run http://drupalbin.com/10206

http://drupalbin.com/10203 on mine server
http://drupalbin.com/10204 on AWS

#1

Amazon - June 29, 2009 - 20:48

On the same site, I ran simpletest from the UI.

http://drupalbin.com/10207

SSH keys and logins are available. Just ask in #drupal-infrastructure.

#2

Damien Tournoud - June 30, 2009 - 00:27
Status:active» postponed (maintainer needs more info)

Care to identify the test cases that are failing?

#3

andypost - June 30, 2009 - 07:48
Status:postponed (maintainer needs more info)» needs work

I have stable fault on test system->Cron Run

http://php.net/manual/en/function.set-exception-handler.php

In comments I found mostly happens when exception raised inside exception handler

#4

andypost - June 30, 2009 - 08:16

So when I run from console scrups/run-tests.sh

Trigger cron (system) actions 30 passes, 0 fails, and 0 exceptions

Fatal error: Exception thrown without a stack frame in Unknown on line 0
Upload functionality 113 passes, 28 fails, and 4 exceptions

Suppose, exception just breaks batch, because result - tests passed

#5

boombatower - July 9, 2009 - 01:47
Status:needs work» postponed (maintainer needs more info)

I'm really not sure what the issue is, can someone provide a bit more detail...seems like it changed from the original thought.

#6

philipnet - July 11, 2009 - 17:00
Title:Batch process broken - replicatable» drupal_cron_run causes "Exception thrown without a stack frame in Unknown on line 0"
Component:simpletest.module» base system
Status:postponed (maintainer needs more info)» active

Test “System -> Cron run” fails with an exception; the message returned is:

Message: {"status":true,"percentage":"100","message":"Processed test 1 of 1 - \x3cem\x3eCron run\x3c\/em\x3e.\x3cdiv class=\"simpletest-pass\"\x3eOverall results: 18 passes, 0 fails, and 0 exceptions\x3c\/div\x3e\x3cdiv class=\"item-list\"\x3e\x3cul\x3e\x3cli class=\"first last\"\x3e\x3cdiv class=\"simpletest-pass\"\x3eCron run: 18 passes, 0 fails, and 0 exceptions\x3c\/div\x3e\x3c\/li\x3e\n\x3c\/ul\x3e\x3c\/div\x3e"}
Fatal error: Exception thrown without a stack frame in Unknown on line 0

Test “System -> Trigger cron (system) actions” fails with an exception; the message returned is:

Message: {"status":true,"percentage":"100","message":"Processed test 1 of 1 - \x3cem\x3eTrigger cron (system) actions\x3c\/em\x3e.\x3cdiv class=\"simpletest-pass\"\x3eOverall results: 30 passes, 0 fails, and 0 exceptions\x3c\/div\x3e\x3cdiv class=\"item-list\"\x3e\x3cul\x3e\x3cli class=\"first last\"\x3e\x3cdiv class=\"simpletest-pass\"\x3eTrigger cron (system) actions: 30 passes, 0 fails, and 0 exceptions\x3c\/div\x3e\x3c\/li\x3e\n\x3c\/ul\x3e\x3c\/div\x3e"}
Fatal error: Exception thrown without a stack frame in Unknown on line 0


Both tests call drupal_cron_run at least once; this instigates the Exception thrown later on in the DBTNG environment, see below for how I arrived at this.


For both of these, the function calling hierarchy is: drupal_cron_run -> module_invoke_all('cron') -> call_user_func_array -> search_cron -> register_shutdown_function('search_update_totals');
search_update_totals -> db_query("... {search_total} ...");

Cron is calling the module's _cron functions, but is falling over on the Search module as that module hasn't been enabled.


I'm looking in function module_implements(); plugging the SQL into mysql via the CLI:
SELECT * FROM registry WHERE type = 'function' AND suffix = "cron";

+-------------+----------+------------------------------+--------+--------+--------+
| name        | type     | filename                     | module | suffix | weight |
+-------------+----------+------------------------------+--------+--------+--------+
| dblog_cron  | function | modules/dblog/dblog.module   | dblog  | cron   |      0 |
| filter_cron | function | modules/filter/filter.module | filter | cron   |      0 |
| node_cron   | function | modules/node/node.module     | node   | cron   |      0 |
| system_cron | function | modules/system/system.module | system | cron   |      0 |
| update_cron | function | modules/update/update.module | update | cron   |      0 |
+-------------+----------+------------------------------+--------+--------+--------+
5 rows in set (0.00 sec)

If I put:
if ($hook=='cron') { var_dump($implementations[$hook]); }
in modules.inc at line 387, it prints:
array(5) {
[0]=>
string(5) "dblog"
[1]=>
string(6) "filter"
[2]=>
string(4) "node"
[3]=>
string(6) "search"
[4]=>
string(6) "system"
}

I don't understand why 'search' is returned and 'update' isn't.


At least
db_query ("SELECT * FROM {does_not_exist}");
throws an exception with helpful text and file names with line numbers.


Can anyone replicate what I've produced above and help clear the fog my brain as to why it's happening?

#7

stuzza - July 28, 2009 - 21:06

I can replicate it, though I can't shed any further light.

Bizarrely, the same query, when run directly before module_implements() is called, returns:

array(5) {
  [0]=>
  string(5) "dblog"
  [1]=>
  string(6) "filter"
  [2]=>
  string(4) "node"
  [3]=>
  string(6) "system"
  [4]=>
  string(6) "update"
}

but within module_implements() it returns the result philipnet mentioned above. I don't believe caching is a factor as I've got module_implements() purging its cache to automatically. It's as if the registry table is changed 'magically' each time the function module_implements() is invoked with the 'cron' hook.

#8

stuzza - July 29, 2009 - 01:49

I've done some more fossicking. In modules/simpletest/drupal_web_test_case.php DrupalWebTestCase::setUp() installs modules from the default profile, including search. I had Drupal installed using the expert ('Drupal (minimal)') profile and I found when reinstalling with the default profile I no longer got the error.

I understand that testing against the default profile makes sense (you have to test against some sort of defined environment) but this testing doesn't seem to be working when the underlying platform has been installed with a different profile.

My colleague Josh Waihi suggests there might be DrupalWebTestCase::preloadRegistry() might be part of the problem.

#9

Josh Waihi - July 29, 2009 - 01:48

To extend what @stuzza is saying, this problem only occurs when testing in Expert mode, because, as it would seem, simpletests assumes the parent database is in a state that reflects the default install profile and tries to cut performance corners by copying the registry from from the parent database (I think with ->preloadRegisty). If this is the case, then when need to either make the default profile modules dependencies of the simpletest module or not steal the registry state from the parent database, which seems like a better idea to me.

Thinking about it a bit more, why not create a drupal install with a prefix like 'st_model' and steal the registry from that rather than the parent - It could also be useful for stealing other bits and pieces.

#10

philipnet - August 5, 2009 - 08:52
Title:drupal_cron_run causes "Exception thrown without a stack frame in Unknown on line 0"» SimpleTest cuts corners by copying the registry from the parent database - causes problems with "Drupal (minimal)" installs
Component:base system» simpletest.module

In that case, this need re-assigning.

#11

Damien Tournoud - August 5, 2009 - 08:57
Title:SimpleTest cuts corners by copying the registry from the parent database - causes problems with "Drupal (minimal)" installs» search_update_totals() should be more robust
Component:simpletest.module» search.module

This has nothing to do with the registry or simpletest. It's just that the search module is registering a shutdown function when run into the child site, but this function fails because at the time when it is executed, the child site has already been destroyed.

Let's just add a try / catch in search_update_totals().

#12

deekayen - August 8, 2009 - 03:27

Is this error showing on servers with php5-suhosin installed? Seems like that was the cause for me. Haven't been able to reproduce this on MySQL 5.0 MyISAM and InnoDB or MySQL 5.1 MyISAM, so I'm removing the blocker tag.

#13

philipnet - August 18, 2009 - 10:26

It showed up on my test server which /didn't have/ suhosin installed.

But I doubt it's a PIFR 2 blocker as it only manifests if the user invokes the tests from an existing Drupal 7 installation where the Search module is not enabled (AIUI).

#14

chx - October 13, 2009 - 05:23
Status:active» duplicate

#602958: Running cron does not end well

 
 

Drupal is a registered trademark of Dries Buytaert.