Conclusion

This bug was caused by a function nameclash, which is now fixed by renaming one of the functions.

Background

The more general issue is that module names are not prefix-free. Thus, function prefix does not determine the module that "owns" the function. Both "user" module and "user_delete" module may declare a function and name it "user_delete_access()".

A solution would be to have namespaces for procedural code, just as is already planned for classes.
The problem is, this would be a lot of work, and some people say we should rather get rid of procedural altogether.
See #1393208-21: Namespace all Drupal PHP code (esp. procedural)

Original bug report

Drush command terminated abnormally due to an unrecoverable error. [error]
Error: Cannot redeclare user_delete_access() (previously declared in
/sites/all/modules/user_delete/user_delete.module:57) in
/modules/user/user.module, line 2564

basically I had to disable user_delete in order to get the update running.

Support from Acquia helps fund testing for Drupal Acquia logo

Comments

fenstrat’s picture

Title: conflicts with Drupal-6.24 using Drush » Fatal error Cannot redeclare user_delete_access() with Drupal-6.24
Version: 6.x-1.4 » 6.x-1.x-dev
Priority: Normal » Critical

This isn't just with Drush, this is caused by a commit to Drupal core #909274: Anonymous delete form is displayed

Solution will be to rename this modules user_delete_access() function.

fenstrat’s picture

Status: Active » Needs review
FileSize
904 bytes

The attached patch simply renames the function here in user_delete from user_delete_access() to user_delete_menu_access().

fenstrat’s picture

This adds to #2 to add the same check as #909274: Anonymous delete form is displayed.

Gábor Hojtsy’s picture

Added this to the known issues on http://drupal.org/drupal-7.12

In Drupal 6.24, if you have the contributed user_delete module enabled on your site, the update will fail with a Cannot redeclare user_delete_access() error. An update of user_delete module is being worked on.

MakeOnlineShop’s picture

Got the problem also, it's good that Drupal automatically disable the module when you delete the files form FTP, ten it works.

fenstrat’s picture

@make-online-shop Could you test the patch here in #3 as it should solve the problem at it's source (rather than just disabling the module).

jerry’s picture

Confirming that the patch worked fine for me on multiple sites.

fenstrat’s picture

@jerry, Could you mark this as RTBC then?

jerry’s picture

Status: Needs review » Reviewed & tested by the community

Done.

fenstrat’s picture

Great, thanks @jerry. Hopefully we can get a maintainers eyes on this for a commit.

donquixote’s picture

This shows the importance of namespaces for functions, that will hopefully come in D8.
#867772-79: Use PHP 5.3 namespaces
Module name as function prefix is simply not sufficient.

donquixote’s picture

Quick comments on the patch in #3:
- "user_delete_menu_access" seems like a stupid name to me. If anyone has a better idea..
- Checking for the $account->uid criteria before the user_access stuff seems like a good idea for performance, doesn't it?

That's all not vital, and I only write this because I stumbled upon this issue.
The existing patch in #3 is technically sufficient and absolutely necessary. Any style fixes can be postponed to a later release.

fenstrat’s picture

@donquixote, Couldn't agree more on the need for function namespaces.

Agree the $account->uid criteria should be first, but was just following the core patch #909274-3: Anonymous delete form is displayed

Would user_delete_account_access() be better than user_delete_menu_access()?

jbrown’s picture

Issue tags: +namespaces

tagging

donquixote’s picture

@fenstrat (#13)

Would user_delete_account_access() be better than user_delete_menu_access()?

Better than _menu..
Imo, the name should make it clear how this access callback is different from the core one. The most relevant difference is, this one is provided by a module.
So, saying user_delete_user_delete_access() does look a bit redundant, but it does clearly indicate that this one is provided by a contrib module.
I think I won't come up with anything smarter than that - I'm out.

fenstrat’s picture

Same as #3, just with updated function name, and a comment.

I've left the $account->uid > 0 check at the end of the return statement, it's only to catch anonymous delete requests (which should be rare), and it matches core.

daveparrish’s picture

I tested #16 and it works well for me. Thanks!

EvanDonovan’s picture

Patch resolves the fatal error, thanks.

hopfrog’s picture

Which module file refers the patch?

fenstrat’s picture

@hopfrog The patch applies to user_delete.module. Please see http://drupal.org/patch/apply for how to apply a patch.

dadderley’s picture

This is really a big problem.
I attempted to update core from 6.22 to 6.24 with this module in place.

This is the error message.

Fatal error: Cannot redeclare user_delete_access() (previously declared in /home/user/mysite.com/sites/all/modules/user_delete/user_delete.module:47) in /home/user/mysite.com/modules/user/user.module on line 2564

This module effectively kills the site.

Only way to get it back is re-upload 6.22 and repopulate the db with a backup (if you were smart enough to make one before updating core).
This is an ugly harrowing experience that no one should have to go through.

jerry’s picture

Only way to get it back is re-upload 6.22 and repopulate the db with a backup (if you were smart enough to make one before updating core.

Did you apply one of the two working patches (#3, #16) that were already posted in this issue before resorting to that?

fenstrat’s picture

@dougzilla As @jerry mentioned you should just need to apply the patch here in #16, no need to rollback the db.

dadderley’s picture

I know this now.
When my site got borked and I was in full panic mode, I did not.
Sorry for being so dramatic about this, but I see this is a real problem when it comes at you right out of the blue.
Maybe it is time to commit the patches.

MakeOnlineShop’s picture

Sorry but you are wrong.

Just delete the USER DELETE module from your FTP and the site will work perfectly as before without this module !

I did it on many websites that I have updated and was happy to see that drupal is smart enough to disable a module when its files are no more accessible.

dadderley’s picture

@make-online-shop
True enough. Deleting the module makes the problem go away.
The problem caused by this module's conflict with Drupal 6.24 is not an end of the world scenario.

But, as I said, when I first updated core with this in place, my site was in fact borked.
This is not a good thing.
Updating core, should not be like playing Russian Roulette.

I did a quick restore, made it work.
If I had found this thread quicker, I would have just deleted the module.

I have not as yet patched and re-installed User Delete.
It is a useful module.

Gábor Hojtsy’s picture

@dougzilla: yes, you are right. We are doing everything we can to ensure that core updates are worry-free, but its always best to apply changes in a test environment first. It cannot be guaranteed that the update will be 100% error free with any modules released on drupal.org (+ custom developed for your site), that is not really humanly possible to ensure. We are sorry for the inconvenience, at this point the best you can do is to (a) remove user_delete module (b) wait for user_delete module to release an update with this patch (c) then apply that update so you can re-enable the user delete module. There is unfortunately not much Drupal core could do at this point because the issue is a name clash with the user delete module not in core.

donquixote’s picture

What drupal core should do in the future is to introduce namespaces for procedural code (as it already will do for classes). This would allow to introduce new functions and hooks without nameclashing with contrib.

This will not happen before D8, though.
Until then, contrib should be preemptively paranoid, and use function names that are not likely to clash with other modules or core.

dadderley’s picture

@Gábor Hojtsy
Thanks for your reply.
I appreciate your hard work.

reload’s picture

Tested #16 fixes problem. Thanks!

jswap’s picture

This #16 patch also worked for me. I just want to note that the instructions on how to apply a patch here:
http://drupal.org/node/707484

say "Download the patch to the root of your working directory."

However, you actually need to put this patch into your .../modules/user_delete directory for it to work.

Maciej Lukianski’s picture

#16 works. Could this make a new release? It will save a lot of people a lot of headache.

sanduhrs’s picture

Status: Reviewed & tested by the community » Fixed

Commited and triggered a new release 6.x-1.5.
Thanks all.

Status: Fixed » Closed (fixed)

Automatically closed -- issue fixed for 2 weeks with no activity.

tezalsec’s picture

Although considered fixed and not expecting response, I just had to add my 2 cents because of the extent of the problems this issue gave me. I too had to re-upload and repopulate the db.

A learning point for me was that the use of drush apparently gave out this error message, pointing at the problem. As a non-drush user, I had no idea where to locate the cause of the issue, just seeing the website crash in the browser, without giving any pointers. Fortunately, I found this thread by Googling "upgrade problem drupal 6.24". So if there are other ways to get such error messages so you have a starting point where to look, I am all ears.

Subscribing to the stressing of the need of function namespaces +1.

Thanks for all effort.

fenstrat’s picture

@Maxim75 This issue had nothing todo with Drush. The error you saw is due to the php fatal error which resulted in a WSOD because your php error reporting is not displaying fatal errors to screen (which is only ever useful, or secure, during development - i.e. not on a live site). To display these errors you need to raise your error reporting level - see http://php.net/manual/en/function.error-reporting.php

donquixote’s picture

#35 / #36:
Error reporting settings can be different for commandline php and web php, and there can be additional settings in your drush setup and in Drupal's settings.php, .htaccess, or any place you want. This is why you may see errors in Drush that don't appear on the web.

tezalsec’s picture

#35: I realize it had nothing to do with drush, just referenced it as an tool to be used as a means to get error descriptions.

#35:36: Thanks for the suggestions. As a newbie php developer, I guess I have to start using more error-reporting methods in such cases. I must say, I never realized you could get php error messages in the browser itself, like in offline and stateful IDE's. Assuming that in such cases mimicing the crash on a development site with the right error reporting settings would provide good debugging pointers.

fenstrat’s picture

@donquixote Good point, I generally try to keep my cli and web php ini settings in sync to avoid any missmatches. What I was getting is that this fatal error would result if the module was updated/enabled via Drush or via the Modules page.

@Maxim75 Yep, you certainly can get error messages in the browser. A good place to start with Drupal is "Error messages to display" in admin/config/development/logging - for dev you want "All messages" for production "None".

fenstrat’s picture

Issue summary: View changes

background: namespaces for procedural?