diff --git bp-core/admin/bp-core-functions.php bp-core/admin/bp-core-functions.php
index e47e7da..d8e979b 100644
--- bp-core/admin/bp-core-functions.php
+++ bp-core/admin/bp-core-functions.php
@@ -271,6 +271,8 @@ function bp_core_activation_notice() {
 			'id'   => 'register',
 			'name' => __( 'Register', 'buddypress' )
 		);
+
+		bp_core_maybe_install_signups();
 	}
 
 	// On the first admin screen after a new installation, this isn't set, so grab it to supress a misleading error message.
@@ -785,3 +787,32 @@ function bp_admin_wp_nav_menu_restrict_items() {
 	</script>
 <?php
 }
+
+/**
+ * Checks if the signups table needs to be created
+ *
+ * @since BuddyPress (2.0.0)
+ * 
+ * @global $wpdb
+ */
+function bp_core_maybe_install_signups() {
+	global $wpdb;
+
+	// Multisite allready have signups table
+	if ( ! empty( $wpdb->signups ) )
+		return;
+
+	$bp_signups = bp_core_get_table_prefix() . 'signups';
+
+	$suppress = $wpdb->suppress_errors();
+	$table_exists = $wpdb->get_results("DESCRIBE {$bp_signups};");
+	$wpdb->suppress_errors( $suppress );
+
+	if ( ! empty( $table_exists ) )
+		return;
+
+	// Signups is not there and we need it so let's create it
+	require_once( buddypress()->plugin_dir . '/bp-core/admin/bp-core-schema.php' );
+	
+	bp_core_install_signups();
+}
diff --git bp-core/admin/bp-core-schema.php bp-core/admin/bp-core-schema.php
index a082d87..dd9f06f 100644
--- bp-core/admin/bp-core-schema.php
+++ bp-core/admin/bp-core-schema.php
@@ -50,6 +50,10 @@ function bp_core_install( $active_components = false ) {
 	// Blog tracking
 	if ( !empty( $active_components['blogs'] ) )
 		bp_core_install_blog_tracking();
+
+	if ( bp_get_signup_allowed() )
+		bp_core_install_signups();
+
 }
 
 function bp_core_install_notifications() {
@@ -343,3 +347,42 @@ function bp_core_install_blog_tracking() {
 
 	dbDelta( $sql );
 }
+
+/**
+ * Installs the signups table
+ *
+ * @since BuddyPress (2.0.0)
+ * 
+ * @global $wpdb
+ * @uses wp_get_db_schema() to get WordPress ms_global schema
+ */
+function bp_core_install_signups() {
+	global $wpdb;
+
+	// Multisite allready have signups table
+	if ( ! empty( $wpdb->signups ) )
+		return;
+
+	$sql             = array();
+	$charset_collate = bp_core_set_charset();
+	$bp_prefix       = bp_core_get_table_prefix();
+
+	$wpdb->signups = $bp_prefix . 'signups';
+
+	$create_queries = wp_get_db_schema( 'ms_global' );
+
+	if ( ! is_array( $create_queries ) ) {
+		$create_queries = explode( ';', $create_queries );
+		$create_queries = array_filter( $create_queries );
+	}
+
+	foreach ( $create_queries as $key => $query ) {
+		if ( preg_match( "|CREATE TABLE ([^ ]*)|", $query, $matches ) ) {
+			if ( $wpdb->signups != trim( $matches[1], '`' ) )
+				unset( $create_queries[ $key ] );
+		}
+	}
+
+	if ( ! empty( $create_queries ) )
+		dbDelta( $create_queries );
+}
diff --git bp-core/bp-core-classes.php bp-core/bp-core-classes.php
index 43c1afe..9283133 100644
--- bp-core/bp-core-classes.php
+++ bp-core/bp-core-classes.php
@@ -2385,3 +2385,687 @@ class BP_Walker_Nav_Menu_Checklist extends Walker_Nav_Menu {
 		$output .= '<input type="hidden" class="menu-item-xfn" name="menu-item[' . $possible_object_id . '][menu-item-xfn]" value="'. esc_attr( $item->xfn ) .'" />';
 	}
 }
+
+/**
+ * Signups Management class.
+ *
+ * @package BuddyPress
+ * @subpackage coreClasses
+ *
+ * @since BuddyPress (2.0.0)
+ */
+class BP_Core_SignUp {
+
+	/**
+	 * ID of the signup which the object relates to.
+	 *
+	 * @var integer
+	 */
+	public $id;
+
+	/**
+	 * The URL to the full size of the avatar for the user.
+	 *
+	 * @var string
+	 */
+	public $avatar;
+
+	/**
+	 * The username for the user.
+	 *
+	 * @var string
+	 */
+	public $user_login;
+
+	/**
+	 * The email for the user.
+	 *
+	 * @var string
+	 */
+	public $user_email;
+
+	/**
+	 * The full name of the user
+	 *
+	 * @var string
+	 */
+	public $user_name;
+
+	/**
+	 * The registered date for the user.
+	 *
+	 * @var string
+	 */
+	public $registered;
+
+	/**
+	 * The activation key for the user.
+	 *
+	 * @var string
+	 */
+	public $activation_key;
+
+
+	/** Public Methods *******************************************************/
+
+	/**
+	 * Class constructor.
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 *
+	 * @param integer $signup_id The ID for the signup being queried.
+	 */
+	public function __construct( $signup_id = 0 ) {
+		if ( !empty( $signup_id ) ) {
+			$this->id = $signup_id;
+			$this->populate();
+		}
+	}
+
+	/**
+	 * Populate the instantiated class with data based on the signup_id provided.
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 */
+	public function populate() {
+		global $wpdb;
+		$signups_table = buddypress()->members->table_name_signups;
+		$signup = $wpdb->get_row( $wpdb->prepare( "SELECT * FROM {$signups_table} WHERE signup_id = %d AND active = 0", $this->id ) );
+
+		$this->avatar     = get_avatar( $signup->user_email, 32 );
+		$this->user_login = $signup->user_login;
+		$this->user_email = $signup->user_email;
+		$meta = maybe_unserialize( $signup->meta );
+		$this->user_name = '';
+
+		if ( ! empty( $meta['field_1'] ) )
+			$this->user_name   = esc_html( wp_unslash( $meta['field_1'] ) );
+
+		$this->registered = $signup->registered;
+
+	}
+
+	/** Static Methods *******************************************************/
+
+	/**
+	 * Populate the instantiated class with data based on the signup_id provided.
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param array $args the argument to retrieve desired signups
+	 * @static
+	 */
+	public static function get( $args = array() ) {
+		global $wpdb;
+
+		$r = bp_parse_args( $args, 
+			array(
+				'offset'     => 0, 
+				'number'     => 1, 
+				'usersearch' => false, 
+				'orderby'    => 'signup_id', 
+				'order'      => 'DESC',
+				'include'    => false
+			),
+			'bp_core_signups_get_args'
+		);
+
+		extract( $r, EXTR_SKIP );
+
+		if ( $orderby != 'signup_id' )
+			$orderby = 'user_' . $orderby;
+
+		$orderby = sanitize_title( $orderby );
+
+		$sql = array();
+		$signups_table = buddypress()->members->table_name_signups;
+		$sql['select'] 	= "SELECT * FROM {$signups_table}";
+		$sql['where'] 	= "WHERE active = 0";
+
+		if ( empty( $include ) ) {
+			if ( ! empty( $usersearch ) ) {
+				$search_terms_clean = mysql_real_escape_string( mysql_real_escape_string( $usersearch ) );
+				$search_terms_clean = like_escape( $search_terms_clean );
+				$sql['search'] = "AND ( user_login LIKE '%" . $search_terms_clean . "%' OR user_email LIKE '%" . $search_terms_clean . "%' OR meta LIKE '%" . $search_terms_clean . "%' )";
+			}
+
+			$sql['orderby'] = "ORDER BY {$orderby}";
+			$sql['order']	= strtoupper( $order );
+			$sql['limit']	= $wpdb->prepare( "LIMIT %d, %d", $offset, $number );
+		} else {
+			$in = implode( ',', wp_parse_id_list( $include ) );
+			$sql['in'] = "AND signup_id IN ({$in})";
+		}
+
+		$paged_signups = $wpdb->get_results( apply_filters( 'bp_members_signups_paged_query', join( ' ', $sql ), $sql, $args, $r ) );
+
+		if ( empty( $paged_signups ) )
+			return array( 'signups' => false, 'total' => false );
+
+		foreach ( (array) $paged_signups as $key => $signup ) {
+
+			$signup->id = intval( $signup->signup_id );
+
+			$meta = !empty( $signup->meta ) ? maybe_unserialize( $signup->meta ) : false;
+
+			$signup->user_name = '';
+
+			if ( ! empty( $meta['field_1'] ) )
+				$signup->user_name  = esc_html( wp_unslash( $meta['field_1'] ) );
+
+			if ( ! empty( $meta['sent_date'] ) ) {
+				$signup->date_sent = $meta['sent_date'];
+			// Defaults to date of registration
+			} else {
+				$signup->date_sent = $signup->registered;
+			}
+
+			if ( ! empty( $meta['count_sent'] ) ) {
+				$signup->count_sent = absint( $meta['count_sent'] );
+			// Defaults to date of registration
+			} else {
+				$signup->count_sent = 1;
+			}
+
+			$paged_signups[ $key ] = $signup;
+		}
+
+		unset( $sql['limit'] );
+		$sql['select'] = preg_replace( "/SELECT.*?FROM/", "SELECT COUNT(*) FROM", $sql['select'] );
+		$total_signups = $wpdb->get_var( apply_filters( 'bp_members_signups_count_query', join( ' ', $sql ), $sql, $args, $r ) );
+
+		return array( 'signups' => $paged_signups, 'total' => $total_signups );
+	}
+
+	/**
+	 * Get a specific signup thanks to registration key.
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param string $key
+	 * @return object the queried data for the signup
+	 * @static
+	 */
+	public static function get_by_key( $key = '' ) {
+		global $wpdb;
+
+		if ( empty( $key ) )
+			return false;
+
+		$signups_table = buddypress()->members->table_name_signups;
+		$signup = $wpdb->get_row( $wpdb->prepare( "SELECT * FROM {$signups_table} WHERE activation_key = %s", $key ) );
+
+		return apply_filters( 'bp_core_signups_get_by_key', $signup );
+	}
+
+	/**
+	 * Get a specific signup id thanks to user login.
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param string $user_login
+	 * @return object the queried data for the signup
+	 * @static
+	 */
+	public static function get_by_userlogin( $user_login = '' ) {
+		global $wpdb;
+
+		if ( empty( $user_login ) )
+			return false;
+
+		$signups_table = buddypress()->members->table_name_signups;
+		$signup = $wpdb->get_row( $wpdb->prepare( "SELECT signup_id FROM {$signups_table} WHERE user_login = %s", $user_login ) );
+
+		return apply_filters( 'bp_core_signups_get_by_userlogin', $signup );
+	}
+
+	/**
+	 * Get a specific signup thanks to its id.
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param int $signup_id
+	 * @return object the queried data for the signup
+	 * @static
+	 */
+	public static function get_specific( $signup_id = 0 ) {
+		global $wpdb;
+
+		$signups_table = buddypress()->members->table_name_signups;
+		$signup = $wpdb->get_row( $wpdb->prepare( "SELECT * FROM {$signups_table} WHERE active = 0 AND signup_id = %d", absint( $signup_id ) ) );
+
+		return apply_filters( 'bp_core_signups_get_specific', $signup );
+	}
+
+	/**
+	 * Add a signup
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param array $args
+	 * @return boolean
+	 * @static
+	 */
+	public static function add( $args = array() ) {
+		global $wpdb;
+
+		$r = bp_parse_args( $args, 
+			array(
+				'domain'         => '',
+				'path'           => '',
+				'title'          => '',
+				'user_login'     => '',
+				'user_email'     => '',
+				'registered'     => current_time( 'mysql', true ),
+				'activation_key' => '',
+				'meta'           => ''
+			),
+			'bp_core_signups_add_args'
+		);
+
+		$inserted = $wpdb->insert( 
+			buddypress()->members->table_name_signups, 
+			$r,
+			array( '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s' )
+		);
+
+		return apply_filters( 'bp_core_signups_add', $inserted );
+	}
+
+	/**
+	 * Keep on creating a user on signup
+	 * 
+	 * Plugins might rely on user_status / activation_key
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param string $user_login
+	 * @param string $user_password
+	 * @param string $user_email
+	 * @param array $usermeta
+	 * @return int user id
+	 * @static
+	 */
+	public static function add_backcompat( $user_login = '', $user_password = '', $user_email = '', $usermeta = array() ) {
+		global $wpdb;
+
+		$errors = new WP_Error();
+
+		$user_id = wp_insert_user( array(
+			'user_login' => $user_login,
+			'user_pass' => $user_password,
+			'display_name' => sanitize_title( $user_login ),
+			'user_email' => $user_email
+		) );
+
+		if ( is_wp_error( $user_id ) || empty( $user_id ) ) {
+			$errors->add( 'registerfail', sprintf( __('<strong>ERROR</strong>: Couldn&#8217;t register you... please contact the <a href="mailto:%s">webmaster</a> !', 'buddypress' ), bp_get_option( 'admin_email' ) ) );
+			return $errors;
+		}
+
+		// Update the user status to '2' which we will use as 'not activated' (0 = active, 1 = spam, 2 = not active)
+		$wpdb->query( $wpdb->prepare( "UPDATE {$wpdb->users} SET user_status = 2 WHERE ID = %d", $user_id ) );
+
+		// Deleting these options will remove signups from users count
+		delete_user_option( $user_id, 'capabilities' );
+		delete_user_option( $user_id, 'user_level' );
+
+		// Set any profile data
+		if ( bp_is_active( 'xprofile' ) ) {
+			if ( !empty( $usermeta['profile_field_ids'] ) ) {
+				$profile_field_ids = explode( ',', $usermeta['profile_field_ids'] );
+
+				foreach( (array) $profile_field_ids as $field_id ) {
+					if ( empty( $usermeta["field_{$field_id}"] ) )
+						continue;
+
+					$current_field = $usermeta["field_{$field_id}"];
+					xprofile_set_field_data( $field_id, $user_id, $current_field );
+
+					// Save the visibility level
+					$visibility_level = !empty( $usermeta['field_' . $field_id . '_visibility'] ) ? $usermeta['field_' . $field_id . '_visibility'] : 'public';
+					xprofile_set_field_visibility_level( $field_id, $user_id, $visibility_level );
+				}
+			}
+		}
+
+		return apply_filters( 'bp_core_signups_add_backcompat', $user_id );
+	}
+
+	/**
+	 * Checks a user status for non multisite config
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param int $user_id
+	 * @return int the status
+	 * @static
+	 */
+	public static function check_user_status( $user_id = 0 ) {
+		global $wpdb;
+
+		if ( empty( $user_id ) )
+			return false;
+
+		$user_status = $wpdb->get_var( $wpdb->prepare( "SELECT user_status FROM {$wpdb->users} WHERE ID = %d", $user_id ) );
+
+		return apply_filters( 'bp_core_signups_check_user_status', intval( $user_status ) );
+	}
+
+	/**
+	 * "Activate" a signup
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param string $key
+	 * @return boolean
+	 * @static
+	 */
+	public static function validate( $key = '' ) {
+		global $wpdb;
+
+		if ( empty( $key ) )
+			return;
+
+		$activated = $wpdb->update(
+			// Signups table
+			buddypress()->members->table_name_signups, 
+			array(
+				'active' => 1,
+				'activated' => current_time( 'mysql', true )
+			),
+			array(
+				'activation_key' => $key
+			),
+			// Data sanitization format
+			array(
+				'%d',
+				'%s'
+			),
+			// WHERE sanitization format
+			array(
+				'%s'
+			)
+		);
+
+		return apply_filters( 'bp_core_signups_validate', $activated );
+	}
+
+	/**
+	 * How many signups ?
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @return int the number of signups
+	 * @static
+	 */
+	public static function count_signups() {
+		global $wpdb;
+
+		$signups_table = buddypress()->members->table_name_signups;
+		$count_signups = $wpdb->get_var( $wpdb->prepare( "SELECT COUNT(*) AS total FROM {$signups_table} WHERE active = %d", 0 ) );
+
+		return apply_filters( 'bp_core_signups_count', (int) $count_signups );
+	}
+
+	/**
+	 * Update the meta for a signup
+	 * 
+	 * This is the way we use to "trace" the last date an activation
+	 * email was sent and how many times activation was sent
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $wpdb
+	 * @param  array $args
+	 * @return int the signup id
+	 * @static
+	 */
+	public static function update( $args = array() ) {
+		global $wpdb;
+
+		$r = bp_parse_args( $args, 
+			array(
+				'signup_id'  => 0, 
+				'meta'       => array(),
+			),
+			'bp_core_signups_update_args'
+		);
+
+		extract( $r, EXTR_SKIP );
+		
+		if ( empty( $signup_id ) || empty( $meta ) )
+			return false;
+
+		$wpdb->update(
+			// Signups table
+			buddypress()->members->table_name_signups,
+			// Data to update 
+			array(
+				'meta' => serialize( $meta )
+			),
+			// WHERE
+			array(
+				'signup_id' => $signup_id
+			),
+			// Data sanitization format
+			array(
+				'%s'
+			),
+			// WHERE sanitization format
+			array(
+				'%d'
+			) 
+		);
+
+		return apply_filters( 'bp_core_signups_update', $signup_id );
+	}
+
+	/**
+	 * Resend an activation link
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @param array $signup_ids single id or list of ids to resend
+	 * @return array the results
+	 * @static
+	 */
+	public static function resend( $signup_ids = array() ) {
+		if ( empty( $signup_ids ) || ! is_array( $signup_ids ) )
+			return false;
+
+		$to_resend = self::get( array( 'include' => $signup_ids ) );
+
+		if ( ! $signups = $to_resend['signups'] )
+			return false;
+
+		$now = current_time( 'timestamp', true );
+		$result = array();
+
+		do_action( 'bp_core_signup_before_resend', $signup_ids );
+
+		foreach ( $signups as $signup ) {
+			$sent_at =  mysql2date('U', $signup->date_sent );
+			$diff = $now - $sent_at;
+
+			// If a previous resent happened less than a day ago, skip.
+			if ( $diff < 1 * DAY_IN_SECONDS ) {
+				$result['errors'][ $signup->signup_id ] = array( $signup->user_login, esc_html__( 'already received an activation email today', 'buddypress' ) );;
+				continue;
+			}
+
+			$meta = maybe_unserialize( $signup->meta );
+
+			$meta['sent_date'] = current_time( 'mysql', true );
+			$meta['count_sent'] = $signup->count_sent + 1;
+
+			// Send activation email
+			if ( is_multisite() ) {
+				wpmu_signup_user_notification( $signup->user_login, $signup->user_email, $signup->activation_key, serialize( $meta ) );
+			} else {
+
+				// Check user status before sending email
+				$user_id = email_exists( $signup->user_email );
+
+				if ( ! empty( $user_id ) && 2 != self::check_user_status( $user_id ) ) {
+					// Status is not 2, so user's account has been activated
+					$result['errors'][ $signup->signup_id ] = array( $signup->user_login, esc_html__( 'the sign-up has already been activated.', 'buddypress' ) );;
+					// repare signups table
+					self::validate( $signup->activation_key );
+					continue;
+
+				// Send the validation email
+				} else {
+					bp_core_signup_send_validation_email( false, $signup->user_email, $signup->activation_key );
+				}
+			}
+			
+			// Update metas
+			$result['resent'][] = self::update( array( 'signup_id' => $signup->signup_id, 'meta' => $meta ) );
+		}
+
+		do_action( 'bp_core_signup_after_resend', $signup_ids );
+
+		return apply_filters( 'bp_core_signup_resend', $result );
+	}
+
+	/**
+	 * Activate a pending account
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @param array $signup_ids single id or list of ids to resend
+	 * @return array the results
+	 * @static
+	 */
+	public static function activate( $signup_ids = array() ) {
+		if ( empty( $signup_ids ) || ! is_array( $signup_ids ) )
+			return false;
+
+		$to_activate = self::get( array( 'include' => $signup_ids ) );
+
+		if ( ! $signups = $to_activate['signups'] )
+			return false;
+
+		$result = array();
+
+		do_action( 'bp_core_signup_before_activate', $signup_ids );
+
+		foreach ( $signups as $signup ) {
+
+			$user = bp_core_activate_signup( $signup->activation_key );
+
+			if ( ! empty( $user->errors ) ) {
+
+				if ( $user_id = username_exists( $signup->user_login ) && 2 != self::check_user_status( $user_id ) ) {
+					// Status is not 2, so user's account has been activated
+					$result['errors'][ $signup->signup_id ] = array( $signup->user_login, esc_html__( 'the sign-up has already been activated.', 'buddypress' ) );
+					// repare signups table
+					self::validate( $signup->activation_key );
+
+				// we have a user id, account is not active, let's delete it
+				} else {
+					$result['errors'][ $signup->signup_id ] = array( $signup->user_login, $user->get_error_message() );
+				}
+				
+			} else {
+				$result['activated'][] = $user;
+			}
+
+		}
+
+		do_action( 'bp_core_signup_after_activate', $result );
+
+		return apply_filters( 'bp_core_signup_activate', $result );
+	}
+
+	/**
+	 * Delete a pending account
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @param array $signup_ids single id or list of ids to resend
+	 * @return array the results
+	 * @static
+	 */
+	public static function delete( $signup_ids = array() ) {
+		global $wpdb;
+
+		if ( empty( $signup_ids ) || ! is_array( $signup_ids ) )
+			return false;
+
+		$to_delete = self::get( array( 'include' => $signup_ids ) );
+
+		if ( ! $signups = $to_delete['signups'] )
+			return false;
+
+		$result = array();
+
+		do_action( 'bp_core_signup_before_delete', $signup_ids );
+
+		foreach ( $signups as $signup ) {
+
+			$user_id = username_exists( $signup->user_login );
+			
+			if ( ! empty( $user_id ) && $signup->activation_key == wp_hash( $user_id ) ) {
+
+				if ( 2 != self::check_user_status( $user_id ) ) {
+					// Status is not 2, so user's account has been activated
+					$result['errors'][ $signup->signup_id ] = array( $signup->user_login, esc_html__( 'the sign-up has already been activated.', 'buddypress' ) );
+					// repare signups table
+					self::validate( $signup->activation_key );
+
+				// we have a user id, account is not active, let's delete it
+				} else {
+					bp_core_delete_account( $user_id );
+				}
+			}
+				
+			if( empty( $result['errors'][ $signup->signup_id ] ) ) {
+
+				$wpdb->delete(
+						// Signups table
+						buddypress()->members->table_name_signups,
+						// Where 
+						array( 'signup_id' => $signup->signup_id ),
+						// WHERE sanitization format
+						array( '%d' )
+					);
+
+				$result['deleted'][] = $signup->signup_id;
+			}
+
+		}
+
+		do_action( 'bp_core_signup_after_delete', $signup_ids, $result );
+
+		return apply_filters( 'bp_core_signup_delete', $result );
+	}
+
+}
diff --git bp-core/bp-core-update.php bp-core/bp-core-update.php
index 9ca5922..0d9ff1e 100644
--- bp-core/bp-core-update.php
+++ bp-core/bp-core-update.php
@@ -365,6 +365,46 @@ function bp_update_to_2_0() {
 
 	$wpdb->query( $sql );
 
+	/** Migrate 'Sign-ups' data *************************************/
+
+	if ( bp_get_signup_allowed() && ! is_multisite() ) {
+
+		if ( empty( $wpdb->signups ) )
+			bp_core_install_signups();
+
+		$signups = get_users( array( 'fields' => 'all_with_meta', 'meta_key' => 'activation_key', 'meta_compare' => 'EXISTS' ) );
+
+		if ( empty( $signups ) )
+			return;
+
+		foreach ( $signups as $signup ) {
+			$meta = array();
+
+			if ( bp_is_active( 'xprofile' ) )
+				$meta['field_1'] = $signup->display_name;
+
+			$meta['password'] = $signup->user_pass;
+			
+			$user_login = preg_replace( '/\s+/', '', sanitize_user( $signup->user_login, true ) );
+			$user_email = sanitize_email( $signup->user_email );
+			$meta = serialize( $meta );
+
+			$args = array(
+				'user_login'     => $user_login,
+				'user_email'     => $user_email,
+				'registered'     => $signup->user_registered,
+				'activation_key' => $signup->activation_key,
+				'meta'           => $meta
+			);
+
+			BP_Core_SignUp::add( $args );
+
+			// Deleting these options will remove signups from users count
+			delete_user_option( $signup->ID, 'capabilities' );
+			delete_user_option( $signup->ID, 'user_level' );
+		}
+	}
+
 	/** Add BP options to the options table ******************************/
 	bp_add_options();
 }
diff --git bp-members/admin/bp-members-classes.php bp-members/admin/bp-members-classes.php
index e69de29..a2050f1 100644
--- bp-members/admin/bp-members-classes.php
+++ bp-members/admin/bp-members-classes.php
@@ -0,0 +1,617 @@
+<?php
+
+/**
+ * BuddyPress Members List Classes
+ *
+ * @package BuddyPress
+ * @subpackage MembersAdminClasses
+ */
+
+// Exit if accessed directly
+if ( !defined( 'ABSPATH' ) ) exit;
+/**
+ * Using specific List Tables has the benefit to make this inherit
+ * from parent views, so that we do not need to count users, etc..
+ */
+if ( class_exists( 'WP_Users_List_Table') ) :
+/**
+ * List table class for signups admin page.
+ *
+ * @since BuddyPress (2.0.0)
+ */
+class BP_Members_List_Table extends WP_Users_List_Table {
+
+	/**
+	 * Signup counts.
+	 *
+	 * @since BuddyPress (2.0.0)
+	 *
+	 * @access public
+	 * @var int
+	 */
+	public $signup_counts = 0;
+
+	/**
+	 * Constructor
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function __construct() {
+		// Define singular and plural labels, as well as whether we support AJAX.
+		parent::__construct( array(
+			'ajax'     => false,
+			'plural'   => 'signups',
+			'singular' => 'signup',
+		) );
+	}
+
+	/**
+	 * Set up items for display in the list table.
+	 *
+	 * Handles filtering of data, sorting, pagination, and any other data
+	 * manipulation required prior to rendering.
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function prepare_items() {
+		global $usersearch;
+
+		$usersearch = isset( $_REQUEST['s'] ) ? $_REQUEST['s'] : '';
+
+		$signups_per_page = $this->get_items_per_page( str_replace( '-', '_', "{$this->screen->id}_per_page" ) );
+
+		$paged = $this->get_pagenum();
+
+		$args = array(
+			'offset'     => ( $paged - 1 ) * $signups_per_page, 
+			'number'     => $signups_per_page, 
+			'usersearch' => $usersearch, 
+			'orderby'    => 'signup_id', 
+			'order'      => 'DESC'
+		);
+
+		if ( isset( $_REQUEST['orderby'] ) )
+			$args['orderby'] = $_REQUEST['orderby'];
+
+		if ( isset( $_REQUEST['order'] ) )
+			$args['order'] = $_REQUEST['order'];
+
+		$signups = BP_Core_SignUp::get( $args );
+
+		$this->items = $signups['signups'];
+		$this->signup_counts = $signups['total'];
+
+		$this->set_pagination_args( array(
+			'total_items' => $this->signup_counts,
+			'per_page'    => $signups_per_page,
+		) );
+	}
+
+	/**
+	 * Get the views : the links above the WP List Table.
+	 *
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @uses WP_Users_List_Table::get_views() to get the users views
+	 */
+	public function get_views() {
+		$views = parent::get_views();
+
+		$views['all'] = str_replace( 'class="current"', '', $views['all'] );
+			$class = ' class="current"';
+
+		$views['registered'] = '<a href="' . add_query_arg( 'page', 'bp-signups', bp_get_admin_url( 'users.php' ) ) . '"  class="current">' . sprintf( _nx( 'Pending account <span class="count">(%s)</span>', 'Pending accounts <span class="count">(%s)</span>', $this->signup_counts, 'signup users', 'buddypress' ), number_format_i18n( $this->signup_counts ) ) . '</a>';
+
+		return $views;
+	}
+
+	/**
+	 * Get rid of the extra nav.
+	 * 
+	 * WP_Users_List_Table will add an extra nav to change user's role
+	 * as we're dealing with signups, we don't need this
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function extra_tablenav( $which ) {
+		return;
+	}
+
+	/**
+	 * Specific signups columns
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function get_columns() {
+		return apply_filters( 'bp_members_signup_columns', array(
+			'cb'         => '<input type="checkbox" />',
+			'username'   => __( 'Username', 'buddypress' ),
+			'name'       => __( 'Name', 'buddypress' ),
+			'email'      => __( 'E-mail', 'buddypress' ),
+			'registered' => __( 'Registered', 'buddypress' ),
+			'date_sent'  => __( 'Last mail', 'buddypress' ),
+			'count_sent' => __( 'Mail count', 'buddypress' )
+		) );
+	}
+
+	/**
+	 * Specific bulk actions for signups
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function get_bulk_actions() {
+		$actions = array();
+		$actions['resend']     = _x( 'Email', 'user', 'buddypress' );
+		$actions['activate']   = _x( 'Activate', 'user', 'buddypress' );
+		if ( current_user_can( 'delete_users' ) )
+			$actions['delete'] = __( 'Delete' );
+
+		return $actions;
+	}
+
+	/**
+	 * Nice job, clean sheet!
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function no_items() {
+		_e( 'No pending accounts found.', 'buddypress' );
+	}
+
+	/**
+	 * The columns signups can be reordered with
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function get_sortable_columns() {
+		return array(
+			'username'   => 'login',
+			'email'      => 'email',
+			'registered' => 'signup_id',
+		);
+	}
+
+	/**
+	 * Display signups rows
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function display_rows() {
+		$style = '';
+		foreach ( $this->items as $userid => $signup_object ) {
+
+			$style = ( ' class="alternate"' == $style ) ? '' : ' class="alternate"';
+			echo "\n\t" . $this->single_row( $signup_object, $style );
+		}
+	}
+
+	/**
+	 * Display a signup row
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function single_row( $signup_object = null, $style = '', $role = '', $numposts = 0 ) {
+
+		echo '<tr' . $style . ' id="signup-' . esc_attr( $signup_object->id ) . '">';
+		echo $this->single_row_columns( $signup_object );
+		echo '</tr>';
+	}
+
+	/**
+	 * The item to select for the bulk actions
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_cb( $signup_object = null ) {
+		?>
+		<label class="screen-reader-text" for="signup_<?php echo $signup_object->id; ?>"><?php echo sprintf( __( 'Select %s' ), $signup_object->user_login ); ?></label>
+		<input type="checkbox" id="signup_<?php echo $signup_object->id ?>" name="allsignups[]" value="<?php echo esc_attr( $signup_object->id ) ?>" />
+		<?php
+	}
+
+	/**
+	 * The row actions (delete/activate/email)
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_username( $signup_object = null ) {
+		$avatar	= get_avatar( $signup_object->user_email, 32 );
+
+		// Activation email link
+		$email_link = add_query_arg( array(
+				'page' => 'bp-signups',
+				'signup_id' => $signup_object->id,
+				'action' => 'resend'
+			), 
+			bp_get_admin_url( 'users.php' )
+		);
+
+		// Activate link
+		$activate_link = add_query_arg( array(
+				'page' => 'bp-signups',
+				'signup_id' => $signup_object->id,
+				'action' => 'activate'
+			), 
+			bp_get_admin_url( 'users.php' )
+		);
+
+		// Delete link
+		$delete_link = add_query_arg( array(
+				'page' => 'bp-signups',
+				'signup_id' => $signup_object->id,
+				'action' => 'delete'
+			), 
+			bp_get_admin_url( 'users.php' )
+		);
+
+		echo $avatar . '<strong><a href="' . $activate_link .'" class="edit" title="' . esc_attr__( 'Activate', 'buddypress' ) . '">' . $signup_object->user_login .'</a></strong><br/>';
+
+		$actions = array();
+
+		$now = current_time( 'timestamp', true );
+		$sent_at =  mysql2date('U', $signup_object->date_sent );
+		$diff = $now - $sent_at;
+
+		// Only if resent happened more than a day ago.
+		if ( $diff > 1 * DAY_IN_SECONDS )
+			$actions['resend'] = '<a href="' . $email_link . '">' . __( 'Email', 'buddypress' ) . '</a>';
+
+		if ( current_user_can( 'delete_users' ) ) {
+			$actions['delete'] = '<a href="' . $delete_link . '" class="delete">' . __( 'Delete', 'buddypress' ) . '</a>';
+		}
+		
+		$actions = apply_filters( 'bp_members_ms_signup_row_actions', $actions, $signup_object );
+		echo $this->row_actions( $actions );
+	}
+
+	/**
+	 * Display user name if any
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_name( $signup_object = null ) {
+		echo $signup_object->user_name;
+	}
+
+	/**
+	 * Display user email
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_email( $signup_object = null ) {
+		echo '<a href="mailto:' . $signup_object->user_email . '">' . $signup_object->user_email .'</a>';
+	}
+
+	/**
+	 * Display registration date
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_registered( $signup_object = null ) {
+		echo mysql2date( 'Y/m/d', $signup_object->registered );
+	}
+
+	/**
+	 * Display the last time an activation email has been sent
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_date_sent( $signup_object = null ) {
+		echo mysql2date( 'Y/m/d', $signup_object->date_sent );
+	}
+
+	/**
+	 * Display number of time an activation email has been sent
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_count_sent( $signup_object = null ) {
+		echo absint( $signup_object->count_sent );
+	}
+
+}
+
+endif;
+
+
+if ( class_exists( 'WP_MS_Users_List_Table' ) ) :
+/**
+ * List table class for signups network admin page.
+ *
+ * @since BuddyPress (2.0.0)
+ */
+class BP_Members_MS_List_Table extends WP_MS_Users_List_Table {
+
+	/**
+	 * Signup counts.
+	 *
+	 * @since BuddyPress (2.0.0)
+	 *
+	 * @access public
+	 * @var int
+	 */
+	public $signup_counts = 0;
+
+	/**
+	 * Constructor
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function __construct() {
+		// Define singular and plural labels, as well as whether we support AJAX.
+		parent::__construct( array(
+			'ajax'     => false,
+			'plural'   => 'signups',
+			'singular' => 'signup',
+		) );
+	}
+
+	/**
+	 * Set up items for display in the list table.
+	 *
+	 * Handles filtering of data, sorting, pagination, and any other data
+	 * manipulation required prior to rendering.
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function prepare_items() {
+		global $usersearch, $wpdb, $mode;
+		
+		$usersearch = isset( $_REQUEST['s'] ) ? $_REQUEST['s'] : '';
+
+		$signups_per_page = $this->get_items_per_page( str_replace( '-', '_', "{$this->screen->id}_per_page" ) );
+
+		$paged = $this->get_pagenum();
+
+		$args = array(
+			'offset'     => ( $paged - 1 ) * $signups_per_page, 
+			'number'     => $signups_per_page, 
+			'usersearch' => $usersearch, 
+			'orderby'    => 'signup_id', 
+			'order'      => 'DESC'
+		);
+
+		if ( isset( $_REQUEST['orderby'] ) )
+			$args['orderby'] = $_REQUEST['orderby'];
+
+		if ( isset( $_REQUEST['order'] ) )
+			$args['order'] = $_REQUEST['order'];
+
+		$mode = empty( $_REQUEST['mode'] ) ? 'list' : $_REQUEST['mode'];
+
+		$signups = BP_Core_SignUp::get( $args );
+
+		$this->items = $signups['signups'];
+		$this->signup_counts = $signups['total'];
+
+		$this->set_pagination_args( array(
+			'total_items' => $this->signup_counts,
+			'per_page'    => $signups_per_page,
+		) );
+	}
+
+	/**
+	 * Get the views : the links above the WP List Table.
+	 *
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @uses WP_MS_Users_List_Table::get_views() to get the users views
+	 */
+	function get_views() {
+		$views = parent::get_views();
+
+		$views['all'] = str_replace( 'class="current"', '', $views['all'] );
+			$class = ' class="current"';
+
+		$views['registered'] = '<a href="' . add_query_arg( 'page', 'bp-signups', bp_get_admin_url( 'users.php' ) ) . '"  class="current">' . sprintf( _nx( 'Pending account <span class="count">(%s)</span>', 'Pending accounts <span class="count">(%s)</span>', $this->signup_counts, 'signup users', 'buddypress' ), number_format_i18n( $this->signup_counts ) ) . '</a>';
+
+		return $views;
+	}
+
+	/**
+	 * Specific signups columns
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function get_columns() {
+		return apply_filters( 'bp_members_ms_signup_columns', array(
+			'cb'         => '<input type="checkbox" />',
+			'username'   => __( 'Username', 'buddypress' ),
+			'name'       => __( 'Name', 'buddypress' ),
+			'email'      => __( 'E-mail', 'buddypress' ),
+			'registered' => __( 'Registered', 'buddypress' ),
+			'date_sent'  => __( 'Last mail', 'buddypress' ),
+			'count_sent' => __( 'Mail count', 'buddypress' )
+		) );
+	}
+
+	/**
+	 * Specific bulk actions for signups
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function get_bulk_actions() {
+		$actions = array();
+		$actions['resend']     = _x( 'Email', 'user', 'buddypress' );
+		$actions['activate']   = _x( 'Activate', 'user', 'buddypress' );
+		if ( current_user_can( 'delete_users' ) )
+			$actions['delete'] = __( 'Delete' );
+
+		return $actions;
+	}
+
+	/**
+	 * Nice job, clean sheet!
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function no_items() {
+		_e( 'No pending accounts found.', 'buddypress' );
+	}
+
+	/**
+	 * The columns signups can be reordered with
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function get_sortable_columns() {
+		return array(
+			'username'   => 'login',
+			'email'      => 'email',
+			'registered' => 'signup_id',
+		);
+	}
+
+	/**
+	 * Display signups rows
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function display_rows() {
+		$style = '';
+		foreach ( $this->items as $userid => $signup_object ) {
+
+			$style = ( ' class="alternate"' == $style ) ? '' : ' class="alternate"';
+			echo "\n\t" . $this->single_row( $signup_object, $style );
+		}
+	}
+
+	/**
+	 * Display a signup row
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function single_row( $signup_object = null, $style = '' ) {
+
+		echo '<tr' . $style . ' id="signup-' . esc_attr( $signup_object->id ) . '">';
+		echo $this->single_row_columns( $signup_object );
+		echo '</tr>';
+	}
+
+	/**
+	 * The item to select for the bulk actions
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_cb( $signup_object = null ) {
+		?>
+		<label class="screen-reader-text" for="signup_<?php echo $signup_object->id; ?>"><?php echo sprintf( __( 'Select %s' ), $signup_object->user_login ); ?></label>
+		<input type="checkbox" id="signup_<?php echo $signup_object->id ?>" name="allsignups[]" value="<?php echo esc_attr( $signup_object->id ) ?>" />
+		<?php
+	}
+
+	/**
+	 * The row actions (delete/activate/email)
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_username( $signup_object = null ) {
+		$avatar	= get_avatar( $signup_object->user_email, 32 );
+
+		// Activation email link
+		$email_link = add_query_arg( array(
+				'page' => 'bp-signups',
+				'signup_id' => $signup_object->id,
+				'action' => 'resend'
+			), 
+			bp_get_admin_url( 'users.php' )
+		);
+
+		// Activate link
+		$activate_link = add_query_arg( array(
+				'page' => 'bp-signups',
+				'signup_id' => $signup_object->id,
+				'action' => 'activate'
+			), 
+			bp_get_admin_url( 'users.php' )
+		);
+
+		// Delete link
+		$delete_link = add_query_arg( array(
+				'page' => 'bp-signups',
+				'signup_id' => $signup_object->id,
+				'action' => 'delete'
+			), 
+			bp_get_admin_url( 'users.php' )
+		);
+
+		echo $avatar . '<strong><a href="' . $activate_link .'" class="edit" title="' . esc_attr__( 'Activate', 'buddypress' ) . '">' . $signup_object->user_login .'</a></strong><br/>';
+
+		$now = current_time( 'timestamp', true );
+		$sent_at =  mysql2date('U', $signup_object->date_sent );
+		$diff = $now - $sent_at;
+
+		// Only if resent happened more than a day ago.
+		if ( $diff > 1 * DAY_IN_SECONDS )
+			$actions['resend'] = '<a href="' . $email_link . '">' . __( 'Email', 'buddypress' ) . '</a>';
+
+		if ( current_user_can( 'delete_users' ) ) {
+			$actions['delete'] = '<a href="' . $delete_link . '" class="delete">' . __( 'Delete', 'buddypress' ) . '</a>';
+		}
+		
+		$actions = apply_filters( 'bp_members_ms_signup_row_actions', $actions, $signup_object );
+		echo $this->row_actions( $actions );
+	}
+
+	/**
+	 * Display user name if any
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_name( $signup_object = null ) {
+		echo $signup_object->user_name;
+	}
+
+	/**
+	 * Display user email
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_email( $signup_object = null ) {
+		echo '<a href="mailto:' . $signup_object->user_email . '">' . $signup_object->user_email .'</a>';
+	}
+
+	/**
+	 * Display registration date
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_registered( $signup_object = null ) {
+		global $mode;
+
+		if ( 'list' == $mode )
+			$date = 'Y/m/d';
+		else
+			$date = 'Y/m/d \<\b\r \/\> g:i:s a';
+
+		echo mysql2date( $date, $signup_object->registered ) . "</td>";
+	}
+
+	/**
+	 * Display the last time an activation email has been sent
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_date_sent( $signup_object = null ) {
+		global $mode;
+
+		if ( 'list' == $mode )
+			$date = 'Y/m/d';
+		else
+			$date = 'Y/m/d \<\b\r \/\> g:i:s a';
+
+		echo mysql2date( $date, $signup_object->date_sent );
+	}
+
+	/**
+	 * Display number of time an activation email has been sent
+	 *
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function column_count_sent( $signup_object = null ) {
+		echo absint( $signup_object->count_sent );
+	}
+
+}
+
+endif;
diff --git bp-members/bp-members-admin.php bp-members/bp-members-admin.php
index 3652320..c7a37ed 100644
--- bp-members/bp-members-admin.php
+++ bp-members/bp-members-admin.php
@@ -62,6 +62,7 @@ class BP_Members_Admin {
 	 * @since BuddyPress (2.0.0)
 	 *
 	 * @uses buddypress() to get BuddyPress main instance
+	 * @static
 	 */
 	public static function register_members_admin() {
 		if( ! is_admin() )
@@ -116,6 +117,13 @@ class BP_Members_Admin {
 
 		// BuddyPress edit user's profile url
 		$this->edit_profile_url = add_query_arg( 'page', 'bp-profile-edit', bp_get_admin_url( 'users.php' ) );
+
+		/**** Specific to Signups ****/
+		
+		$this->users_page = '';
+		$this->signups_page = '';
+		$this->users_url = bp_get_admin_url( 'users.php' );
+		$this->users_screen = bp_core_do_network_admin() ? 'users-network' : 'users';
 	}
 
 	/**
@@ -126,7 +134,7 @@ class BP_Members_Admin {
 	 */
 	private function setup_actions() {
 
-		/** Actions ***************************************************/
+		/** Community Profile ***************************************************/
 
 		// Add some page specific output to the <head>
 		add_action( 'bp_admin_head',            array( $this, 'admin_head'      ), 999    );
@@ -140,16 +148,26 @@ class BP_Members_Admin {
 		// Create the Profile Navigation (WordPress/Community)
 		add_action( 'edit_user_profile',        array( $this, 'profile_nav'     ),  99, 1 );
 
-
-		/** Filters ***************************************************/
-
 		// Add a row action to users listing
 		add_filter( bp_core_do_network_admin() ? 'ms_user_row_actions' : 'user_row_actions', array( $this, 'row_actions' ), 10, 2 );
 
+
+		/** Signups **************************************************************/
+		
+		if( bp_get_signup_allowed() ) {
+
+			if ( ! is_multisite() )
+				add_action( 'pre_user_query', array( $this, 'remove_signups_from_user_query'),  10, 1 );
+
+			// Reorganise the views navigation in users.php and signups page
+			add_filter( "views_{$this->users_screen}", array( $this, 'signup_filter_view' ),    10, 1 );
+			add_filter( 'set-screen-option',           array( $this, 'signup_screen_options' ), 10, 3 );
+		}
+
 	}
 
 	/**
-	 * Create the All Users > Edit Profile submenu.
+	 * Create the All Users > Edit Profile and Signups submenus.
 	 *
 	 * @access public
 	 * @since BuddyPress (2.0.0)
@@ -159,7 +177,7 @@ class BP_Members_Admin {
 	public function admin_menus() {
 
 		// Manage user's profile
-		$hook = $this->user_page = add_users_page(
+		$hooks['user'] = $this->user_page = add_users_page(
 			__( 'Edit Profile',  'buddypress' ),
 			__( 'Edit Profile',  'buddypress' ),
 			'bp_moderate',
@@ -167,21 +185,65 @@ class BP_Members_Admin {
 			array( &$this, 'user_admin' )
 		);
 
+		$hooks['signups'] = $this->users_page = add_users_page(
+			__( 'Manage Signups',  'buddypress' ),
+			__( 'Manage Signups',  'buddypress' ),
+			'bp_moderate',
+			'bp-signups',
+			array( &$this, 'signups_admin' )
+		);
+
 		$edit_page = 'user-edit';
+		$this->users_page = 'users';
 
 		if ( bp_core_do_network_admin() ) {
-			$edit_page       .= '-network';
-			$this->user_page .= '-network';
+			$edit_page          .= '-network';
+			$this->users_page   .= '-network';
+			$this->user_page    .= '-network';
+			$this->signups_page .= '-network';
 		}
 
 		$this->screen_id = array( $edit_page, $this->user_page );
 
-		add_action( "admin_head-$hook", array( $this, 'modify_admin_menu_highlight' ) );
-		add_action( "load-$hook",       array( $this, 'user_admin_load' ) );
+		foreach ( $hooks as $key => $hook ) {
+			add_action( "admin_head-$hook", array( $this, 'modify_admin_menu_highlight' ) );
+			add_action( "load-$hook",       array( $this, $key .'_admin_load' ) );
+		}
+
+	}
+
+	/**
+	 * Highlight the Users menu if on Edit Profile or Signups pages.
+	 *
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function modify_admin_menu_highlight() {
+		global $plugin_page, $submenu_file;
 
+		// Only Show the All users menu
+		if ( in_array( $plugin_page, array( 'bp-profile-edit', 'bp-signups' ) ) ) {
+			$submenu_file = 'users.php';
+		}
 	}
 
 	/**
+	 * Remove the Edit Profile & Signups submenu page.
+	 *
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function admin_head() {
+		// Remove submenu to force using Profile Navigation
+		remove_submenu_page( 'users.php', 'bp-profile-edit' );
+
+		// Remove submenu to force using users views
+		remove_submenu_page( 'users.php', 'bp-signups' );
+	}
+
+	/******* Community Profile ******************************************************************************************/
+
+	/**
 	 * Add some specific styling to the Edit User and Edit User's Profile page.
 	 *
 	 * @access public
@@ -248,32 +310,6 @@ class BP_Members_Admin {
 	}
 
 	/**
-	 * Highlight the Users menu if on Edit Profile pages.
-	 *
-	 * @access public
-	 * @since BuddyPress (2.0.0)
-	 */
-	public function modify_admin_menu_highlight() {
-		global $plugin_page, $submenu_file;
-
-		// Only Show the All users menu
-		if ( 'bp-profile-edit' ==  $plugin_page ) {
-			$submenu_file = 'users.php';
-		}
-	}
-
-	/**
-	 * Remove the Edit Profile submenu page.
-	 *
-	 * @access public
-	 * @since BuddyPress (2.0.0)
-	 */
-	public function admin_head() {
-		// Remove submenu to force using Profile Navigation
-		remove_submenu_page( 'users.php', 'bp-profile-edit' );
-	}
-
-	/**
 	 * Set up the user's profile admin page.
 	 *
 	 * Loaded before the page is rendered, this function does all initial
@@ -691,6 +727,615 @@ class BP_Members_Admin {
 
 		return array_merge( $new_edit_actions, $actions );
 	}
+
+	/******* Signups Management ******************************************************************************************/
+
+	/**
+	 * Display the admin preferences about signups pagination
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @param  int $value
+	 * @param  string $option
+	 * @param  int $new_value
+	 * @return int the pagination preferences
+	 */
+	public function signup_screen_options( $value = 0, $option = '', $new_value = 0 ) {
+		if ( 'users_page_bp_signups_network_per_page' != $option && 'users_page_bp_signups_per_page' != $option )
+			return $value;
+
+		// Per page
+		$new_value = (int) $new_value;
+		if ( $new_value < 1 || $new_value > 999 )
+			return $value;
+
+		return $new_value;
+	}
+
+	/**
+	 * Make sure no signups will show in users list
+	 * 
+	 * This is needed to eventually handle signups that
+	 * may have not been activated before the 2.0.0 upgrade
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @param  WP_User_Query $query the users query
+	 * @return WP_User_Query the users query without the signups
+	 */
+	public function remove_signups_from_user_query( $query = null ) {
+		global $wpdb;
+
+		if ( bp_is_update() )
+			return;
+
+		if ( $this->users_page != get_current_screen()->id )
+			return;
+
+		if ( ! empty( $query->query_vars['role'] ) )
+			return;
+
+		$query->query_where .= " AND {$wpdb->users}.user_status != 2";
+	}
+
+	/**
+	 * Filter the WP Users List Table views to include the signup one
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @param  array  $views the WP List Table views
+	 * @return array  the views with the signup one
+	 */
+	public function signup_filter_view( $views = array() ) {
+		$class = '';
+
+		$signups = BP_Core_Signup::count_signups();
+
+		if ( $this->signups_page == get_current_screen()->id ) {
+			$views['all'] = str_replace( 'class="current"', '', $views['all'] );
+			$class = ' class="current"';
+		}
+
+		$views['registered'] = '<a href="' . add_query_arg( 'page', 'bp-signups', bp_get_admin_url( 'users.php' ) ) . '"' . $class . '>' . sprintf( _nx( 'Pending account <span class="count">(%s)</span>', 'Pending accounts <span class="count">(%s)</span>', $signups, 'signup users', 'buddypress' ), number_format_i18n( $signups ) ) . '</a>';
+
+		return $views;
+	}
+
+	/**
+	 * Load the Signup WP Users List table
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @param  string $class    the name of the class to use
+	 * @param  string $required the parent class
+	 * @return WP_List_Table    the List table
+	 * @static
+	 */
+	public static function get_list_table_class( $class = '', $required = '' ) {
+		if ( empty( $class ) )
+			return;
+
+		if ( ! empty( $required ) ) {
+			require_once( ABSPATH . 'wp-admin/includes/class-wp-' . $required . '-list-table.php' );
+			require_once( buddypress()->members->admin->admin_dir . 'bp-members-classes.php'    );
+		}
+
+		return new $class();
+	}
+
+	/**
+	 * Set up the signups admin page.
+	 *
+	 * Loaded before the page is rendered, this function does all initial
+	 * setup, including: processing form requests, registering contextual
+	 * help, and setting up screen options.
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $bp_members_signup_list_table
+	 */
+	public function signups_admin_load() {
+		global $bp_members_signup_list_table;
+
+		// Build redirection URL
+		$redirect_to = remove_query_arg( array( 'action', 'error', 'updated', 'activated', 'notactivated', 'deleted', 'notdeleted', 'resent', 'notresent', 'do_delete', 'do_resend', 'do_activate', '_wpnonce', 'signup_ids' ), $_SERVER['REQUEST_URI'] );
+		$doaction = bp_admin_list_table_current_bulk_action();
+
+		// Call an action for plugins to hook in early
+		do_action_ref_array( 'bp_signups_admin_load', array( $doaction, $_REQUEST ) );
+
+		// Allowed actions
+		$allowed_actions = apply_filters( 'bp_signups_admin_allowed_actions', array( 'do_delete', 'do_activate', 'do_resend' ) );
+
+		// Prepare the display of the Community Profile screen
+		if ( ! in_array( $doaction, $allowed_actions ) || -1 == $doaction ) {
+			
+			if ( bp_core_do_network_admin() ) {
+				$bp_members_signup_list_table = self::get_list_table_class( 'BP_Members_MS_List_Table', 'ms-users' );
+			} else {
+				$bp_members_signup_list_table = self::get_list_table_class( 'BP_Members_List_Table', 'users' );
+			}
+
+			// per_page screen option
+			add_screen_option( 'per_page', array( 'label' => _x( 'Pending Accounts', 'Pending Accounts per page (screen options)', 'buddypress' ) ) );
+
+			get_current_screen()->add_help_tab( array(
+				'id'      => 'bp-signups-overview',
+				'title'   => __( 'Overview', 'buddypress' ),
+				'content' =>
+				'<p>' . __( 'This is the admininistration screen of the pending accounts of your site.', 'buddypress' ) . '</p>' .
+				'<p>' . __( 'From the screen options, you can customize the displayed columns and the pagination of this screen.', 'buddypress' ) . '</p>' .
+				'<p>' . __( 'You can reorder the list of your pending accounts by clicking on the Username, E-mail or Registered column headers.', 'buddypress' ) . '</p>' .
+				'<p>' . __( 'Using the search form, you can find pending accounts more easily: Username and E-mail fields will be looked at.', 'buddypress' ) . '</p>'
+			) );
+
+			get_current_screen()->add_help_tab( array(
+				'id'      => 'bp-signups-actions',
+				'title'   => __( 'Actions', 'buddypress' ),
+				'content' =>
+				'<p>' . __( 'Hovering over a row in the pending accounts list will display action links that allow you to manage pending accounts. You can perform the following actions:', 'buddypress' ) . '</p>' .
+				'<ul><li>' . __( 'Email takes you to the confirmation screen before being able to send the activation link to the desired pending account. You can only send the activation link once per day.', 'buddypress' ) . '</li>' .
+				'<li>' . __( 'Delete allows you to delete a pending account from your site, once you confirmed your choice from the confirmation screen.', 'buddypress' ) . '</li></ul>' .
+				'<p>' . __( 'By clicking on a Username you will be able to activate a pending account from the confirmation screen.', 'buddypress' ) . '</p>' .
+				'<p>' . __( 'Bulk actions allow you to perform these 3 actions for the selected rows.', 'buddypress' ) . '</p>'
+			) );
+
+			// Help panel - sidebar links
+			get_current_screen()->set_help_sidebar(
+				'<p><strong>' . __( 'For more information:', 'buddypress' ) . '</strong></p>' .
+				'<p>' . __( '<a href="http://codex.buddypress.org/buddypress-site-administration/managing-signups/">Managing Sign-ups</a>', 'buddypress' ) . '</p>' .
+				'<p>' . __( '<a href="http://buddypress.org/support/">Support Forums</a>', 'buddypress' ) . '</p>'
+			);
+		} else {
+			if ( ! empty( $_REQUEST['signup_ids' ] ) )
+				$signups = wp_parse_id_list( $_REQUEST['signup_ids' ] );
+
+			// Handle resent activation links
+			if ( 'do_resend' == $doaction ) {
+				// nonce check
+				check_admin_referer( 'signups_resend' );
+
+				$resent = BP_Core_SignUp::resend( $signups );
+
+				if ( empty( $resent ) ) {
+					$redirect_to = add_query_arg( 'error', $doaction, $redirect_to );
+				// resent activation emails
+				} else {
+					$query_arg = array( 'updated' => 'resent' );
+
+					if ( ! empty( $resent['resent'] ) )
+						$query_arg['resent'] = count( $resent['resent'] );
+
+					if ( ! empty( $resent['errors'] ) ) {
+						$query_arg['notsent'] = count( $resent['errors'] );
+						set_transient( '_bp_admin_signups_errors', $resent['errors'], 30 );
+					}						
+
+					$redirect_to = add_query_arg( $query_arg, $redirect_to );
+				}
+
+				bp_core_redirect( $redirect_to );
+
+			// Handle activated accounts
+			} else if ( 'do_activate' == $doaction ) {
+				// nonce check
+				check_admin_referer( 'signups_activate' );
+
+				$activated = BP_Core_SignUp::activate( $signups );
+
+				if ( empty( $activated ) ) {
+					$redirect_to = add_query_arg( 'error', $doaction, $redirect_to );
+				// activate signups
+				} else {
+					$query_arg = array( 'updated' => 'activated' );
+
+					if ( ! empty( $activated['activated'] ) )
+						$query_arg['activated'] = count( $activated['activated'] );
+
+					if ( ! empty( $activated['errors'] ) ) {
+						$query_arg['notactivated'] = count( $activated['errors'] );
+						set_transient( '_bp_admin_signups_errors', $activated['errors'], 30 );
+					}
+
+					$redirect_to = add_query_arg( $query_arg, $redirect_to );
+				}
+
+				bp_core_redirect( $redirect_to );
+
+			// Handle sign-ups delete
+			} else if ( 'do_delete' == $doaction ) {
+				// nonce check
+				check_admin_referer( 'signups_delete' );
+
+				$deleted = BP_Core_SignUp::delete( $signups );
+
+				if ( empty( $deleted ) ) {
+					$redirect_to = add_query_arg( 'error', $doaction, $redirect_to );
+				// delete signups
+				} else {
+					$query_arg = array( 'updated' => 'deleted' );
+
+					if ( ! empty( $deleted['deleted'] ) )
+						$query_arg['deleted'] = count( $deleted['deleted'] );
+
+					if ( ! empty( $deleted['errors'] ) ) {
+						$query_arg['notdeleted'] = count( $deleted['errors'] );
+						set_transient( '_bp_admin_signups_errors', $deleted['errors'], 30 );
+					}
+
+					$redirect_to = add_query_arg( $query_arg, $redirect_to );
+				}
+
+				bp_core_redirect( $redirect_to );
+
+			// Plugins can update other stuff from here
+			} else {
+				$this->redirect = $redirect_to;
+
+				do_action_ref_array( 'bp_members_admin_update_signups', array( $doaction, $_REQUEST, $this->redirect ) );
+
+				bp_core_redirect( $this->redirect );
+			}
+		}
+	}
+
+	/**
+	 * Display the activation errors
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function signups_display_errors() {
+		// Bail if no activation errors
+		if ( ! $errors = get_transient( '_bp_admin_signups_errors' ) )
+			return;
+
+		foreach ( $errors as $error ) {
+			?>
+			<li><?php echo esc_html( $error[0] );?>: <?php echo esc_html( $error[1] );?></li>
+			<?php
+		}
+
+		// Delete the redirect transient
+		delete_transient( '_bp_admin_signups_errors' );
+	}
+
+	/**
+	 * Choose the best signups admin page
+	 * 
+	 * Depending on the context, display 
+	 * - the list of signups
+	 * - or the delete confirmation screen
+	 * - or the activate confirmation screen
+	 * - or the "resend" email confirmation screen
+	 * 
+	 * Also prepare the admin notices
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 */
+	public function signups_admin() {
+		$doaction = bp_admin_list_table_current_bulk_action();
+
+		// Prepare notices for admin
+		$notice = array();
+
+		if ( ! empty( $_REQUEST['updated'] ) ) {
+			switch ( $_REQUEST['updated'] ) {
+				case 'resent':
+					$notice = array(
+						'class'   => 'updated',
+						'message' => ''
+					);
+
+					if ( ! empty( $_REQUEST['resent'] ) ) {
+						$notice['message'] .= sprintf( 
+							_nx( '%s activation email successfully sent! ', '%s activation emails successfully sent! ',
+							 absint( $_REQUEST['resent'] ), 
+							 'signup resent', 
+							 'buddypress' 
+							), 
+							number_format_i18n( absint( $_REQUEST['resent'] ) ) 
+						);
+					}
+
+					if ( ! empty( $_REQUEST['notsent'] ) ) {
+						$notice['message'] .= sprintf( 
+							_nx( '%s activation email was not sent.', '%s activation emails were not sent.',
+							 absint( $_REQUEST['notsent'] ), 
+							 'signup notsent', 
+							 'buddypress' 
+							), 
+							number_format_i18n( absint( $_REQUEST['notsent'] ) ) 
+						);
+
+						if ( empty( $_REQUEST['resent'] ) )
+							$notice['class'] = 'error';
+					}
+						
+					break;
+
+				case 'activated':
+					$notice = array(
+						'class'   => 'updated',
+						'message' => ''
+					);
+
+					if ( ! empty( $_REQUEST['activated'] ) ) {
+						$notice['message'] .= sprintf( 
+							_nx( '%s account successfully activated! ', '%s accounts successfully activated! ',
+							 absint( $_REQUEST['activated'] ), 
+							 'signup resent', 
+							 'buddypress' 
+							), 
+							number_format_i18n( absint( $_REQUEST['activated'] ) ) 
+						);
+					}
+
+					if ( ! empty( $_REQUEST['notactivated'] ) ) {
+						$notice['message'] .= sprintf( 
+							_nx( '%s account was not activated.', '%s accounts were not activated.',
+							 absint( $_REQUEST['notactivated'] ), 
+							 'signup notsent', 
+							 'buddypress' 
+							), 
+							number_format_i18n( absint( $_REQUEST['notactivated'] ) ) 
+						);
+
+						if ( empty( $_REQUEST['activated'] ) )
+							$notice['class'] = 'error';
+					}
+						
+					break;
+
+				case 'deleted':
+					$notice = array(
+						'class'   => 'updated',
+						'message' => ''
+					);
+
+					if ( ! empty( $_REQUEST['deleted'] ) ) {
+						$notice['message'] .= sprintf( 
+							_nx( '%s sign-up successfully deleted!', '%s sign-ups successfully deleted!',
+							 absint( $_REQUEST['deleted'] ), 
+							 'signup deleted', 
+							 'buddypress' 
+							), 
+							number_format_i18n( absint( $_REQUEST['deleted'] ) )
+						);
+					}
+
+					if ( ! empty( $_REQUEST['notdeleted'] ) ) {
+						$notice['message'] .= sprintf( 
+							_nx( '%s sign-up was not deleted.', '%s sign-ups were not deleted.',
+							 absint( $_REQUEST['notdeleted'] ), 
+							 'signup notdeleted', 
+							 'buddypress' 
+							), 
+							number_format_i18n( absint( $_REQUEST['notdeleted'] ) ) 
+						);
+
+						if ( empty( $_REQUEST['deleted'] ) )
+							$notice['class'] = 'error';
+					}
+						
+					break;
+			}
+		}
+
+		if ( ! empty( $_REQUEST['error'] ) ) {
+			switch ( $_REQUEST['error'] ) {
+				case 'do_resend':
+					$notice = array(
+						'class'   => 'error',
+						'message' => esc_html__( 'There was a problem sending the activation emails, please try again.', 'buddypress' )
+					);
+					break;
+				case 'do_activate':
+					$notice = array(
+						'class'   => 'error',
+						'message' => esc_html__( 'There was a problem activating accounts, please try again.', 'buddypress' )
+					);
+					break;
+				case 'do_delete':
+					$notice = array(
+						'class'   => 'error',
+						'message' => esc_html__( 'There was a problem deleting sign-ups, please try again.', 'buddypress' )
+					);
+					break;
+			}
+		}
+
+		if ( ! empty( $notice ) ) :
+			if ( 'updated' === $notice['class'] ) : ?>
+				<div id="message" class="<?php echo esc_attr( $notice['class'] ); ?>">
+			<?php else: ?>
+				<div class="<?php echo esc_attr( $notice['class'] ); ?>">
+			<?php endif; ?>
+				<p><?php echo $notice['message']; ?></p>
+				<?php if ( ! empty( $_REQUEST['notactivated'] ) || ! empty( $_REQUEST['notdeleted'] ) || ! empty( $_REQUEST['notsent'] ) ) :?>
+					<ul><?php $this->signups_display_errors();?></ul>
+				<?php endif ;?>
+			</div>
+		<?php endif;
+
+		switch( $doaction ) {
+			case 'activate' :
+			case 'delete' :
+			case 'resend' :
+				$this->signups_admin_manage( $doaction );
+				break;
+
+			default:
+				$this->signups_admin_index();
+				break;
+
+		}
+	}
+
+	/**
+	 * This is the list of the Pending accounts (signups)
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @global $plugin_page
+	 * @global $bp_members_signup_list_table
+	 */
+	public function signups_admin_index() {
+		global $plugin_page, $bp_members_signup_list_table;
+
+		$usersearch = ! empty( $_REQUEST['s'] ) ? $_REQUEST['s'] : '';
+		// Prepare the group items for display
+		$bp_members_signup_list_table->prepare_items();
+
+		$form_url = add_query_arg( array(
+			'page' => 'bp-signups'
+			), 
+			bp_get_admin_url( 'users.php' )
+		);
+		$search_form_url = remove_query_arg( 
+			array( 
+				'action',
+				'deleted',
+				'notdeleted',
+				'error',
+				'updated',
+				'delete',
+				'activate',
+				'activated',
+				'notactivated',
+				'resend',
+				'resent',
+				'notresent',
+				'do_delete',
+				'do_activate',
+				'do_resend',
+				'action2',
+				'_wpnonce',
+				'signup_ids'
+			), $_SERVER['REQUEST_URI'] 
+		);
+		?>
+
+		<div class="wrap">
+			<?php screen_icon( 'users' ); ?>
+			<h2>
+				<?php
+				_e( 'Users', 'buddypress' );
+				if ( current_user_can( 'create_users' ) ) { ?>
+					<a href="user-new.php" class="add-new-h2"><?php echo esc_html_x( 'Add New', 'user' ); ?></a>
+				<?php } elseif ( is_multisite() && current_user_can( 'promote_users' ) ) { ?>
+					<a href="user-new.php" class="add-new-h2"><?php echo esc_html_x( 'Add Existing', 'user' ); ?></a>
+				<?php }
+
+				if ( $usersearch )
+					printf( '<span class="subtitle">' . __('Search results for &#8220;%s&#8221;') . '</span>', esc_html( $usersearch ) ); ?>
+			</h2>
+
+			<?php // Display each signups on its own row ?>
+			<?php $bp_members_signup_list_table->views(); ?>
+
+			<form id="bp-signups-search-form" action="<?php echo $search_form_url ;?>">
+				<input type="hidden" name="page" value="<?php echo esc_attr( $plugin_page ); ?>" />
+				<?php $bp_members_signup_list_table->search_box( __( 'Search Pending accounts', 'buddypress' ), 'bp-signups' ); ?>
+			</form>
+
+			<form id="bp-signups-form" action="<?php echo $form_url;?>" method="post">
+				<?php $bp_members_signup_list_table->display(); ?>
+			</form>
+
+		</div>
+	<?php
+	}
+
+	/**
+	 * This is the confirmation screen for actions
+	 * 
+	 * @access public
+	 * @since BuddyPress (2.0.0)
+	 * 
+	 * @param  string $action delete/activate or resend activation link
+	 */
+	public function signups_admin_manage( $action = '' ) {
+		if ( ! is_super_admin() || empty( $action ) )
+			die( '-1' );
+
+		$ids = false;
+
+
+		if ( ! empty( $_REQUEST['allsignups'] ) ) {
+			$ids = wp_parse_id_list( $_REQUEST['allsignups'] );
+		} else if ( ! empty( $_REQUEST['signup_id'] ) ) {
+			$ids = absint( $_REQUEST['signup_id'] );
+		}
+
+		if ( empty( $ids ) )
+			return false;
+
+		$signups_query = BP_Core_SignUp::get( array( 'include' => $ids ) );
+		$signups = $signups_query['signups'];
+
+		// Create a new list of signup ids, based on those that actually exist
+		$signup_ids = array();
+		foreach ( $signups as $signup ) {
+			$signup_ids[] = $signup->signup_id;
+		}
+
+		switch ( $action ) {
+			case 'delete' :
+				$caption = __( 'delete', 'buddypress' );
+				break;
+			case 'activate' :
+				$caption = __( 'activate', 'buddypress' );
+				break;
+			case 'resend' :
+				$caption = __( 'resend activation email to', 'buddypress' ) ;
+		}
+		
+
+		$url_args = array( 'page' => 'bp-signups' );
+		$action_args = array(
+			'action'     => 'do_' . $action,
+			'signup_ids' => implode( ',', $signup_ids )
+		);
+
+		$cancel_url = add_query_arg( $url_args, bp_get_admin_url( 'users.php' ) );
+		$action_url = wp_nonce_url( 
+			add_query_arg( 
+				array_merge( $url_args, $action_args ), 
+				bp_get_admin_url( 'users.php' ) 
+			), 
+			'signups_' . $action ); 
+		?>
+
+		<div class="wrap">
+			<?php screen_icon( 'users' ); ?>
+			<h2><?php printf( __( '%s Pending accounts', 'buddypress' ), ucfirst( $caption ) ); ?></h2>
+			<p><?php printf( _n( 'You are about to %s the following account:', 'You are about to %s the following accounts:', count( $signup_ids ), 'buddypress' ), $caption ); ?></p>
+
+			<ol class="bp-signups-list">
+			<?php foreach ( $signups as $signup ) : ?>
+				<li><?php echo esc_html( $signup->user_name ) ?> - <?php echo sanitize_email( $signup->user_email );?></li>
+			<?php endforeach; ?>
+			</ol>
+
+			<?php if ( 'resend' != $action ) : ?>
+				<p><strong><?php esc_html_e( 'This action cannot be undone.', 'buddypress' ) ?></strong></p>
+			<?php endif ; ?>
+
+			<a class="button-primary" href="<?php echo $action_url; ?>"><?php esc_html_e( 'Confirm', 'buddypress' ); ?></a>
+			<a class="button" href="<?php echo esc_attr( $cancel_url ); ?>"><?php esc_html_e( 'Cancel', 'buddypress' ) ?></a>
+		</div>
+
+		<?php
+	}
+
 }
 endif; // class_exists check
 
diff --git bp-members/bp-members-functions.php bp-members/bp-members-functions.php
index 9212f9b..ec28c93 100644
--- bp-members/bp-members-functions.php
+++ bp-members/bp-members-functions.php
@@ -1300,8 +1300,11 @@ function bp_core_validate_user_signup( $user_name, $user_email ) {
 			$errors->add( 'user_name', __( 'Sorry, usernames must have letters too!', 'buddypress' ) );
 		}
 
+		// Check into signups
+		$signup = BP_Core_SignUp::get_by_userlogin( $user_name );
+
 		// Check if the username has been used already.
-		if ( username_exists( $user_name ) ) {
+		if ( username_exists( $user_name ) || ! empty( $signup ) ) {
 			$errors->add( 'user_name', __( 'Sorry, that username already exists!', 'buddypress' ) );
 		}
 
@@ -1332,74 +1335,55 @@ function bp_core_validate_blog_signup( $blog_url, $blog_title ) {
 }
 
 function bp_core_signup_user( $user_login, $user_password, $user_email, $usermeta ) {
-	global $bp, $wpdb;
+	global $bp;
+
+	// We need to cast $user_id to pass to the filters
+	$user_id = false;
 
 	// Multisite installs have their own install procedure
 	if ( is_multisite() ) {
 		wpmu_signup_user( $user_login, $user_email, $usermeta );
 
-		// On multisite, the user id is not created until the user activates the account
-		// but we need to cast $user_id to pass to the filters
-		$user_id = false;
-
 	} else {
-		$errors = new WP_Error();
-
-		$user_id = wp_insert_user( array(
-			'user_login' => $user_login,
-			'user_pass' => $user_password,
-			'display_name' => sanitize_title( $user_login ),
-			'user_email' => $user_email
-		) );
 
-		if ( is_wp_error( $user_id ) || empty( $user_id ) ) {
-			$errors->add( 'registerfail', sprintf( __('<strong>ERROR</strong>: Couldn&#8217;t register you... please contact the <a href="mailto:%s">webmaster</a> !', 'buddypress' ), bp_get_option( 'admin_email' ) ) );
-			return $errors;
+		// Format data
+		$user_login     = preg_replace( '/\s+/', '', sanitize_user( $user_login, true ) );
+		$user_email     = sanitize_email( $user_email );
+		$activation_key = substr( md5( time() . rand() . $user_email ), 0, 16 );
+		$meta           = serialize( $usermeta );
+
+		/**
+		 * Plugins may use the user_status / activation_key usermeta mechanism
+		 * defining BP_SIGNUP_NOT_USER_YET to true skip this step, in case the
+		 * administrator is sure this kind of plugins is not used on his config
+		 * and don't want to directly create a user on sign-up.
+		 */
+		if ( ! defined( 'BP_SIGNUP_NOT_USER_YET' ) ) {
+			$user_id = BP_Core_SignUp::add_backcompat( $user_login, $user_password, $user_email, $usermeta );
+
+			if ( is_wp_error( $user_id ) )
+				return $user_id;
+
+			$activation_key = wp_hash( $user_id );
+			update_user_meta( $user_id, 'activation_key', $activation_key );
 		}
 
-		// Update the user status to '2' which we will use as 'not activated' (0 = active, 1 = spam, 2 = not active)
-		$wpdb->query( $wpdb->prepare( "UPDATE {$wpdb->users} SET user_status = 2 WHERE ID = %d", $user_id ) );
-
-		// Set any profile data
-		if ( bp_is_active( 'xprofile' ) ) {
-			if ( !empty( $usermeta['profile_field_ids'] ) ) {
-				$profile_field_ids = explode( ',', $usermeta['profile_field_ids'] );
-
-				foreach( (array) $profile_field_ids as $field_id ) {
-					if ( empty( $usermeta["field_{$field_id}"] ) )
-						continue;
-
-					$current_field = $usermeta["field_{$field_id}"];
-					xprofile_set_field_data( $field_id, $user_id, $current_field );
-
-					// Save the visibility level
-					$visibility_level = !empty( $usermeta['field_' . $field_id . '_visibility'] ) ? $usermeta['field_' . $field_id . '_visibility'] : 'public';
-					xprofile_set_field_visibility_level( $field_id, $user_id, $visibility_level );
-				}
-			}
-		}
-	}
-	$bp->signup->username = $user_login;
+		$args = array(
+			'user_login'     => $user_login,
+			'user_email'     => $user_email,
+			'activation_key' => $activation_key,
+			'meta'           => $meta
+		);
 
-	/***
-	 * Now generate an activation key and send an email to the user so they can activate their
-	 * account and validate their email address. Multisite installs send their own email, so
-	 * this is only for single blog installs.
-	 *
-	 * To disable sending activation emails you can user the filter
-	 * 'bp_core_signup_send_activation_key' and return false. Note that this will only disable
-	 * the email - a key will still be generated, and the account must still be activated
-	 * before use.
-	 */
-	if ( !is_multisite() ) {
-		$activation_key = wp_hash( $user_id );
-		update_user_meta( $user_id, 'activation_key', $activation_key );
+		BP_Core_SignUp::add( $args );
 
 		if ( apply_filters( 'bp_core_signup_send_activation_key', true ) ) {
 			bp_core_signup_send_validation_email( $user_id, $user_email, $activation_key );
 		}
 	}
 
+	$bp->signup->username = $user_login;
+
 	do_action( 'bp_core_signup_user', $user_id, $user_login, $user_password, $user_email, $usermeta );
 
 	return $user_id;
@@ -1422,53 +1406,96 @@ function bp_core_activate_signup( $key ) {
 		$user = wpmu_activate_signup( $key );
 
 		// If there were errors, add a message and redirect
-		if ( !empty( $user->errors ) ) {
+		if ( ! empty( $user->errors ) ) {
 			return $user;
 		}
 
 		$user_id = $user['user_id'];
 
-		// Set any profile data
-		if ( bp_is_active( 'xprofile' ) ) {
-			if ( !empty( $user['meta']['profile_field_ids'] ) ) {
-				$profile_field_ids = explode( ',', $user['meta']['profile_field_ids'] );
+	} else {
 
-				foreach( (array) $profile_field_ids as $field_id ) {
-					$current_field = isset( $user['meta']["field_{$field_id}"] ) ? $user['meta']["field_{$field_id}"] : false;
+		$signup = BP_Core_SignUp::get_by_key( $key );
 
-					if ( !empty( $current_field ) )
-						xprofile_set_field_data( $field_id, $user_id, $current_field );
+		if ( empty( $signup ) )
+			return new WP_Error( 'invalid_key', __( 'Invalid activation key.', 'buddypress' ) );
 
-					// Save the visibility level
-					$visibility_level = !empty( $user['meta']['field_' . $field_id . '_visibility'] ) ? $user['meta']['field_' . $field_id . '_visibility'] : 'public';
-					xprofile_set_field_visibility_level( $field_id, $user_id, $visibility_level );
-				}
-			}
+		if ( $signup->active ) {
+			if ( empty( $signup->domain ) )
+				return new WP_Error( 'already_active', __( 'The user is already active.', 'buddypress' ), $signup );
+			else
+				return new WP_Error( 'already_active', __( 'The site is already active.', 'buddypress' ), $signup );
 		}
-	} else {
 
-		// Get the user_id based on the $key
-		$user_id = $wpdb->get_var( $wpdb->prepare( "SELECT user_id FROM {$wpdb->usermeta} WHERE meta_key = 'activation_key' AND meta_value = %s", $key ) );
+		$meta = maybe_unserialize( $signup->meta );
+		// password is hashed again in wp_insert_user
+		$password = wp_generate_password( 12, false );
+
+		$user_id = username_exists( $signup->user_login );
+
+		if ( ! $user_id ) {
+			$user_id = wp_create_user( $signup->user_login, $password, $signup->user_email );
+		// It might be a signup set in previous versions let's check against previous way of setting activation key
+		} else if ( $key == wp_hash( $user_id ) ) {
+			// Change the user's status so they become active
+			if ( ! $wpdb->query( $wpdb->prepare( "UPDATE {$wpdb->users} SET user_status = 0 WHERE ID = %d", $user_id ) ) )
+				return new WP_Error( 'invalid_key', __( 'Invalid activation key', 'buddypress' ) );
+			
+			bp_delete_user_meta( $user_id, 'activation_key' );
+
+			$member = get_userdata( $user_id );
+			$member->set_role( get_option('default_role') );
 
-		if ( empty( $user_id ) )
-			return new WP_Error( 'invalid_key', __( 'Invalid activation key', 'buddypress' ) );
+			$user_already_created = true;
 
-		// Change the user's status so they become active
-		if ( !$wpdb->query( $wpdb->prepare( "UPDATE {$wpdb->users} SET user_status = 0 WHERE ID = %d", $user_id ) ) )
-			return new WP_Error( 'invalid_key', __( 'Invalid activation key', 'buddypress' ) );
+		} else {
+			$user_already_exists = true;
+		}
+			
+		if ( ! $user_id )
+			return new WP_Error( 'create_user', __( 'Could not create user', 'buddypress' ), $signup );
+		
+		BP_Core_SignUp::validate( $key );
+
+		if ( isset( $user_already_exists ) )
+			return new WP_Error( 'user_already_exists', __( 'That username is already activated.' ), $signup );
+
+		$user = array( 'user_id' => $user_id, 'password' => $meta['password'], 'meta' => $meta );
 
 		// Notify the site admin of a new user registration
 		wp_new_user_notification( $user_id );
 
-		// Remove the activation key meta
-		delete_user_meta( $user_id, 'activation_key' );
+		if ( isset( $user_already_created ) ) {
+
+			do_action( 'bp_core_activated_user', $user_id, $key, $user );
+
+			return $user_id;
+		}
+
+	}
+
+	// Set any profile data
+	if ( bp_is_active( 'xprofile' ) ) {
+		if ( ! empty( $user['meta']['profile_field_ids'] ) ) {
+			$profile_field_ids = explode( ',', $user['meta']['profile_field_ids'] );
+
+			foreach( (array) $profile_field_ids as $field_id ) {
+				$current_field = isset( $user['meta']["field_{$field_id}"] ) ? $user['meta']["field_{$field_id}"] : false;
+
+				if ( !empty( $current_field ) )
+					xprofile_set_field_data( $field_id, $user_id, $current_field );
+
+				// Save the visibility level
+				$visibility_level = ! empty( $user['meta']['field_' . $field_id . '_visibility'] ) ? $user['meta']['field_' . $field_id . '_visibility'] : 'public';
+				xprofile_set_field_visibility_level( $field_id, $user_id, $visibility_level );
+			}
+		}
 	}
 
 	// Update the display_name
 	wp_update_user( array( 'ID' => $user_id, 'display_name' => bp_core_get_user_displayname( $user_id ) ) );
 
 	// Set the password on multisite installs
-	if ( is_multisite() && !empty( $user['meta']['password'] ) )
+	if ( ! empty( $user['meta']['password'] ) )
 		$wpdb->query( $wpdb->prepare( "UPDATE {$wpdb->users} SET user_pass = %s WHERE ID = %d", $user['meta']['password'], $user_id ) );
 
 	do_action( 'bp_core_activated_user', $user_id, $key, $user );
diff --git bp-members/bp-members-loader.php bp-members/bp-members-loader.php
index d88380b..e1e4762 100644
--- bp-members/bp-members-loader.php
+++ bp-members/bp-members-loader.php
@@ -68,7 +68,7 @@ class BP_Members_Component extends BP_Component {
 		if ( !defined( 'BP_MEMBERS_SLUG' ) )
 			define( 'BP_MEMBERS_SLUG', $this->id );
 
-		parent::setup_globals( array(
+		$members_globals = array(
 			'slug'          => BP_MEMBERS_SLUG,
 			'root_slug'     => isset( $bp->pages->members->slug ) ? $bp->pages->members->slug : BP_MEMBERS_SLUG,
 			'has_directory' => true,
@@ -76,7 +76,13 @@ class BP_Members_Component extends BP_Component {
 				'table_name_last_activity' => bp_core_get_table_prefix() . 'bp_activity',
 			),
 			'search_string' => __( 'Search Members...', 'buddypress' ),
-		) );
+		);
+
+		if ( bp_get_signup_allowed() ) {
+			$members_globals['global_tables']['table_name_signups'] = bp_core_get_table_prefix() . 'signups';
+ 		}
+
+		parent::setup_globals( $members_globals );
 
 		/** Logged in user ****************************************************/
 
diff --git bp-members/bp-members-screens.php bp-members/bp-members-screens.php
index 4cb9f40..5cf8b8a 100644
--- bp-members/bp-members-screens.php
+++ bp-members/bp-members-screens.php
@@ -251,11 +251,7 @@ function bp_core_screen_activation() {
 			bp_core_redirect( trailingslashit( bp_get_root_domain() . '/' . $bp->pages->activate->slug ) );
 		}
 
-		// Check for an uploaded avatar and move that to the correct user folder
-		if ( is_multisite() )
-			$hashed_key = wp_hash( $_GET['key'] );
-		else
-			$hashed_key = wp_hash( $user );
+		$hashed_key = wp_hash( $_GET['key'] );
 
 		// Check if the avatar folder exists. If it does, move rename it, move
 		// it and delete the signup avatar dir
