Skip to:
Content

BuddyPress.org

Ticket #8734: 8734.02.patch

File 8734.02.patch, 23.5 KB (added by dcavins, 3 years ago)

Beta site privacy patch, now calles "community visibility".

  • src/bp-core/admin/bp-core-admin-settings.php

    diff --git src/bp-core/admin/bp-core-admin-settings.php src/bp-core/admin/bp-core-admin-settings.php
    index a4ae985c8..ad43c3996 100644
    function bp_admin_setting_callback_account_deletion() { 
    4747<?php
    4848}
    4949
     50/**
     51 * Enable private site functionality.
     52 *
     53 * @since 12.0.0
     54 *
     55 */
     56function bp_admin_setting_callback_community_visibility() {
     57        $visibility      = bp_community_visibility_get_visibility();
     58        $directory_pages = bp_core_get_directory_pages();
     59?>
     60        <fieldset class="community-visibility-setting">
     61                <legend><?php esc_html_e( 'Global (Fallback) Setting', 'buddypress' ); ?></legend>
     62                <label for="_bp_community_visibility-global-anyone"><input type="radio" id="_bp_community_visibility-global-anyone" name="_bp_community_visibility[global]" value="anyone" <?php checked( $visibility['global'], 'anyone' ); ?>/> <?php esc_html_e( 'Anyone', 'buddypress' ); ?></label>
     63                <label for="_bp_community_visibility-global-members"><input type="radio" id="_bp_community_visibility-global-members" name="_bp_community_visibility[global]" value="members" <?php checked( $visibility['global'], 'members' ); ?>/> <?php esc_html_e( 'Members Only', 'buddypress' ); ?></label>
     64        </fieldset>
     65
     66        <?php foreach ( $directory_pages as $component_id => $component_page ) :
     67                // Register and Activate must not be private.
     68                if ( in_array( $component_id, array( 'register', 'activate' ) ) ) {
     69                        continue;
     70                }
     71                ?>
     72                <fieldset class="community-visibility-setting">
     73                        <legend><?php esc_html_e( $component_page->title, 'buddypress' ); ?></legend>
     74                        <label for="_bp_community_visibility-<?php echo esc_attr( $component_id ); ?>-anyone"><input type="radio" id="_bp_community_visibility-<?php echo esc_attr( $component_id ); ?>-anyone" name="_bp_community_visibility[<?php echo esc_attr( $component_id ); ?>]" value="anyone" <?php checked( $visibility[ $component_id ], 'anyone' ); ?>/> <?php esc_html_e( 'Anyone', 'buddypress' ); ?></label>
     75                        <label for="_bp_community_visibility-<?php echo esc_attr( $component_id ); ?>-members"><input type="radio" id="_bp_community_visibility-<?php echo esc_attr( $component_id ); ?>-members" name="_bp_community_visibility[<?php echo esc_attr( $component_id ); ?>]" value="members" <?php checked( $visibility[ $component_id ], 'members' ); ?>/> <?php esc_html_e( 'Members Only', 'buddypress' ); ?></label>
     76                </fieldset>
     77        <?php endforeach; ?>
     78
     79        <p id="_bp_community_visibility_description" class="description"><?php esc_html_e( 'Choose "Anyone" to allow any visitor access to your community area. Choose "Members" to restrict access to your community area to logged-in members only. The global setting is used when a more specific setting is not available.', 'buddypress' ); ?></p>
     80<?php
     81}
     82
    5083/**
    5184 * Form element to change the active template pack.
    5285 */
    function bp_admin_setting_callback_group_cover_image_uploads() { 
    306339<?php
    307340}
    308341
     342/** Community Visibility ******************************************************/
     343
     344/**
     345 * Groups settings section description for the settings page.
     346 *
     347 * @since 12.0.0
     348 */
     349function bp_admin_setting_callback_community_visibility_section() { }
     350
     351
    309352/** Settings Page *************************************************************/
    310353
    311354/**
  • src/bp-core/admin/css/common.css

    diff --git src/bp-core/admin/css/common.css src/bp-core/admin/css/common.css
    index 6b91fe18b..ffec45da8 100644
    body.bp-is-tabbed-screen #wpcontent { 
    713713                width: auto;
    714714        }
    715715}
     716
     717/* Community Visibility */
     718fieldset.community-visibility-setting {
     719        padding: 2px 6px;
     720}
     721fieldset.community-visibility-setting:nth-of-type(2n+1) {
     722        background: #fafafa;
     723}
     724fieldset.community-visibility-setting legend,
     725fieldset.community-visibility-setting label {
     726        float: left;
     727}
     728fieldset.community-visibility-setting legend {
     729        margin: 0.35em 0 0.5em;
     730        width: 50%;
     731        font-weight: 600;
     732}
     733fieldset.community-visibility-setting label {
     734        width: 24%;
     735}
  • src/bp-core/bp-core-caps.php

    diff --git src/bp-core/bp-core-caps.php src/bp-core/bp-core-caps.php
    index dd8288029..8f1dc573e 100644
    function bp_remove_caps() { 
    124124 * Map community caps to built in WordPress caps.
    125125 *
    126126 * @since 1.6.0
     127 * @since 12.0.0 Added mapping for `bp_read` capability.
    127128 *
    128129 * @see WP_User::has_cap() for description of the arguments passed to the
    129130 *      'map_meta_cap' filter.
    function bp_remove_caps() { 
    137138 */
    138139function bp_map_meta_caps( $caps, $cap, $user_id, $args ) {
    139140
     141        switch ( $cap ) {
     142                case 'bp_read' :
     143                        $caps = array( 'exist' );
     144                        break;
     145        }
     146
    140147        /**
    141148         * Filters the community caps mapping to be built in WordPress caps.
    142149         *
  • new file src/bp-core/bp-core-community-visibility.php

    diff --git src/bp-core/bp-core-community-visibility.php src/bp-core/bp-core-community-visibility.php
    new file mode 100644
    index 000000000..93c5e49ef
    - +  
     1<?php
     2/**
     3 * Core community visibility functions.
     4 *
     5 * @package BuddyPress
     6 * @subpackage CommunityVisibility
     7 * @since 12.0.0
     8 */
     9
     10// Exit if accessed directly.
     11defined( 'ABSPATH' ) || exit;
     12
     13/**
     14 * The main change on a private site is that visitors who are not
     15 * logged in may not have the `bp_read` capability.
     16 *
     17 * @since 12.0.0
     18 *
     19 * @param bool   $retval     Whether or not the current user has the capability.
     20 * @param int    $user_id
     21 * @param string $capability The capability being checked for.
     22 * @param int    $site_id    Site ID. Defaults to the BP root blog.
     23 * @param array  $args       Array of extra arguments passed.
     24 *
     25 * @return bool
     26 */
     27function bp_community_visibility_user_can_filter( $retval, $user_id, $capability, $site_id, $args ) {
     28        switch ( $capability ) {
     29                case 'bp_read':
     30                        if ( ! $user_id ) {
     31                                $component = $args['bp_component'] ?? '';
     32
     33                                if ( $component && 'members' === bp_community_visibility_get_visibility( $component ) ) {
     34                                        $retval = false;
     35                                }
     36
     37                                /**
     38                                 * Filters the private site capability.
     39                                 *
     40                                 * @since 12.0.0
     41                                 *
     42                                 * @param bool   $retval     Whether or not the current user has the capability.
     43                                 * @param int    $user_id
     44                                 * @param string $capability The capability being checked for.
     45                                 * @param int    $site_id    Site ID. Defaults to the BP root blog.
     46                                 * @param array  $args       Array of extra arguments passed.
     47                                 */
     48                                $retval = apply_filters( 'bp_private_site_user_can_filter', $retval, $user_id, $capability, $site_id, $args );
     49                        }
     50                        break;
     51        }
     52
     53        return $retval;
     54}
     55add_filter( 'bp_user_can', 'bp_community_visibility_user_can_filter', 10, 5 );
     56
     57/**
     58 * Set default permissions for the BP REST API.
     59 *
     60 * @since 12.0.0
     61 */
     62function bp_community_visibility_rest_set_default_permission_checks() {
     63        $visibility_settings = bp_community_visibility_get_visibility();
     64
     65        foreach ( $visibility_settings as $component_id => $setting ) {
     66                if ( 'global' === $component_id || 'anyone' === $setting ) {
     67                        continue;
     68                }
     69
     70                if ( 'xprofiles' === $component_id ) {
     71                        add_filter( 'bp_rest_xprofile_field_groups_get_items_permissions_check', 'bp_community_visibility_rest_check_default_permission', 1, 2 );
     72                        add_filter( 'bp_rest_xprofile_fields_get_items_permissions_check', 'bp_community_visibility_rest_check_default_permission', 1, 2 );
     73                } else {
     74                        add_filter( "bp_rest_{$component_id}_get_items_permissions_check", 'bp_community_visibility_rest_check_default_permission', 1, 2 );
     75                }
     76        }
     77}
     78add_action( 'bp_rest_api_init', 'bp_community_visibility_rest_set_default_permission_checks', 1 );
     79
     80/**
     81 * Checks if a natively "public" BP REST request can be performed.
     82 *
     83 * @since 12.0.0
     84 *
     85 * @param true            $retval  Returned value.
     86 * @param WP_REST_Request $request The request sent to the API.
     87 * @return bool True if the user has access. False otherwise.
     88 */
     89function bp_community_visibility_rest_check_default_permission( $retval, $request ) {
     90        $path         = wp_parse_url( $request->get_route(), PHP_URL_PATH );
     91        $component_id = trim( str_replace( bp_rest_namespace() . '/' . bp_rest_version(), '', trim( $path, '/' ) ), '/' );
     92        $args         = array();
     93
     94        if ( $component_id ) {
     95                $args['bp_component'] = $component_id;
     96        }
     97
     98        return bp_current_user_can( 'bp_read', $args );
     99}
     100
     101/**
     102 * Should RSS feeds for activity be enabled?
     103 *
     104 * @since 12.0.0
     105 *
     106 * @param bool   $feed_enabled True if feeds are enabled. Default true.
     107 * @param string $feed_id      The feed identifier.
     108 */
     109function bp_community_visibility_rss_feed_access_protection( $feed_enabled, $feed_id ) {
     110        // @TODO: I'm not sure this is adequate, since feeds are about other components, too.
     111        // From the hook, "possible feed_ids are 'sitewide', 'personal', 'friends', 'mygroups', 'mentions', 'favorites'"
     112        // Which component should those other items refer to?
     113        if ( ! bp_current_user_can( 'bp_read', array( 'bp_component' => 'activity' ) ) ) {
     114                /**
     115                 * Allow plugins to allow specific feeds even when community visibility is limited.
     116                 *
     117                 * @since 12.0.0
     118                 *
     119                 * @param bool  $feed_enabled True to allow access to the feed.
     120                 * @param array $feed_id      The feed identifier.
     121                 */
     122                $feed_enabled = apply_filters( 'bp_community_visibility_rss_feed_access_protection', false, $feed_id );
     123        }
     124        return $feed_enabled;
     125}
     126add_filter( 'bp_activity_enable_feeds', 'bp_community_visibility_rss_feed_access_protection', 10, 2 );
     127
     128/**
     129 * Get the community visibility value calculated from the
     130 * saved visibility setting.
     131 *
     132 * @since 12.0.0
     133 *
     134 * @param string $component Whether we want the visibility for a component
     135 *                          or for all components.
     136 *
     137 * @return arrary|string $retval The calculated visbility settings for the site.
     138 */
     139function bp_community_visibility_get_visibility( $component = 'all' ) {
     140        $retval      = 'anyone';
     141        $saved_value = get_option( '_bp_community_visibility' );
     142
     143        // If the global value has not been set, we assume that the site is open.
     144        if ( ! isset( $saved_value['global'] ) ) {
     145                $saved_value['global'] = 'anyone';
     146        }
     147
     148        if ( 'all' === $component ) {
     149                // Build the component list.
     150                $retval = array(
     151                        'global' => $saved_value['global']
     152                );
     153                $directory_pages = bp_core_get_directory_pages();
     154                foreach ( $directory_pages as $component_id => $component_page ) {
     155                        if ( in_array( $component_id, array( 'register', 'activate' ), true ) ) {
     156                                continue;
     157                        }
     158                        $retval[ $component_id ] = $saved_value[ $component_id ] ?? $saved_value['global'];
     159                }
     160        } else {
     161                // We are checking a particular component.
     162                // Fall back to the global value if not set.
     163                $retval = $saved_value[ $component ] ?? $saved_value['global'];
     164        }
     165
     166        /**
     167         * Filter the community visibility value calculated from the
     168         * saved visibility setting.
     169         *
     170         * @since 12.0.0
     171         *
     172         * @param arrary|string $retval    The calculated visbility settings for the site.
     173         * @param string        $component The component value to get the visibility for.
     174         */
     175        return apply_filters( 'bp_community_visibility_get_visibility', $retval, $component );
     176}
     177
     178/**
     179 * Sanitize the visibility setting when it is saved.
     180 *
     181 * @since 12.0.0
     182 *
     183 * @param mixed $saved_value The value passed to the save function.
     184 */
     185function bp_community_visibility_sanitize_setting( $saved_value ) {
     186        $retval = array();
     187
     188        // Use the global setting, if it has been passed.
     189        $retval['global'] = $saved_value['global'] ?? 'anyone';
     190        // Ensure the global value is a valid option. Else, assume that the site is open.
     191        if ( ! in_array( $retval['global'], array( 'anyone', 'members' ), true ) ) {
     192                $retval['global'] = 'anyone';
     193        }
     194
     195        // Keys must be either 'global' or a component ID, but not register or activate.
     196        $directory_pages = bp_core_get_directory_pages();
     197        foreach ( $directory_pages as $component_id => $component_page ) {
     198                if ( in_array( $component_id, array( 'register', 'activate' ), true ) ) {
     199                        continue;
     200                }
     201
     202                // Use the global value if a specific value hasn't been set.
     203                $component_value = $saved_value[ $component_id ] ?? $retval['global'];
     204
     205                // Valid values are 'anyone' or 'memebers'.
     206                if ( ! in_array( $component_value, array( 'anyone', 'members' ), true ) ) {
     207                        $component_value = $retval['global'];
     208                }
     209                $retval[ $component_id ] = $component_value;
     210        }
     211
     212        return $saved_value;
     213}
  • src/bp-core/bp-core-functions.php

    diff --git src/bp-core/bp-core-functions.php src/bp-core/bp-core-functions.php
    index b6ae3455d..68adf0672 100644
    function bp_core_get_directory_page_id( $component = null ) { 
    668668        return $page_id;
    669669}
    670670
     671/**
     672 * Get the component ID corresponding to a directory page ID.
     673 *
     674 * @since 12.0.0
     675 *
     676 * @param int $page_id The ID of the directory page associated with the component.
     677 * @return int|false The slug representing the component. False if none is found.
     678 */
     679function bp_core_get_component_from_directory_page_id( $page_id = 0 ) {
     680        $bp_pages = bp_core_get_directory_page_ids( 'all' );
     681
     682        $component = false;
     683        foreach ( $bp_pages as $component_id => $p_id) {
     684                if ( $page_id === $p_id ) {
     685                        $component = $component_id;
     686                        break;
     687                }
     688        }
     689
     690        return $component;
     691}
     692
    671693/**
    672694 * Store the list of BP directory pages in the appropriate meta table.
    673695 *
  • src/bp-core/classes/class-bp-admin.php

    diff --git src/bp-core/classes/class-bp-admin.php src/bp-core/classes/class-bp-admin.php
    index 173219099..dcbc2e369 100644
    class BP_Admin { 
    562562                                register_setting( 'buddypress', '_bp_enable_akismet', 'intval' );
    563563                        }
    564564                }
     565
     566                /* Community Visibility ************************************************/
     567                add_settings_section( 'bp_community_visibility', __( 'Community Visibility', 'buddypress' ), 'bp_admin_setting_callback_community_visibility_section', 'buddypress' );
     568
     569                add_settings_field( '_bp_community_visibility', __( 'Visibility by Component', 'buddypress' ), 'bp_admin_setting_callback_community_visibility', 'buddypress', 'bp_community_visibility' );
     570                register_setting( 'buddypress', '_bp_community_visibility', 'bp_community_visibility_sanitize_setting' );
    565571        }
    566572
    567573        /**
  • src/bp-core/classes/class-bp-component.php

    diff --git src/bp-core/classes/class-bp-component.php src/bp-core/classes/class-bp-component.php
    index 80adaf668..1f810a213 100644
    class BP_Component { 
    12681268                $queried_object = $query->get_queried_object();
    12691269
    12701270                if ( $queried_object instanceof WP_Post && 'buddypress' === get_post_type( $queried_object ) ) {
    1271                         // Only include the queried directory post into returned posts.
    1272                         $retval = array( $queried_object );
    1273 
    1274                         // Reset some query flags.
    1275                         $query->is_home       = false;
    1276                         $query->is_front_page = false;
    1277                         $query->is_page       = false;
    1278                         $query->is_archive    = false;
    1279                         $query->is_tax        = false;
    1280 
    1281                         if ( ! is_embed() ) {
    1282                                 $query->is_single = true;
     1271                        $component = bp_core_get_component_from_directory_page_id( $queried_object->ID );
     1272                        if ( $component && bp_current_user_can( 'bp_read', array( 'bp_component' => $component ) ) ) {
     1273                                // Only include the queried directory post into returned posts.
     1274                                $retval = array( $queried_object );
     1275
     1276                                // Reset some query flags.
     1277                                $query->is_home       = false;
     1278                                $query->is_front_page = false;
     1279                                $query->is_page       = false;
     1280                                $query->is_archive    = false;
     1281                                $query->is_tax        = false;
     1282
     1283                                if ( ! is_embed() ) {
     1284                                        $query->is_single = true;
     1285                                }
     1286                        } else {
     1287                                // The current user may not access the directory page.
     1288                                $bp                    = buddypress();
     1289                                $bp->current_component = 'core';
     1290
     1291                                // Unset other BuddyPress URI globals.
     1292                                foreach ( array( 'current_item', 'current_action', 'action_variables', 'displayed_user' ) as $global ) {
     1293                                        if ( 'action_variables' === $global ) {
     1294                                                $bp->{$global} = array();
     1295                                        } elseif ( 'displayed_user' === $global ) {
     1296                                                $bp->{$global} = new \stdClass();
     1297                                        } else {
     1298                                                $bp->{$global} = '';
     1299                                        }
     1300                                }
     1301
     1302                                // Reset the post.
     1303                                $post = (object) array(
     1304                                        'ID'             => 0,
     1305                                        'post_type'      => 'buddypress',
     1306                                        'post_name'      => 'restricted',
     1307                                        'post_title'     => __( 'Members-only area', 'bp-rewrites' ),
     1308                                        'post_content'   => bp_buffer_template_part( 'assets/utils/restricted-access-message', null, false ),
     1309                                        'comment_status' => 'closed',
     1310                                        'comment_count'  => 0,
     1311                                );
     1312
     1313                                // Reset the queried object.
     1314                                $query->queried_object    = get_post( $post );
     1315                                $query->queried_object_id = $query->queried_object->ID;
     1316
     1317                                // Reset the posts.
     1318                                $retval = array( $query->queried_object );
     1319
     1320                                // Reset some WP Query properties.
     1321                                $query->found_posts   = 1;
     1322                                $query->max_num_pages = 1;
     1323                                $query->posts         = $posts;
     1324                                $query->post          = $post;
     1325                                $query->post_count    = 1;
     1326                                $query->is_home       = false;
     1327                                $query->is_front_page = false;
     1328                                $query->is_page       = false;
     1329                                $query->is_single     = true;
     1330                                $query->is_archive    = false;
     1331                                $query->is_tax        = false;
     1332
     1333                                // Make sure no comments are displayed for this page.
     1334                                add_filter( 'comments_pre_query', 'bp_comments_pre_query', 10, 2 );
     1335
     1336                                // @TODO: From bp-rewrites, meant to improve the button coloration.
     1337                                // if ( function_exists( 'wp_get_global_styles' ) ) {
     1338                                //      add_action( 'bp_enqueue_community_scripts', __NAMESPACE__ . '\add_bp_login_block_inline_style' );
     1339                                // }
    12831340                        }
    1284                 }
    12851341
    1286                 return $retval;
     1342                        return $retval;
     1343                }
    12871344        }
    12881345
    12891346        /**
  • new file src/bp-templates/bp-legacy/buddypress/assets/utils/restricted-access-message.php

    diff --git src/bp-templates/bp-legacy/buddypress/assets/utils/restricted-access-message.php src/bp-templates/bp-legacy/buddypress/assets/utils/restricted-access-message.php
    new file mode 100644
    index 000000000..aaf58ccc3
    - +  
     1<?php
     2/**
     3 * Message to inform the community is restricted to members.
     4 *
     5 * @package BuddyPress
     6 * @subpackage bp-legacy
     7 *
     8 * @since 12.0.0
     9 */
     10
     11// Exit if accessed directly.
     12if ( ! defined( 'ABSPATH' ) ) {
     13        exit;
     14}
     15?>
     16<!-- wp:paragraph {"align":"center"} -->
     17<p class="has-text-align-center"><?php esc_html_e( 'This community area is accessible to logged-in members only.', 'bp-rewrites' ); ?></p>
     18<!-- /wp:paragraph -->
     19
     20<!-- wp:columns -->
     21<div class="wp-block-columns"><!-- wp:column {"width":"25%"} -->
     22<div class="wp-block-column" style="flex-basis:25%"></div>
     23<!-- /wp:column -->
     24
     25<!-- wp:column {"width":"50%"} -->
     26<div class="wp-block-column" style="flex-basis:50%"><!-- wp:bp/login-form {"forgotPwdLink":true} /--></div>
     27<!-- /wp:column -->
     28
     29<!-- wp:column {"width":"25%"} -->
     30<div class="wp-block-column" style="flex-basis:25%"></div>
     31<!-- /wp:column --></div>
     32<!-- /wp:columns -->
  • new file src/bp-templates/bp-nouveau/buddypress/assets/utils/restricted-access-message.php

    diff --git src/bp-templates/bp-nouveau/buddypress/assets/utils/restricted-access-message.php src/bp-templates/bp-nouveau/buddypress/assets/utils/restricted-access-message.php
    new file mode 100644
    index 000000000..fc7ff8553
    - +  
     1<?php
     2/**
     3 * Message to inform the community is restricted to members.
     4 *
     5 * @package BuddyPress
     6 * @subpackage bp-nouveau
     7 *
     8 * @since 12.0.0
     9 */
     10
     11// Exit if accessed directly.
     12if ( ! defined( 'ABSPATH' ) ) {
     13        exit;
     14}
     15?>
     16<!-- wp:paragraph {"align":"center"} -->
     17<p class="has-text-align-center"><?php esc_html_e( 'This community area is accessible to logged-in members only.', 'bp-rewrites' ); ?></p>
     18<!-- /wp:paragraph -->
     19
     20<!-- wp:columns -->
     21<div class="wp-block-columns"><!-- wp:column {"width":"25%"} -->
     22<div class="wp-block-column" style="flex-basis:25%"></div>
     23<!-- /wp:column -->
     24
     25<!-- wp:column {"width":"50%"} -->
     26<div class="wp-block-column" style="flex-basis:50%"><!-- wp:bp/login-form {"forgotPwdLink":true} /--></div>
     27<!-- /wp:column -->
     28
     29<!-- wp:column {"width":"25%"} -->
     30<div class="wp-block-column" style="flex-basis:25%"></div>
     31<!-- /wp:column --></div>
     32<!-- /wp:columns -->
  • src/class-buddypress.php

    diff --git src/class-buddypress.php src/class-buddypress.php
    index a088e4cea..40b31041f 100644
    class BuddyPress { 
    644644                require $this->plugin_dir . 'bp-core/bp-core-customizer-email.php';
    645645                require $this->plugin_dir . 'bp-core/bp-core-rest-api.php';
    646646                require $this->plugin_dir . 'bp-core/bp-core-blocks.php';
     647                require $this->plugin_dir . 'bp-core/bp-core-community-visibility.php';
    647648
    648649                // Get the list of versions needing their deprecated functions to be loaded.
    649650                $deprecated_functions_versions = bp_get_deprecated_functions_versions();
  • new file tests/phpunit/testcases/core/community-visibility.php

    diff --git tests/phpunit/testcases/core/community-visibility.php tests/phpunit/testcases/core/community-visibility.php
    new file mode 100644
    index 000000000..1ceec4171
    - +  
     1<?php
     2/**
     3 * @group bp_community_visibility
     4 */
     5class BP_Tests_BP_Community_Visibility_TestCases extends BP_UnitTestCase {
     6        protected $old_user;
     7        protected $logged_in_user;
     8
     9        public function set_up() {
     10                parent::set_up();
     11                $this->old_user = get_current_user_id();
     12                $this->logged_in_user = self::factory()->user->create();
     13                $this->set_current_user( $this->logged_in_user );
     14
     15                // Save a typical setting.
     16                $setting = array(
     17                        'global'      => 'anyone',
     18                        'members'     => 'anyone',
     19                        'attachments' => 'anyone',
     20                        'activity'    => 'members',
     21                        'groups'      => 'members'
     22                );
     23                update_option( '_bp_community_visibility', $setting );
     24        }
     25
     26        public function tear_down() {
     27                parent::tear_down();
     28                $this->set_current_user( $this->old_user );
     29        }
     30
     31        // Test that logged-in user has access to component marked anyone and component marked members
     32        public function test_bp_community_visibility_allow_visibility_for_logged_in_user() {
     33                $this->assertTrue( bp_user_can( $this->logged_in_user, 'bp_read', array( 'bp_component' => 'members' ) ) );
     34                $this->assertTrue( bp_user_can( $this->logged_in_user, 'bp_read', array( 'bp_component' => 'groups' ) ) );
     35        }
     36
     37        // Test that anonymous user has access to component marked anyone but not component marked members
     38        public function test_bp_community_visibility_enforce_visibility_for_anon_user() {
     39                $this->assertTrue( bp_user_can( 0, 'bp_read', array( 'bp_component' => 'members' ) ) );
     40                $this->assertFalse( bp_user_can( 0, 'bp_read', array( 'bp_component' => 'groups' ) ) );
     41        }
     42
     43        // No component or bad component should be open.
     44        public function test_bp_community_visibility_bad_component_id() {
     45                $this->assertTrue( bp_user_can( 0, 'bp_read' ) );
     46                $this->assertTrue( bp_user_can( $this->logged_in_user, 'bp_read' ) );
     47                $this->assertTrue( bp_user_can( 0, 'bp_read', array( 'bp_component' => 'blerg' ) ) );
     48                $this->assertTrue( bp_user_can( $this->logged_in_user, 'bp_read', array( 'bp_component' => 'blerg' ) ) );
     49        }
     50
     51        // No saved setting should be open access for anonymous users and logged in users.
     52        public function test_bp_community_visibility_no_saved_setting() {
     53                delete_option( '_bp_community_visibility' );
     54                // No saved setting should result in the site being open to anyone.
     55                $this->assertTrue( bp_user_can( 0, 'bp_read', array( 'bp_component' => 'groups' ) ) );
     56                $this->assertTrue( bp_user_can( $this->logged_in_user, 'bp_read', array( 'bp_component' => 'groups' ) ) );
     57        }
     58
     59        // Make sure fallback logic works for mixed-up setting values.
     60        public function test_bp_community_visibility_fallback_setting() {
     61                // Save a partial setting.
     62                $setting = array(
     63                        'global'      => 'members',
     64                        'members'     => 'anyone',
     65                );
     66                update_option( '_bp_community_visibility', $setting );
     67                $this->assertTrue( 'members' === bp_community_visibility_get_visibility( 'groups' ) );
     68        }
     69}