/**
  * Show the add/edit group form
  *
  * @param 	string		'add' or 'edit'
  * @return	@e void		[Outputs to screen]
  * @todo	_initTab doesn't seem to work anymore with the new tabs, need to update each app to have a unique name/id
  */
 protected function _groupForm($type = 'edit')
 {
     //-----------------------------------------
     // Grab group data and start us off
     //-----------------------------------------
     if ($type == 'edit') {
         if ($this->request['id'] == "") {
             $this->registry->output->showError($this->lang->words['g_whichgroup'], 11210);
         }
         $group = $this->DB->buildAndFetch(array('select' => '*', 'from' => 'groups', 'where' => "g_id=" . intval($this->request['id'])));
         $group = IPSMember::unpackGroup($group, FALSE, TRUE);
         //-----------------------------------------
         // Check restrictions.
         //-----------------------------------------
         if ($group['g_access_cp']) {
             $this->registry->getClass('class_permissions')->checkPermissionAutoMsg('groups_edit_admin');
         }
     } else {
         $group = array();
         if ($this->request['id']) {
             $group = $this->DB->buildAndFetch(array('select' => '*', 'from' => 'groups', 'where' => "g_id=" . intval($this->request['id'])));
             $group = IPSMember::unpackGroup($group, FALSE, TRUE);
         }
         $group['g_title'] = 'New Group';
     }
     //-----------------------------------------
     // Grab permission masks
     //-----------------------------------------
     $perm_masks = array();
     $this->DB->build(array('select' => '*', 'from' => 'forum_perms', 'order' => 'perm_name ASC'));
     $this->DB->execute();
     while ($r = $this->DB->fetch()) {
         $perm_masks[] = array($r['perm_id'], $r['perm_name']);
     }
     //-----------------------------------------
     // Ok? Load interface and child classes
     //-----------------------------------------
     $blocks = array('tabs' => array(), 'area' => array());
     IPSLib::loadInterface('admin/group_form.php');
     $tabsUsed = 5;
     $firstTab = empty($this->request['_initTab']) ? false : trim($this->request['_initTab']);
     foreach (IPSLib::getEnabledApplications() as $app_dir => $app_data) {
         if (is_file(IPSLib::getAppDir($app_dir) . '/extensions/admin/group_form.php')) {
             $_class = IPSLib::loadLibrary(IPSLib::getAppDir($app_dir) . '/extensions/admin/group_form.php', 'admin_group_form__' . $app_dir, $app_dir);
             if (class_exists($_class)) {
                 $_object = new $_class($this->registry);
                 $data = $_object->getDisplayContent($group, $tabsUsed);
                 $blocks['area'][$app_dir] = $data['content'];
                 $blocks['tabs'][$app_dir] = $data['tabs'];
                 $tabsUsed = $data['tabsUsed'] ? $tabsUsed + $data['tabsUsed'] : $tabsUsed + 1;
                 if (!empty($this->request['_initTab']) && $this->request['_initTab'] == $app_dir) {
                     $firstTab = $tabsUsed;
                 }
             }
         }
     }
     //-----------------------------------------
     // And output to form
     //-----------------------------------------
     $this->registry->output->extra_nav[] = array("{$this->settings['base_url']}&{$this->form_code}", $this->lang->words['menu__manage_groups']);
     $this->registry->output->html .= $this->html->groupsForm($type, $group, $perm_masks, $blocks, $firstTab);
 }
 /**
  * Load member
  *
  * @param 	string	Member key: Either ID or email address OR array of IDs when $key_type is either ID or not set OR a list of $key_type strings (email address, name, etc)
  * @param 	string	Extra tables to load(all, none or comma delisted tables) Tables: members, pfields_content, profile_portal, groups, sessions, core_item_markers_storage, members_partial.
  *					You can also use the aliases: 'extendedProfile', 'customFields' and 'itemMarkingStorage'
  * @param	string  Key type. Leave it blank to auto-detect or specify "id", "email", "username", "displayname".
  * @return	array   Array containing member data
  * <code>
  * # Single member
  * $member = IPSMember::load( 1, 'extendedProfile,groups' );
  * $member = IPSMember::load( '*****@*****.**', 'all' );
  * $member = IPSMember::load( 'MattM', 'all', 'displayname' ); // Can also use 'username', 'email' or 'id'
  * # Multiple members
  * $members = IPSMember::load( array( 1, 2, 10 ), 'all' );
  * $members = IPSMember::load( array( 'MattM, 'JoeD', 'DaveP' ), 'all', 'displayname' );
  * </code>
  */
 public static function load($member_key, $extra_tables = 'all', $key_type = '')
 {
     //-----------------------------------------
     // INIT
     //-----------------------------------------
     $member_value = 0;
     $members = array();
     $multiple_ids = array();
     $member_field = '';
     $joins = array();
     $tables = array('pfields_content' => 0, 'profile_portal' => 0, 'groups' => 0, 'sessions' => 0, 'members_partial' => 0);
     $remap = array('extendedProfile' => 'profile_portal', 'customFields' => 'pfields_content');
     //-----------------------------------------
     // ID or email?
     //-----------------------------------------
     if (!$key_type) {
         if (is_array($member_key)) {
             $multiple_ids = array_map('intval', $member_key);
             // Bug #20908
             $member_field = 'member_id';
         } else {
             if (strstr($member_key, '@')) {
                 if (strstr($member_key, ' ')) {
                     $member_key = '';
                 }
                 $member_key = IPSText::mbsubstr($member_key, 0, 150);
                 $member_value = "'" . ipsRegistry::DB()->addSlashes(strtolower($member_key)) . "'";
                 $member_field = 'email';
             } else {
                 $member_value = intval($member_key);
                 $member_field = 'member_id';
             }
         }
     } else {
         switch ($key_type) {
             default:
             case 'id':
                 if (is_array($member_key)) {
                     $multiple_ids = $member_key;
                 } else {
                     $member_value = intval($member_key);
                 }
                 $member_field = 'member_id';
                 break;
             case 'fb_uid':
                 if (is_array($member_key)) {
                     $multiple_ids = $member_key;
                 } else {
                     $member_value = is_numeric($member_key) ? $member_key : 0;
                 }
                 $member_field = 'fb_uid';
                 if ($member_value == 0) {
                     return array();
                 }
                 break;
             case 'twitter_id':
                 if (is_array($member_key)) {
                     $multiple_ids = $member_key;
                 } else {
                     $member_value = is_numeric($member_key) ? $member_key : 0;
                 }
                 $member_field = 'twitter_id';
                 if ($member_value == 0) {
                     return array();
                 }
                 break;
             case 'email':
                 if (is_array($member_key)) {
                     array_walk($member_key, create_function('&$v,$k', '$v="\'".( ( strstr( $v, \' \' ) ) ? \'\' : ipsRegistry::DB()->addSlashes( IPSText::mbsubstr( strtolower( $v ), 0, 150 ) ) ) . "\'";'));
                     $multiple_ids = $member_key;
                 } else {
                     if (strstr($member_key, ' ')) {
                         $member_key = '';
                     }
                     $member_key = IPSText::mbsubstr($member_key, 0, 150);
                     $member_value = "'" . ipsRegistry::DB()->addSlashes(strtolower($member_key)) . "'";
                 }
                 $member_field = 'email';
                 break;
             case 'username':
                 if (is_array($member_key)) {
                     array_walk($member_key, create_function('&$v,$k', '$v="\'".ipsRegistry::DB()->addSlashes( IPSText::mbsubstr( strtolower( $v ), 0, 255 ) ) . "\'";'));
                     $multiple_ids = $member_key;
                 } else {
                     $member_key = IPSText::mbsubstr($member_key, 0, 255);
                     $member_value = "'" . ipsRegistry::DB()->addSlashes(strtolower($member_key)) . "'";
                 }
                 $member_field = 'members_l_username';
                 break;
             case 'displayname':
                 if (is_array($member_key)) {
                     array_walk($member_key, create_function('&$v,$k', '$v="\'".ipsRegistry::DB()->addSlashes( IPSText::mbsubstr( strtolower( $v ), 0, 255 ) ) . "\'";'));
                     $multiple_ids = $member_key;
                 } else {
                     $member_key = IPSText::mbsubstr($member_key, 0, 255);
                     $member_value = "'" . ipsRegistry::DB()->addSlashes(strtolower($member_key)) . "'";
                 }
                 $member_field = 'members_l_display_name';
                 break;
             case 'ipsconnect':
                 if (is_array($member_key)) {
                     $multiple_ids = $member_key;
                 } else {
                     $member_value = intval($member_key);
                 }
                 $member_field = 'ipsconnect_id';
                 break;
         }
     }
     //-----------------------------------------
     // Protected against member_id=0
     //-----------------------------------------
     if (!count($multiple_ids) or !is_array($multiple_ids)) {
         if ($member_field == 'member_id' and !$member_value) {
             return array();
         }
     }
     //-----------------------------------------
     // Sort out joins...
     //-----------------------------------------
     if ($extra_tables == 'all') {
         foreach ($tables as $_table => $_val) {
             /* Let's not load sessions or members_partial unless specifically requested */
             if ($_table == 'sessions' or $_table == 'members_partial') {
                 continue;
             }
             $tables[$_table] = 1;
         }
     } else {
         if ($extra_tables) {
             $_tables = explode(",", $extra_tables);
             foreach ($_tables as $_t) {
                 $_t = trim($_t);
                 if (isset($tables[$_t])) {
                     $tables[$_t] = 1;
                 } else {
                     if (isset(self::$remap[$_t])) {
                         if (strstr($tables[self::$remap[$_t]], ',')) {
                             $__tables = explode(',', $tables[self::$remap[$_t]]);
                             foreach ($__tables as $__t) {
                                 $tables[$__t] = 1;
                             }
                         } else {
                             $tables[self::$remap[$_t]] = 1;
                         }
                     }
                 }
             }
         }
     }
     //-----------------------------------------
     // Grab used tables
     //-----------------------------------------
     $_usedTables = array();
     foreach ($tables as $_name => $_use) {
         if ($_use) {
             $_usedTables[] = $_name;
         }
     }
     //-----------------------------------------
     // Check the cache first...
     //-----------------------------------------
     if ($member_field == 'member_id' and $member_value) {
         $member = self::_fetchFromCache($member_value, $_usedTables);
         if ($member !== FALSE) {
             return $member;
         }
     } else {
         if (count($multiple_ids) and is_array($multiple_ids)) {
             $_totalUsers = count($multiple_ids);
             $_gotFromCache = 0;
             $_fromCache = array();
             foreach ($multiple_ids as $_memberValue) {
                 $member = self::_fetchFromCache($_memberValue, $_usedTables);
                 if ($member !== FALSE) {
                     $_fromCache[$member['member_id']] = $member;
                     $_gotFromCache++;
                 }
             }
             //-----------------------------------------
             // Did we find all the members in cache?
             //-----------------------------------------
             if ($_gotFromCache == $_totalUsers) {
                 return $_fromCache;
             }
         }
     }
     self::$ignoreCache = FALSE;
     //-----------------------------------------
     // Fix up joins...
     //-----------------------------------------
     if ($tables['pfields_content']) {
         $joins[] = array('select' => 'p.*', 'from' => array('pfields_content' => 'p'), 'where' => 'p.member_id=m.member_id', 'type' => 'left');
     }
     if ($tables['profile_portal']) {
         $joins[] = array('select' => 'pp.*', 'from' => array('profile_portal' => 'pp'), 'where' => 'pp.pp_member_id=m.member_id', 'type' => 'left');
     }
     if ($tables['groups']) {
         $joins[] = array('select' => 'g.*', 'from' => array('groups' => 'g'), 'where' => 'g.g_id=m.member_group_id', 'type' => 'left');
     }
     if ($tables['sessions']) {
         $joins[] = array('select' => 's.*', 'from' => array('sessions' => 's'), 'where' => 's.member_id=m.member_id', 'type' => 'left');
     }
     if ($tables['core_item_markers_storage']) {
         $joins[] = array('select' => 'im.*', 'from' => array('core_item_markers_storage' => 'im'), 'where' => 'im.item_member_id=m.member_id', 'type' => 'left');
     }
     if ($tables['members_partial']) {
         $joins[] = array('select' => 'mp.*', 'from' => array('members_partial' => 'mp'), 'where' => 'mp.partial_member_id=m.member_id', 'type' => 'left');
     }
     if (IPSContentCache::isEnabled()) {
         if (IPSContentCache::fetchSettingValue('sig')) {
             $joins[] = IPSContentCache::join('sig', 'm.member_id', 'ccb', 'left', 'ccb.cache_content');
         }
     }
     //-----------------------------------------
     // Do eeet
     //-----------------------------------------
     if (count($joins)) {
         ipsRegistry::DB()->build(array('select' => 'm.*, m.member_id as my_member_id', 'from' => array('members' => 'm'), 'where' => (is_array($multiple_ids) and count($multiple_ids)) ? 'm.' . $member_field . ' IN (' . implode(',', $multiple_ids) . ')' : 'm.' . $member_field . '=' . $member_value, 'add_join' => $joins));
     } else {
         ipsRegistry::DB()->build(array('select' => '*', 'from' => 'members', 'where' => (is_array($multiple_ids) and count($multiple_ids)) ? $member_field . ' IN (' . implode(',', $multiple_ids) . ')' : $member_field . '=' . $member_value));
     }
     //-----------------------------------------
     // Execute
     //-----------------------------------------
     ipsRegistry::DB()->execute();
     while ($mem = ipsRegistry::DB()->fetch()) {
         if (isset($mem['my_member_id'])) {
             $mem['member_id'] = $mem['my_member_id'];
         }
         $mem['full'] = true;
         if (!$mem['email'] or !$mem['members_display_name'] or $mem['email'] == $mem['name'] . '@' . $mem['joined']) {
             $mem['full'] = false;
             $mem['timenow'] = $mem['joined'];
         }
         /* Clean secondary groups */
         $mem['mgroup_others'] = $mem['mgroup_others'] != '' ? IPSText::cleanPermString($mem['mgroup_others']) : '';
         //-----------------------------------------
         // Be sure we properly apply secondary permissions
         //-----------------------------------------
         if ($tables['groups']) {
             $mem = ips_MemberRegistry::setUpSecondaryGroups($mem);
             /* Unpack groups */
             $mem = IPSMember::unpackGroup($mem, TRUE, TRUE);
         }
         //-----------------------------------------
         // Unblockable
         //-----------------------------------------
         $mem['_canBeIgnored'] = self::isIgnorable($mem['member_group_id'], $mem['mgroup_others']);
         /* Bitwise Options */
         $mem = self::buildBitWiseOptions($mem);
         /* Twitter is disabled them remove twitter tokens and such */
         if ($mem['twitter_id'] && !IPSLib::twitter_enabled()) {
             $mem['twitter_token'] = '';
             $mem['twitter_secret'] = '';
             $mem['twitter_id'] = '';
         }
         /* Add to array */
         $members[$mem['member_id']] = $mem;
         //-----------------------------------------
         // Add to cache
         //-----------------------------------------
         self::_addToCache($mem, $_usedTables);
     }
     //-----------------------------------------
     // Return just a single if we only sent one id
     //-----------------------------------------
     return (is_array($multiple_ids) and count($multiple_ids)) ? $members : array_shift($members);
 }