这是我的经验。
我必须在Wordpress中为每个站点添加角色,我在dashboard中开发了一个添加页面,以便站点管理员可以添加自定义角色/功能。
但我发现$wp_roles->add_role
, add_cap
仅适用于子网站。所以我做了一些修复,
我制作了一个插件,超级管理员(不是站点管理员,而是“管理员”)可以在仪表板中“网络激活”
xxx/wp管理员/网络/插件。php
自定义角色/功能保存在role.ini
文件中,插件可以创建两个名为wp_s_role
和wp_s_cap
, 预定义的角色/功能将插入表中。
然后$wp_roles->add_rol
e和add_cap
可以跨网络并将角色/功能插入所有子网站。
但是子网站管理员必须添加自定义角色/功能,并使其在所有子网站中都能工作,因此我为
register_activation_hook(__FILE__, array($s_role, \'install\'));
register_deactivation_hook(__FILE__, array($s_role, \'uninstall\'));
然后卸载功能工作,所有两个表的数据将保存到
role.ini
然后,安装功能将再次工作。并将所有自定义角色/功能添加到所有子网站中。
如您所见,我做了一个触发器,以便将自定义角色添加到所有子网站中,但有效性非常低,插件重新启动需要5秒钟以上。因此,我改进了这些方法,这次,当add\\u role功能完成时,我将子网站角色/功能复制到其他子网站中。
一些步骤:
在子网站中,当管理员添加角色时,我使用$blog_id
和$table_prefix
获取子网站表wp_2_options
目录(我们假设blog\\u id为2
table\\u前缀为wp
).
我选择option_name=wp_2_user_roles
result($wpdb->get_row("select `option_value` from `wp_2_options` where `option_name`=\'wp_2_user_roles\'", ARRAY_A);),
然后我
foreach
并获取子网站表。因此,我将选择结果插入到每个子网站表中(
wp_n_options
) 和主表(
wp_options
), 哈哈,我够聪明吗?:)
下面的功能是如何删除所有子网站中的自定义角色。我想这对你有帮助。
public function reset_subsite_role_cap()
{
//select * from `wp_options` where `option_name` = \'wp_user_roles\';
//select * from `wp_options` where `option_name` = \'wp_backup_user_roles\';
//select * from `wp_3_options` where `option_name` = \'wp_3_user_roles\';
//select * from `wp_4_options` where `option_name` = \'wp_4_user_roles\';
//select * from `wp_5_options` where `option_name` = \'wp_5_user_roles\';
global $wpdb;
$sql = "select * from ".$wpdb->blogs;
$multisite_info = $wpdb->get_results($sql, ARRAY_A);
$site_result = array();
if (!empty($multisite_info) && is_array($multisite_info)) {
foreach ($multisite_info as $k => $v) {
$site_result[$v[\'blog_id\']] = trim($v[\'path\'], \'/\');
}
}
global $table_prefix;
$tp_arr = explode(\'_\', $table_prefix);
$table_arr = array();
foreach ($site_result as $blog_id => $site_name) {
if ($blog_id !== 1) {
$table_arr[$tp_arr[0].\'_\'.$blog_id.\'_options\'] = $tp_arr[0].\'_\'.$blog_id.\'_user_roles\';
} else {
$table_arr[$tp_arr[0].\'_options\'] = $tp_arr[0].\'_user_roles\';
}
}
// get the backup user roles.
$backup_roles_result = $wpdb->get_row("select `option_value` from `".$tp_arr[0]."_options` where `option_name`=\'wp_backup_user_roles\'", ARRAY_A);
// clean the others role cap
if (isset($table_arr) && is_array($table_arr)) {
foreach ($table_arr as $table_role_cap_name => $table_role_cap_filed) {
$wpdb->update(
$table_role_cap_name,
array(\'option_value\' => $backup_roles_result[\'option_value\']),
array(\'option_name\' => $table_role_cap_filed)
);
}
}
return true;
}
对于$site\\u结果,我有另一个函数来获取所有准确的站点信息。
/**
* Get the all site info.
*
* @param integer $id BlogID.
*
* @return array array(\'blog_id\' => \'path\', \'1\' => \'printsolv\', \'2\' => \'govsolv\')
*/
public function s_get_multisite_info($id = null)
{
global $wpdb;
$where = \'1=1\';
if (isset($id)) {
$sql = "select * from ".$wpdb->blogs." where `blog_id`="."\'".$id."\'";
} else {
$sql = "select * from ".$wpdb->blogs." where 1=1 ";
}
$multisite_info = $wpdb->get_results($sql, ARRAY_A);
$result = array();
if (!empty($multisite_info) && is_array($multisite_info)) {
// clean the path, > 1 means not http://site_name/theme.php but http://site_name/path_name/theme.php
if (isset($id)) {
$site_info = $wpdb->get_row("select * from ".$wpdb->site." where `id`="."\'".$multisite_info[0][\'site_id\']."\'", ARRAY_A);
} else {
$site_info = $wpdb->get_row("select * from ".$wpdb->site, ARRAY_A);
}
$site_path_status = false; // path= /
if (isset($site_info[\'path\']) && strlen(trim($site_info[\'path\'], \'/\')) > 1 ) {
// site have path./xxx/
$site_path_status = true;
}
foreach ($multisite_info as $k => $v) {
if (isset($site_info[\'domain\']) && $site_info[\'domain\'] == $v[\'domain\']) {
if ($site_path_status == true) {
$result[$v[\'blog_id\']] = trim(substr($v[\'path\'], strlen(trim($site_info[\'path\'], \'/\')) + 1), \'/\');
} else {
$result[$v[\'blog_id\']] = trim($v[\'path\'], \'/\');
}
}
}
}
return $result;
}
我刚刚完成了这个功能,它工作得很好。您可以使用s\\u copy\\u site\\u role\\u cap()调用。添加\\u角色后,该功能可以将角色复制到其他子网站角色中。由于该插件可能在主站点或子站点中工作,因此在网络中有两种方式(子域、子路径),因此我创建了另一个函数来获取正确的当前blog\\u名称,以便从blog\\u名称信息中获取最新的角色内容。
/**
* Copy the subsite role/caps to all subsites and main site..
*
* @param string $subsite_name SubSite Name.
*
* @return boolean.
*/
public function s_copy_site_role_cap()
{
global $wpdb;
// Get all site info
$multisite_info = $this->s_get_multisite_info();
global $table_prefix;
$tp_arr = explode(\'_\', $table_prefix);
// Get all site wp_x_options table. and table filed.
$table_arr = array();
foreach ($multisite_info as $blog_id => $site_name) {
if ($blog_id !== 1) {
$table_arr[$tp_arr[0].\'_\'.$blog_id.\'_options\'] = $tp_arr[0].\'_\'.$blog_id.\'_user_roles\';
} else {
$table_arr[$tp_arr[0].\'_options\'] = $tp_arr[0].\'_user_roles\';
}
}
// select the blog id by blog name.
$subsite_name = $this->s_get_dashboard_site_name();
$subsite_id = array_search($subsite_name, $multisite_info);
if ($subsite_id === false) {
return false;
}
$current_site_table_pre = $tp_arr[0].\'_\'.$subsite_id;
// get the current subsite roles.
$subsite_roles = $wpdb->get_row("select `option_value` from `".$current_site_table_pre."_options` where `option_name`=\'".$current_site_table_pre."_user_roles\'", ARRAY_A);
if (isset($table_arr) && is_array($table_arr)) {
foreach ($table_arr as $table_role_cap_name => $table_role_cap_filed) {
if ($table_role_cap_name != $current_site_table_pre.\'_options\') {
$wpdb->update(
$table_role_cap_name,
array(\'option_value\' => $subsite_roles[\'option_value\']),
array(\'option_name\' => $table_role_cap_filed)
);
}
}
}
return true;
}
/**
* Get dashboard site name.
*
* @return string. SiteName
*/
public function s_get_dashboard_site_name()
{
$dashboard_url = admin_url();
//$dashboard_url = "http://xxx/wp-admin/";
//$dashboard_url = "http://subsite_name.xxx/wp-admin/";
//$dashboard_url = "http://xxx/subsite_name/wp-admin/";
// get main site name.
$site_name = get_current_site()->domain;
$parse_url = parse_url($dashboard_url);
if (!is_subdomain_install()) {
// base path http://xxx/wp-admin/
// subsite path http://xxx/subsite_name/wp-admin/
if ($parse_url[\'path\'] == "/wp-admin/") {
return $site_name;
} else {
$tmp_url = explode("/", trim($parse_url[\'path\'], "/"));
return $tmp_url[0];
}
} else {
// base domain http://xxx/wp-admin/
// subsite domain http://subsite_name.xxx/wp-admin/
if ($parse_url[\'host\'] == $site_name) {
return $site_name;
} else {
$tmp_url = explode(".", $parse_url[\'host\']);
return $tmp_url[0];
}
}
}
谢谢。