9

I have a plugin that currently doesn't support network activation. The best fix for this of course is to fix it :) which I plan to do. However I wonder if there is a temporary solution I can use to prevent network activation in the meantime, perhaps a workflow similar to:

  1. Detect if the activation is network-wide (how??)
  2. Display message that it's currently not supported, and I stink, I'm sorry
  3. Interrupt the activation or deactivate

Or, other suggestions accepted. Thanks.

For clarification: Multisite activation is fine, just not network-wide activation.

4 Answers 4

5

The answers here are overthought and too complex. Why deactivating the plugin instead of preventing activation? Something as simple as calling die('your error message here) upon activation will do the job.

function activate($networkwide) {
    if (is_multisite() && $networkwide) 
       die('This plugin can\'t be activated networkwide');
}

register_activation_hook('your-plugin/index.php','activate');

Then when you try to activate in the panel, you will get a nice error on top of the page, with your error message.

6

A plugin header Network: false will be ignored by WordPress … unfortunately. But the activation hook gets a parameter $network_wide, and we can use that to deactivate the plugin during activation:

<?php
/**
 * Plugin Name: Prevent Network Activation
 * Plugin URI:  http://wordpress.stackexchange.com/questions/76145/prevent-network-activation-of-plugin
 * Network:     false
 *
 * Note the 'Network' option will be ignored by WordPress.
 */

register_activation_hook( __FILE__, 'pna_check_network_activation' );

function pna_check_network_activation( $network_wide )
{
    if ( ! $network_wide )
        return;

    deactivate_plugins( plugin_basename( __FILE__ ), TRUE, TRUE );

    header( 'Location: ' . network_admin_url( 'plugins.php?deactivate=true' ) );
    exit;
}
2
  • This is useful, but doesn't let me explain what's happening (at least as currently presented). I could just put a wp_die in there and skip the redirection, but that seems only a little less tacky than deactivating without explanation. :)
    – k3davis
    Commented Dec 14, 2012 at 19:28
  • 1
    This is the solution I ended up using - I just adjusted this function to "die" to send the message rather than redirect to the deactivate URL. It's not the cleanest, but it meets all the requirements and has less overhead than the other solutions, for a temporary patch on my part.
    – k3davis
    Commented Dec 18, 2012 at 14:15
4

You could simply hide it from the network-plugins list.

add_filter( 'all_plugins', 'wpse_76145_hide_network_plugin' );
function wpse_76145_hide_network_plugin( $all )
{
    global $current_screen;

    if( $current_screen->is_network )
        unset($all['akismet/akismet.php']);

    return $all;
}

And display a one-time network admin notice. Adapting the Q&A add_role() run only once?.

add_action( 'network_admin_notices', 'wpse_76145_admin_notice' );

function wpse_76145_admin_notice()
{ 
    global $current_screen;
    if( 'plugins-network' == $current_screen->id )
    {
        if ( wpse_25643_run_once( 'hide_akismet_network' ) )
            echo '<div class="error">Akismet not available in Network mode</div>';
    }
}

function wpse_25643_run_once( $key )
{
    $test_case = get_option( 'run_once' );

    if ( isset( $test_case[$key] ) && $test_case[$key] )
    {
        return false;
    }
    else
    {
        $test_case[$key] = true;
        update_option( 'run_once',$test_case );
        return true;
    }
}

Or use this other technique: Add a notice to users upon first login to the admin area

2

(This is untested)

add_action( 'activated_plugin', 'wpse76145_no_network_activation',10,2 );
function wpse76145_no_network_activation( $plugin, $network_wide){

   if( $plugin == 'myplugin/myplugin.php' && $network_wide ){
       //Plugin was network activated

       //Network deactivate
       deactivate_plugins( $plugin,false, true );

       //Activate on single site
       activate_plugins( $plugin);

       add_option('wpse76145_network_activate_notice',1);
   }

}

And then on admin_notices check for the wpse76145_network_activate_notice option and display notice.

Note: It would be better not to hardcode 'myplugin/myplugin.php' - I think replacing it with plugin_basename(__FILE__); would work (and be preferable).

Edit if multi-site activation is ok, then you could use switch_to_blog() to activate on each plug-in individually. I would still display a notice as you've not done what the user has asked.

2
  • This might work, but I don't understand how the admin notice is going to get called if the plugin is already deactivated? Or is it the single site activation that lets this happen?
    – k3davis
    Commented Dec 14, 2012 at 19:33
  • Yup, you activate the plugin on just the main site. Commented Dec 14, 2012 at 21:17

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.