| 1 | <?php |
| 2 | |
| 3 | require_once dirname( __FILE__ ) . '/factory.php'; |
| 4 | |
| 5 | class BBP_UnitTestCase extends WP_UnitTestCase { |
| 6 | |
| 7 | protected $cached_SERVER_NAME = null; |
| 8 | |
| 9 | public function setUp() { |
| 10 | parent::setUp(); |
| 11 | |
| 12 | // Make sure all users are deleted |
| 13 | // There's a bug in the multisite tests that causes the |
| 14 | // transaction rollback to fail for the first user created, |
| 15 | // which busts every other attempt to create users. This is a |
| 16 | // hack workaround |
| 17 | global $wpdb; |
| 18 | $wpdb->query( "TRUNCATE TABLE {$wpdb->users}" ); |
| 19 | |
| 20 | // Fake WP mail globals, to avoid errors |
| 21 | add_filter( 'wp_mail', array( $this, 'setUp_wp_mail' ) ); |
| 22 | add_filter( 'wp_mail_from', array( $this, 'tearDown_wp_mail' ) ); |
| 23 | |
| 24 | $this->factory = new BBP_UnitTest_Factory; |
| 25 | } |
| 26 | |
| 27 | function assertPreConditions() { |
| 28 | parent::assertPreConditions(); |
| 29 | |
| 30 | // Reinit some of the globals that might have been cleared by BBP_UnitTestCase::clean_up_global_scope(). |
| 31 | // This is here because it didn't work in clean_up_global_scope(); I don't know why. |
| 32 | do_action( 'bbp_setup_globals' ); |
| 33 | } |
| 34 | |
| 35 | function go_to( $url ) { |
| 36 | // note: the WP and WP_Query classes like to silently fetch parameters |
| 37 | // from all over the place (globals, GET, etc), which makes it tricky |
| 38 | // to run them more than once without very carefully clearing everything |
| 39 | $_GET = $_POST = array(); |
| 40 | foreach (array('query_string', 'id', 'postdata', 'authordata', 'day', 'currentmonth', 'page', 'pages', 'multipage', 'more', 'numpages', 'pagenow') as $v) { |
| 41 | if ( isset( $GLOBALS[$v] ) ) unset( $GLOBALS[$v] ); |
| 42 | } |
| 43 | $parts = parse_url($url); |
| 44 | if (isset($parts['scheme'])) { |
| 45 | // set the HTTP_HOST |
| 46 | $GLOBALS['_SERVER']['HTTP_HOST'] = $parts['host']; |
| 47 | |
| 48 | $req = $parts['path']; |
| 49 | if (isset($parts['query'])) { |
| 50 | $req .= '?' . $parts['query']; |
| 51 | // parse the url query vars into $_GET |
| 52 | parse_str($parts['query'], $_GET); |
| 53 | } |
| 54 | } else { |
| 55 | $req = $url; |
| 56 | } |
| 57 | if ( ! isset( $parts['query'] ) ) { |
| 58 | $parts['query'] = ''; |
| 59 | } |
| 60 | |
| 61 | // Scheme |
| 62 | if ( 0 === strpos( $req, '/wp-admin' ) && force_ssl_admin() ) { |
| 63 | $_SERVER['HTTPS'] = 'on'; |
| 64 | } else { |
| 65 | unset( $_SERVER['HTTPS'] ); |
| 66 | } |
| 67 | |
| 68 | // Set this for bbp_core_set_uri_globals() |
| 69 | $GLOBALS['_SERVER']['REQUEST_URI'] = $req; |
| 70 | unset($_SERVER['PATH_INFO']); |
| 71 | |
| 72 | // setup $current_site and $current_blog globals for multisite based on |
| 73 | // REQUEST_URI; mostly copied from /wp-includes/ms-settings.php |
| 74 | if ( is_multisite() ) { |
| 75 | $domain = addslashes( $_SERVER['HTTP_HOST'] ); |
| 76 | if ( false !== strpos( $domain, ':' ) ) { |
| 77 | if ( substr( $domain, -3 ) == ':80' ) { |
| 78 | $domain = substr( $domain, 0, -3 ); |
| 79 | $_SERVER['HTTP_HOST'] = substr( $_SERVER['HTTP_HOST'], 0, -3 ); |
| 80 | } elseif ( substr( $domain, -4 ) == ':443' ) { |
| 81 | $domain = substr( $domain, 0, -4 ); |
| 82 | $_SERVER['HTTP_HOST'] = substr( $_SERVER['HTTP_HOST'], 0, -4 ); |
| 83 | } |
| 84 | } |
| 85 | |
| 86 | $domain = rtrim( $domain, '.' ); |
| 87 | $cookie_domain = $domain; |
| 88 | if ( substr( $cookie_domain, 0, 4 ) == 'www.' ) |
| 89 | $cookie_domain = substr( $cookie_domain, 4 ); |
| 90 | |
| 91 | $path = preg_replace( '|([a-z0-9-]+.php.*)|', '', $GLOBALS['_SERVER']['REQUEST_URI'] ); |
| 92 | $path = str_replace ( '/wp-admin/', '/', $path ); |
| 93 | $path = preg_replace( '|(/[a-z0-9-]+?/).*|', '$1', $path ); |
| 94 | |
| 95 | $GLOBALS['current_site'] = wpmu_current_site(); |
| 96 | if ( ! isset( $GLOBALS['current_site']->blog_id ) ) |
| 97 | $GLOBALS['current_site']->blog_id = $wpdb->get_var( $wpdb->prepare( "SELECT blog_id FROM $wpdb->blogs WHERE domain = %s AND path = %s", $GLOBALS['current_site']->domain, $GLOBALS['current_site']->path ) ); |
| 98 | |
| 99 | // unit tests only support subdirectory install at the moment |
| 100 | // removed object cache references |
| 101 | if ( ! is_subdomain_install() ) { |
| 102 | $blogname = htmlspecialchars( substr( $GLOBALS['_SERVER']['REQUEST_URI'], strlen( $path ) ) ); |
| 103 | if ( false !== strpos( $blogname, '/' ) ) |
| 104 | $blogname = substr( $blogname, 0, strpos( $blogname, '/' ) ); |
| 105 | if ( false !== strpos( $blogname, '?' ) ) |
| 106 | $blogname = substr( $blogname, 0, strpos( $blogname, '?' ) ); |
| 107 | $reserved_blognames = array( 'page', 'comments', 'blog', 'wp-admin', 'wp-includes', 'wp-content', 'files', 'feed' ); |
| 108 | if ( $blogname != '' && ! in_array( $blogname, $reserved_blognames ) && ! is_file( $blogname ) ) |
| 109 | $path .= $blogname . '/'; |
| 110 | |
| 111 | $GLOBALS['current_blog'] = get_blog_details( array( 'domain' => $domain, 'path' => $path ), false ); |
| 112 | |
| 113 | unset($reserved_blognames); |
| 114 | } |
| 115 | |
| 116 | $GLOBALS['blog_id'] = $GLOBALS['current_blog']->blog_id; |
| 117 | } |
| 118 | |
| 119 | unset($GLOBALS['wp_query'], $GLOBALS['wp_the_query']); |
| 120 | $GLOBALS['wp_the_query'] = new WP_Query(); |
| 121 | $GLOBALS['wp_query'] = $GLOBALS['wp_the_query']; |
| 122 | $GLOBALS['wp'] = new WP(); |
| 123 | |
| 124 | // clean out globals to stop them polluting wp and wp_query |
| 125 | foreach ($GLOBALS['wp']->public_query_vars as $v) { |
| 126 | unset($GLOBALS[$v]); |
| 127 | } |
| 128 | foreach ($GLOBALS['wp']->private_query_vars as $v) { |
| 129 | unset($GLOBALS[$v]); |
| 130 | } |
| 131 | |
| 132 | $GLOBALS['wp']->main($parts['query']); |
| 133 | |
| 134 | // For bbPress, James. |
| 135 | $GLOBALS['bbp']->loggedin_user = NULL; |
| 136 | do_action( 'bbp_init' ); |
| 137 | } |
| 138 | |
| 139 | protected function checkRequirements() { |
| 140 | if ( WP_TESTS_FORCE_KNOWN_BUGS ) |
| 141 | return; |
| 142 | |
| 143 | parent::checkRequirements(); |
| 144 | |
| 145 | $tickets = PHPUnit_Util_Test::getTickets( get_class( $this ), $this->getName( false ) ); |
| 146 | foreach ( $tickets as $ticket ) { |
| 147 | if ( 'BBP' == substr( $ticket, 0, 2 ) ) { |
| 148 | $ticket = substr( $ticket, 2 ); |
| 149 | if ( $ticket && is_numeric( $ticket ) ) |
| 150 | $this->knownBBPBug( $ticket ); |
| 151 | } |
| 152 | } |
| 153 | } |
| 154 | |
| 155 | /** |
| 156 | * Skips the current test if there is an open BuddyPress ticket with id $ticket_id |
| 157 | */ |
| 158 | function knownBBPBug( $ticket_id ) { |
| 159 | if ( WP_TESTS_FORCE_KNOWN_BUGS || in_array( $ticket_id, self::$forced_tickets ) ) |
| 160 | return; |
| 161 | |
| 162 | if ( ! TracTickets::isTracTicketClosed( 'http://bbpress.trac.wordpress.org', $ticket_id ) ) |
| 163 | $this->markTestSkipped( sprintf( 'bbPress Ticket #%d is not fixed', $ticket_id ) ); |
| 164 | } |
| 165 | |
| 166 | /** |
| 167 | * WP's core tests use wp_set_current_user() to change the current |
| 168 | * user during tests. BBP caches the current user differently, so we |
| 169 | * have to do a bit more work to change it |
| 170 | * |
| 171 | * @global bbPres $bbp |
| 172 | */ |
| 173 | function set_current_user( $user_id ) { |
| 174 | global $bbp; |
| 175 | $bbp->loggedin_user->id = $user_id; |
| 176 | $bbp->loggedin_user->fullname = bbp_core_get_user_displayname( $user_id ); |
| 177 | $bbp->loggedin_user->is_super_admin = $bbp->loggedin_user->is_site_admin = is_super_admin( $user_id ); |
| 178 | |
| 179 | wp_set_current_user( $user_id ); |
| 180 | } |
| 181 | |
| 182 | /** |
| 183 | * When creating a new user, it's almost always necessary to have the |
| 184 | * last_activity usermeta set right away, so that the user shows up in |
| 185 | * directory queries. This is a shorthand wrapper for the user factory |
| 186 | * create() method. |
| 187 | * |
| 188 | * Also set a display name |
| 189 | */ |
| 190 | function create_user( $args = array() ) { |
| 191 | $r = wp_parse_args( $args, array( |
| 192 | 'role' => 'subscriber', |
| 193 | 'last_activity' => bbp_core_current_time() - 60*60*24*365, |
| 194 | ) ); |
| 195 | |
| 196 | $last_activity = $r['last_activity']; |
| 197 | unset( $r['last_activity'] ); |
| 198 | |
| 199 | $user_id = $this->factory->user->create( $args ); |
| 200 | |
| 201 | bbp_update_user_last_posted( $user_id, $last_activity ); |
| 202 | |
| 203 | return $user_id; |
| 204 | } |
| 205 | |
| 206 | /** |
| 207 | * We can't use grant_super_admin() because we will need to modify |
| 208 | * the list more than once, and grant_super_admin() can only be run |
| 209 | * once because of its global check |
| 210 | */ |
| 211 | public function grant_super_admin( $user_id ) { |
| 212 | global $super_admins; |
| 213 | if ( ! is_multisite() ) { |
| 214 | return; |
| 215 | } |
| 216 | |
| 217 | $user = get_userdata( $user_id ); |
| 218 | $super_admins[] = $user->user_login; |
| 219 | } |
| 220 | |
| 221 | public function restore_admins() { |
| 222 | // We assume that the global can be wiped out |
| 223 | // @see grant_super_admin() |
| 224 | unset( $GLOBALS['super_admins'] ); |
| 225 | } |
| 226 | |
| 227 | /** |
| 228 | * Set up globals necessary to avoid errors when using wp_mail() |
| 229 | */ |
| 230 | public function setUp_wp_mail( $args ) { |
| 231 | if ( isset( $_SERVER['SERVER_NAME'] ) ) { |
| 232 | $this->cached_SERVER_NAME = $_SERVER['SERVER_NAME']; |
| 233 | } |
| 234 | |
| 235 | $_SERVER['SERVER_NAME'] = 'example.com'; |
| 236 | |
| 237 | // passthrough |
| 238 | return $args; |
| 239 | } |
| 240 | |
| 241 | /** |
| 242 | * Tear down globals set up in setUp_wp_mail() |
| 243 | */ |
| 244 | public function tearDown_wp_mail( $args ) { |
| 245 | if ( ! empty( $this->cached_SERVER_NAME ) ) { |
| 246 | $_SERVER['SERVER_NAME'] = $this->cached_SERVER_NAME; |
| 247 | unset( $this->cached_SERVER_NAME ); |
| 248 | } else { |
| 249 | unset( $_SERVER['SERVER_NAME'] ); |
| 250 | } |
| 251 | |
| 252 | // passthrough |
| 253 | return $args; |
| 254 | } |
| 255 | } |