Per user, per site Dashboard and Screen Options in WordPress multisite

June 6 |
By: IvanWalsh.com - CC BY 2.0
By: IvanWalsh.comCC BY 2.0
The Offbeat Empire uses many plugins on our sites to streamline the writing and editing process. Different users have access to different plugins, depending on their job. When editors began reporting that their plugin settings were not sticking on the Add New Post page, I dug into the code and found that WordPress (as of version 3.2) was overwriting their Screen Options settings every time they visited the Add New Post page, no matter which blog they visited. For example, if they regularly used the Editorial Comments meta box on one blog and had moved it to be directly under the main post box, this preference in their Add New Post layout would be overwritten if they visited the Dashboard of a blog without the Editorial Comments plugin.

I ended up writing the following functions that create a series of shadow screen options for each user. This code filters reads and writes of user Screen Options metadata based on the blog_id global variable. Screen Options for plugin-generated meta boxes will be saved on a per site basis for each user, allowing them to retain their Add New/Edit Post appearance on each separate blog.

This code is useful on multisite installs with a finite number of users and blogs where blogs have different uses and the active plugin set differs between blogs.

function ucc_sso_update_user_metadata( $meta_type = null, $user_id, $meta_key, $meta_value, $prev_value = '' ) {
  global $blog_id, $wpdb;

  $prefix = 'ucc_sso_' . $blog_id . '_';
  if ( preg_match( "#^closedpostboxes#", $meta_key ) ||
       preg_match( "#^metaboxhidden#", $meta_key ) ||
       preg_match( "#^meta-box-order#", $meta_key ) ||
       preg_match( "#^screen_layout#", $meta_key ) ) {
    $meta_key = $prefix . $meta_key;
    $result = update_user_meta( $user_id, $meta_key, $meta_value, $prev_value = '' );
    return $result;
  } else {
    return null;
  }
}
add_filter( 'update_user_metadata', 'ucc_sso_update_user_metadata', 10, 5 );

function ucc_sso_get_user_metadata( $meta_type = null, $user_id, $meta_key, $single ) {
  global $blog_id, $wpdb;

  $prefix = 'ucc_sso_' . $blog_id . '_';
  if ( preg_match( "#^closedpostboxes#", $meta_key ) ||
       preg_match( "#^metaboxhidden#", $meta_key ) ||
       preg_match( "#^meta-box-order#", $meta_key ) ||
       preg_match( "#^screen_layout#", $meta_key ) ) {
    $meta_key = $prefix . $meta_key;
    $result = get_user_meta( $user_id, $meta_key, $single );
    return $result;
  } else {
    return null;
  }
}
add_filter( 'get_user_metadata', 'ucc_sso_get_user_metadata', 10, 4 );

function ucc_sso_get_user_option( $result, $option, $user ) {
  global $blog_id, $wpdb;

  $prefix = 'ucc_sso_' . $blog_id . '_';
  $option = $prefix . $option;
  $result = get_user_option( $option, $user->ID );

  return $result;
}
add_filter( "get_user_option_closedpostboxes_post", 'ucc_sso_get_user_option', 10, 3 );
add_filter( "get_user_option_metaboxhidden_post", 'ucc_sso_get_user_option', 10, 3 );
add_filter( "get_user_option_meta-box-order_post", 'ucc_sso_get_user_option', 10, 3 );
add_filter( "get_user_option_screen_layout_post", 'ucc_sso_get_user_option', 10, 3 );

Code contained in this entry is licensed under GNU General Public License, version 2.

References

Leave a Reply

No-drama comment policy

Part of what makes the Offbeat Empire different is our commitment to civil, constructive commenting. Make sure you're familiar with our no-drama comment policy.

Biz owners & wedding bloggers

Please just use your real name in your comment, not your business name or blog title. Our comments are not the place to pimp your website. If you want to promote your stuff on Offbeat Bride, join us as an advertiser instead.