Changeset 7141
- Timestamp:
- 06/03/2013 05:12:54 PM (11 years ago)
- Location:
- trunk
- Files:
-
- 1 added
- 6 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/bp-core/bp-core-classes.php
r7135 r7141 49 49 50 50 /** 51 * Unaltered params as passed to the constructor 52 * 53 * @since BuddyPress (1.8) 54 * @var array 55 */ 56 public $query_vars_raw = array(); 57 58 /** 51 59 * Array of variables to query with 52 60 * … … 120 128 */ 121 129 public function __construct( $query = null ) { 122 if ( ! empty( $query ) ) { 123 $this->query_vars = wp_parse_args( $query, array( 130 131 // Store the raw query vars for later access 132 $this->query_vars_raw = $query; 133 134 // Allow extending classes to register action/filter hooks 135 $this->setup_hooks(); 136 137 if ( ! empty( $this->query_vars_raw ) ) { 138 $this->query_vars = wp_parse_args( $this->query_vars_raw, array( 124 139 'type' => 'newest', 125 140 'per_page' => 0, … … 163 178 164 179 /** 180 * Allow extending classes to set up action/filter hooks 181 * 182 * When extending BP_User_Query, you may need to use some of its 183 * internal hooks to modify the output. It's not convenient to call 184 * add_action() or add_filter() in your class constructor, because 185 * BP_User_Query::__construct() contains a fair amount of logic that 186 * you may not want to override in your class. Define this method in 187 * your own class if you need a place where your extending class can 188 * add its hooks early in the query-building process. See 189 * BP_Group_Member_Query::setup_hooks() for an example. 190 * 191 * @since BuddyPress (1.8) 192 */ 193 public function setup_hooks() {} 194 195 /** 165 196 * Prepare the query for user_ids 166 197 * … … 285 316 286 317 // 'include' - User ids to include in the results 287 if ( false !== $include ) { 288 $include = wp_parse_id_list( $include ); 289 $include_ids = $wpdb->escape( implode( ',', (array) $include ) ); 318 $include = ! empty( $include ) ? wp_parse_id_list( $include ) : array(); 319 $include_ids = $this->get_include_ids( $include ); 320 if ( ! empty( $include_ids ) ) { 321 $include_ids = implode( ',', wp_parse_id_list( $include_ids ) ); 290 322 $sql['where'][] = "u.{$this->uid_name} IN ({$include_ids})"; 291 323 } … … 428 460 } 429 461 } 462 } 463 464 /** 465 * Fetches the ids of users to put in the IN clause of the main query 466 * 467 * By default, returns the value passed to it 468 * ($this->query_vars['include']). Having this abstracted into a 469 * standalone method means that extending classes can override the 470 * logic, parsing together their own user_id limits with the 'include' 471 * ids passed to the class constructor. See BP_Group_Member_Query for 472 * an example. 473 * 474 * @since BuddyPress (1.8) 475 * @param array Sanitized array of user ids, as passed to the 'include' 476 * parameter of the class constructor 477 * @return array The list of users to which the main query should be 478 * limited 479 */ 480 public function get_include_ids( $include = array() ) { 481 return $include; 430 482 } 431 483 -
trunk/bp-groups/bp-groups-classes.php
r7140 r7141 948 948 } 949 949 950 /** 951 * Query for the members of a group 952 * 953 * @since BuddyPress (1.8) 954 */ 955 class BP_Group_Member_Query extends BP_User_Query { 956 /** 957 * Set up action hooks 958 * 959 * @since BuddyPress (1.8) 960 */ 961 public function setup_hooks() { 962 // Take this early opportunity to set the default 'type' param 963 // to 'last_modified', which will ensure that BP_User_Query 964 // trusts our order and does not try to apply its own 965 if ( empty( $this->query_vars_raw['type'] ) ) { 966 $this->query_vars_raw['type'] = 'last_modified'; 967 } 968 969 // Set up our populate_extras method 970 add_action( 'bp_user_query_populate_extras', array( $this, 'populate_group_member_extras' ), 10, 2 ); 971 } 972 973 /** 974 * Get a list of user_ids to include in the IN clause of the main query 975 * 976 * Overrides BP_User_Query::get_include_ids(), adding our additional 977 * group-member logic. 978 * 979 * @since BuddyPress (1.8) 980 * @param array 981 * @return array 982 */ 983 public function get_include_ids( $include ) { 984 // The following args are specific to group member queries, and 985 // are not present in the query_vars of a normal BP_User_Query. 986 // We loop through to make sure that defaults are set (though 987 // values passed to the constructor will, as usual, override 988 // these defaults). 989 $this->query_vars = wp_parse_args( $this->query_vars, array( 990 'group_id' => 0, 991 'group_role' => array( 'member' ), 992 'exclude_banned' => true, 993 ) ); 994 995 $group_member_ids = $this->get_group_member_ids(); 996 997 if ( ! empty( $include ) ) { 998 $group_member_ids = array_intersect( $include, $group_member_ids ); 999 } 1000 1001 return $group_member_ids; 1002 } 1003 1004 /** 1005 * Get the members of the queried group 1006 * 1007 * @since BuddyPress (1.8) 1008 * @return array $ids User IDs of relevant group member ids 1009 */ 1010 protected function get_group_member_ids() { 1011 global $wpdb; 1012 1013 $bp = buddypress(); 1014 $sql = array( 1015 'select' => "SELECT user_id FROM {$bp->groups->table_name_members}", 1016 'where' => array(), 1017 'orderby' => '', 1018 'order' => '', 1019 'limit' => '', 1020 ); 1021 1022 /** WHERE clauses *****************************************************/ 1023 1024 $sql['where'][] = $wpdb->prepare( "group_id = %d", $this->query_vars['group_id'] ); 1025 1026 // Role information is stored as follows: admins have 1027 // is_admin = 1, mods have is_mod = 1, and members have both 1028 // set to 0. 1029 $roles = !empty( $this->query_vars['group_role'] ) ? $this->query_vars['group_role'] : array(); 1030 if ( is_string( $roles ) ) { 1031 $roles = explode( ',', $roles ); 1032 } 1033 1034 // Sanitize: Only 'admin', 'mod', and 'member' are valid 1035 foreach ( $roles as $role_key => $role_value ) { 1036 if ( ! in_array( $role_value, array( 'admin', 'mod', 'member' ) ) ) { 1037 unset( $roles[ $role_key ] ); 1038 } 1039 } 1040 1041 // Remove dupes to make the count accurate, and flip for faster 1042 // isset() lookups 1043 $roles = array_flip( array_unique( $roles ) ); 1044 1045 switch ( count( $roles ) ) { 1046 1047 // All three roles means we don't limit results 1048 case 3 : 1049 default : 1050 $roles_sql = ''; 1051 break; 1052 1053 case 2 : 1054 // member + mod = no admins 1055 // member + admin = no mods 1056 if ( isset( $roles['member'] ) ) { 1057 $roles_sql = isset( $roles['admin'] ) ? "is_mod = 0" : "is_admin = 0"; 1058 1059 // Two non-member roles are 'admin' and 'mod' 1060 } else { 1061 $roles_sql = "(is_admin = 1 OR is_mod = 1)"; 1062 } 1063 break; 1064 1065 case 1 : 1066 // member only means no admins or mods 1067 if ( isset( $roles['member'] ) ) { 1068 $roles_sql = "is_admin = 0 AND is_mod = 0"; 1069 1070 // Filter by that role only 1071 } else { 1072 $roles_sql = isset( $roles['admin'] ) ? "is_admin = 1" : "is_mod = 1"; 1073 } 1074 break; 1075 1076 // No roles means no users should be returned 1077 case 0 : 1078 $roles_sql = $this->no_results['where']; 1079 break; 1080 } 1081 1082 if ( ! empty( $roles_sql ) ) { 1083 $sql['where'][] = $roles_sql; 1084 } 1085 1086 if ( ! empty( $this->query_vars['exclude_banned'] ) ) { 1087 $sql['where'][] = "is_banned = 0"; 1088 } 1089 1090 $sql['where'] = ! empty( $sql['where'] ) ? 'WHERE ' . implode( ' AND ', $sql['where'] ) : ''; 1091 1092 /** ORDER BY clause ***************************************************/ 1093 1094 // @todo For now, mimicking legacy behavior of 1095 // bp_group_has_members(), which has us order by date_modified 1096 // only. Should abstract it in the future 1097 $sql['orderby'] = "ORDER BY date_modified"; 1098 $sql['order'] = "DESC"; 1099 1100 /** LIMIT clause ******************************************************/ 1101 1102 // Technically, this is also handled by BP_User_Query, but 1103 // repeating the limit here helps to make the query more 1104 // efficient, by not fetching every single matching user 1105 if ( ! empty( $this->query_vars['per_page'] ) && ! empty( $this->query_vars['page'] ) ) { 1106 $sql['limit'] = $wpdb->prepare( "LIMIT %d, %d", absint( ( $this->query_vars['page'] - 1 ) * $this->query_vars['per_page'] ), absint( $this->query_vars['per_page'] ) ); 1107 } 1108 1109 $ids = $wpdb->get_col( "{$sql['select']} {$sql['where']} {$sql['orderby']} {$sql['order']} {$sql['limit']}" ); 1110 1111 return $ids; 1112 } 1113 1114 /** 1115 * Fetch additional data required in bp_group_has_members() loops 1116 * 1117 * @since BuddyPress (1.8) 1118 * @param object $query BP_User_Query object. Because we're filtering 1119 * the current object, we use $this inside of the method instead 1120 * @param string $user_ids_sql Sanitized, comma-separated string of 1121 * the user ids returned by the main query 1122 */ 1123 public function populate_group_member_extras( $query, $user_ids_sql ) { 1124 global $wpdb; 1125 1126 $bp = buddypress(); 1127 $extras = $wpdb->get_results( $wpdb->prepare( "SELECT user_id, date_modified, is_banned FROM {$bp->groups->table_name_members} WHERE user_id IN ({$user_ids_sql}) AND group_id = %d", $this->query_vars['group_id'] ) ); 1128 1129 foreach ( (array) $extras as $extra ) { 1130 if ( isset( $this->results[ $extra->user_id ] ) ) { 1131 // user_id is provided for backward compatibility 1132 $this->results[ $extra->user_id ]->user_id = (int) $extra->user_id; 1133 $this->results[ $extra->user_id ]->is_banned = (int) $extra->is_banned; 1134 $this->results[ $extra->user_id ]->date_modified = $extra->date_modified; 1135 } 1136 } 1137 1138 // Don't filter other BP_User_Query objects on the same page 1139 remove_action( 'bp_user_query_populate_extras', array( $this, 'populate_group_member_extras' ), 10, 2 ); 1140 } 1141 } 1142 950 1143 class BP_Groups_Member { 951 1144 var $id; … … 1399 1592 function get_all_for_group( $group_id, $limit = false, $page = false, $exclude_admins_mods = true, $exclude_banned = true, $exclude = false ) { 1400 1593 global $bp, $wpdb; 1594 1595 _deprecated_function( __METHOD__, '1.8', 'BP_Group_Member_Query' ); 1401 1596 1402 1597 $pag_sql = ''; -
trunk/bp-groups/bp-groups-functions.php
r7087 r7141 383 383 * Fetch the members of a group 384 384 * 385 * Procedural wrapper for BP_Groups_Member::get_all_for_group(). 385 * Since BuddyPress 1.8, a procedural wrapper for BP_Group_Member_Query. 386 * Previously called BP_Groups_Member::get_all_for_group(). 387 * 388 * To use the legacy query, filter 'bp_use_legacy_group_member_query', 389 * returning true. 386 390 * 387 391 * @param int $group_id … … 393 397 * @return array Multi-d array of 'members' list and 'count' 394 398 */ 395 function groups_get_group_members( $group_id, $limit = false, $page = false, $exclude_admins_mods = true, $exclude_banned = true, $exclude = false ) { 396 return BP_Groups_Member::get_all_for_group( $group_id, $limit, $page, $exclude_admins_mods, $exclude_banned, $exclude ); 399 function groups_get_group_members( $group_id, $limit = false, $page = false, $exclude_admins_mods = true, $exclude_banned = true, $exclude = false, $group_role = false ) { 400 401 // For legacy users. Use of BP_Groups_Member::get_all_for_group() 402 // is deprecated. 403 if ( apply_filters( 'bp_use_legacy_group_member_query', false, __FUNCTION__, func_get_args() ) ) { 404 $retval = BP_Groups_Member::get_all_for_group( $group_id, $limit, $page, $exclude_admins_mods, $exclude_banned, $exclude ); 405 } else { 406 407 // exclude_admins_mods is a legacy argument. Convert to group_role 408 if ( empty( $group_role ) ) { 409 $group_role = $exclude_admins_mods ? array( 'member' ) : array( 'member', 'mod', 'admin' ); 410 } 411 412 // Perform the group member query (extends BP_User_Query) 413 $members = new BP_Group_Member_Query( array( 414 'group_id' => $group_id, 415 'per_page' => $limit, 416 'page' => $page, 417 'group_role' => $group_role, 418 'exclude_banned' => $exclude_banned, 419 'exclude' => $exclude, 420 'type' => 'last_modified', 421 ) ); 422 423 // Structure the return value as expected by the template functions 424 $retval = array( 425 'members' => array_values( $members->results ), 426 'count' => $members->total_users, 427 ); 428 } 429 430 return $retval; 397 431 } 398 432 -
trunk/bp-groups/bp-groups-template.php
r7091 r7141 1898 1898 var $total_group_count; 1899 1899 1900 function __construct( $group_id, $per_page, $max, $exclude_admins_mods, $exclude_banned, $exclude ) {1900 function __construct( $group_id, $per_page, $max, $exclude_admins_mods, $exclude_banned, $exclude, $group_role = false ) { 1901 1901 1902 1902 $this->pag_page = isset( $_REQUEST['mlpage'] ) ? intval( $_REQUEST['mlpage'] ) : 1; 1903 1903 $this->pag_num = isset( $_REQUEST['num'] ) ? intval( $_REQUEST['num'] ) : $per_page; 1904 $this->members = BP_Groups_Member::get_all_for_group( $group_id, $this->pag_num, $this->pag_page, $exclude_admins_mods, $exclude_banned, $exclude );1904 $this->members = groups_get_group_members( $group_id, $this->pag_num, $this->pag_page, $exclude_admins_mods, $exclude_banned, $exclude, $group_role ); 1905 1905 1906 1906 if ( !$max || $max >= (int) $this->members['count'] ) … … 1984 1984 'exclude' => false, 1985 1985 'exclude_admins_mods' => 1, 1986 'exclude_banned' => 1 1986 'exclude_banned' => 1, 1987 'group_role' => false, 1987 1988 ) ); 1988 1989 1989 $members_template = new BP_Groups_Group_Members_Template( $r['group_id'], $r['per_page'], $r['max'], (int) $r['exclude_admins_mods'], (int) $r['exclude_banned'], $r['exclude'] );1990 $members_template = new BP_Groups_Group_Members_Template( $r['group_id'], $r['per_page'], $r['max'], (int) $r['exclude_admins_mods'], (int) $r['exclude_banned'], $r['exclude'], $r['group_role'] ); 1990 1991 return apply_filters( 'bp_group_has_members', $members_template->has_members(), $members_template ); 1991 1992 } -
trunk/tests/includes/testcase.php
r7090 r7141 224 224 } 225 225 226 public static function add_user_to_group( $user_id, $group_id ) { 226 public static function add_user_to_group( $user_id, $group_id, $args = array() ) { 227 $r = wp_parse_args( $args, array( 228 'date_modified' => bp_core_current_time(), 229 ) ); 230 227 231 $new_member = new BP_Groups_Member; 228 232 $new_member->group_id = $group_id; … … 231 235 $new_member->is_admin = 0; 232 236 $new_member->user_title = ''; 233 $new_member->date_modified = bp_core_current_time();237 $new_member->date_modified = $r['date_modified']; 234 238 $new_member->is_confirmed = 1; 235 239 -
trunk/tests/testcases/groups/template.php
r7125 r7141 119 119 120 120 /** 121 * Switching from BP_Groups_Member to BP_Group_Member_Query meant a 122 * change in the format of the values returned from the query. For 123 * backward compatibility, we translate some of the return values 124 * of BP_Group_Member_Query to the older format. This test makes sure 125 * that the translation happens properly. 126 * 127 * @group bp_group_has_members 128 */ 129 public function test_bp_group_has_members_backpat_retval_format() { 130 $g = $this->factory->group->create(); 131 $u1 = $this->create_user(); 132 $u2 = $this->create_user(); 133 134 $date_modified = gmdate( 'Y-m-d H:i:s', time() - 100 ); 135 136 $new_member = new BP_Groups_Member; 137 $new_member->group_id = $g; 138 $new_member->user_id = $u1; 139 $new_member->inviter_id = $u2; 140 $new_member->is_admin = 0; 141 $new_member->user_title = ''; 142 $new_member->date_modified = $date_modified; 143 $new_member->is_confirmed = 1; 144 $new_member->save(); 145 146 global $members_template; 147 bp_group_has_members( array( 148 'group_id' => $g, 149 ) ); 150 151 $u1_object = new WP_User( $u1 ); 152 153 $expected = new stdClass; 154 $expected->user_id = $u1; 155 $expected->date_modified = $date_modified; 156 $expected->is_banned = 0; 157 $expected->user_login = $u1_object->user_login; 158 $expected->user_nicename = $u1_object->user_nicename; 159 $expected->user_email = $u1_object->user_email; 160 $expected->display_name = $u1_object->display_name; 161 162 // In order to use assertEquals, we need to discard the 163 // irrelevant properties of the found object. Hack alert 164 $found = new stdClass; 165 foreach ( array( 'user_id', 'date_modified', 'is_banned', 'user_login', 'user_nicename', 'user_email', 'display_name' ) as $key ) { 166 if ( isset( $members_template->members[0]->{$key} ) ) { 167 $found->{$key} = $members_template->members[0]->{$key}; 168 } 169 } 170 171 $this->assertEquals( $expected, $found ); 172 } 173 174 /** 121 175 * @group bp_group_has_members 122 176 */
Note: See TracChangeset
for help on using the changeset viewer.