public static function load_mock_forum_data(array $data) { $cat_name = __('Test category'); $subject = __('Test post'); $message = __('Message'); $forum_name = __('Test forum'); $forum_desc = __('This is just a test forum'); $now = time(); $ip = Utils::getIp(); return $mock_data = array('categories' => array('cat_name' => $cat_name, 'disp_position' => 1), 'forums' => array('forum_name' => $forum_name, 'forum_desc' => $forum_desc, 'num_topics' => 1, 'num_posts' => 1, 'last_post' => $now, 'last_post_id' => 1, 'last_poster' => $data['username'], 'disp_position' => 1, 'cat_id' => 1), 'topics' => array('poster' => $data['username'], 'subject' => $subject, 'posted' => $now, 'first_post_id' => 1, 'last_post' => $now, 'last_post_id' => 1, 'last_poster' => $data['username'], 'forum_id' => 1), 'posts' => array('poster' => $data['username'], 'poster_id' => 2, 'poster_ip' => $ip, 'message' => $message, 'posted' => $now, 'topic_id' => 1)); }
public static function load_user($user_id) { $user_id = (int) $user_id; $result['select'] = array('u.*', 'g.*', 'o.logged', 'o.idle'); $result['where'] = array('u.id' => $user_id); $result['join'] = $user_id == 1 ? Utils::getIp() : 'u.id'; $escape = $user_id == 1 ? true : false; $result = DB::for_table('users')->table_alias('u')->select_many($result['select'])->inner_join('groups', array('u.group_id', '=', 'g.g_id'), 'g')->left_outer_join('online', array('o.user_id', '=', $result['join']), 'o', $escape)->where($result['where']); $result = $result->find_result_set(); foreach ($result as $user) { return $user; } }
public function logout($req, $res, $args) { $token = Container::get('hooks')->fire('controller.logout', $args['token']); if (User::get()->is_guest || !isset($token) || $token != Random::hash(User::get()->id . Random::hash(Utils::getIp()))) { return Router::redirect(Router::pathFor('home'), 'Not logged in'); } ModelAuth::delete_online_by_id(User::get()->id); // Update last_visit (make sure there's something to update it with) if (isset(User::get()->logged)) { ModelAuth::set_last_visit(User::get()->id, User::get()->logged); } ModelAuth::feather_setcookie('Bearer ', 1); Container::get('hooks')->fire('controller.logout_end'); return Router::redirect(Router::pathFor('home'), __('Logout redirect')); }
public function insert_user($user) { $user = Container::get('hooks')->fire('model.register.insert_user_start', $user); // Insert the new user into the database. We do this now to get the last inserted ID for later use $now = time(); $intial_group_id = ForumSettings::get('o_regs_verify') == '0' ? ForumSettings::get('o_default_user_group') : ForumEnv::get('FEATHER_UNVERIFIED'); $password_hash = Random::hash($user['password1']); // Add the user $user['insert'] = array('username' => $user['username'], 'group_id' => $intial_group_id, 'password' => $password_hash, 'email' => $user['email1'], 'email_setting' => ForumSettings::get('o_default_email_setting'), 'timezone' => ForumSettings::get('o_default_timezone'), 'dst' => 0, 'language' => $user['language'], 'style' => ForumSettings::get('o_default_style'), 'registered' => $now, 'registration_ip' => Utils::getIp(), 'last_visit' => $now); $user = DB::for_table('users')->create()->set($user['insert']); $user = Container::get('hooks')->fireDB('model.register.insert_user_query', $user); $user = $user->save(); $new_uid = DB::get_db()->lastInsertId(ForumSettings::get('db_prefix') . 'users'); // If the mailing list isn't empty, we may need to send out some alerts if (ForumSettings::get('o_mailing_list') != '') { // If we previously found out that the email was banned if (isset($user['banned_email'])) { // Load the "banned email register" template $mail_tpl = trim(file_get_contents(ForumEnv::get('FEATHER_ROOT') . 'featherbb/lang/' . User::get()->language . '/mail_templates/banned_email_register.tpl')); $mail_tpl = Container::get('hooks')->fire('model.register.insert_user_banned_mail_tpl', $mail_tpl); // The first row contains the subject $first_crlf = strpos($mail_tpl, "\n"); $mail_subject = trim(substr($mail_tpl, 8, $first_crlf - 8)); $mail_subject = Container::get('hooks')->fire('model.register.insert_user_banned_mail_subject', $mail_subject); $mail_message = trim(substr($mail_tpl, $first_crlf)); $mail_message = str_replace('<username>', $user['username'], $mail_message); $mail_message = str_replace('<email>', $user['email1'], $mail_message); $mail_message = str_replace('<profile_url>', Router::pathFor('userProfile', ['id' => $new_uid]), $mail_message); $mail_message = str_replace('<board_mailer>', ForumSettings::get('o_board_title'), $mail_message); $mail_message = Container::get('hooks')->fire('model.register.insert_user_banned_mail_message', $mail_message); Container::get('email')->feather_mail(ForumSettings::get('o_mailing_list'), $mail_subject, $mail_message); } // If we previously found out that the email was a dupe if (!empty($dupe_list)) { // Load the "dupe email register" template $mail_tpl = trim(file_get_contents(ForumEnv::get('FEATHER_ROOT') . 'featherbb/lang/' . User::get()->language . '/mail_templates/dupe_email_register.tpl')); $mail_tpl = Container::get('hooks')->fire('model.register.insert_user_dupe_mail_tpl', $mail_tpl); // The first row contains the subject $first_crlf = strpos($mail_tpl, "\n"); $mail_subject = trim(substr($mail_tpl, 8, $first_crlf - 8)); $mail_subject = Container::get('hooks')->fire('model.register.insert_user_dupe_mail_subject', $mail_subject); $mail_message = trim(substr($mail_tpl, $first_crlf)); $mail_message = str_replace('<username>', $user['username'], $mail_message); $mail_message = str_replace('<dupe_list>', implode(', ', $dupe_list), $mail_message); $mail_message = str_replace('<profile_url>', Router::pathFor('userProfile', ['id' => $new_uid]), $mail_message); $mail_message = str_replace('<board_mailer>', ForumSettings::get('o_board_title'), $mail_message); $mail_message = Container::get('hooks')->fire('model.register.insert_user_dupe_mail_message', $mail_message); Container::get('email')->feather_mail(ForumSettings::get('o_mailing_list'), $mail_subject, $mail_message); } // Should we alert people on the admin mailing list that a new user has registered? if (ForumSettings::get('o_regs_report') == '1') { // Load the "new user" template $mail_tpl = trim(file_get_contents(ForumEnv::get('FEATHER_ROOT') . 'featherbb/lang/' . User::get()->language . '/mail_templates/new_user.tpl')); $mail_tpl = Container::get('hooks')->fire('model.register.insert_user_new_mail_tpl', $mail_tpl); // The first row contains the subject $first_crlf = strpos($mail_tpl, "\n"); $mail_subject = trim(substr($mail_tpl, 8, $first_crlf - 8)); $mail_subject = Container::get('hooks')->fire('model.register.insert_user_new_mail_subject', $mail_subject); $mail_message = trim(substr($mail_tpl, $first_crlf)); $mail_message = str_replace('<username>', $user['username'], $mail_message); $mail_message = str_replace('<base_url>', Router::pathFor('home'), $mail_message); $mail_message = str_replace('<profile_url>', Router::pathFor('userProfile', ['id' => $new_uid]), $mail_message); $mail_message = str_replace('<admin_url>', Router::pathFor('profileSection', ['id' => $new_uid, 'section' => 'admin']), $mail_message); $mail_message = str_replace('<board_mailer>', ForumSettings::get('o_board_title'), $mail_message); $mail_message = Container::get('hooks')->fire('model.register.insert_user_new_mail_message', $mail_message); Container::get('email')->feather_mail(ForumSettings::get('o_mailing_list'), $mail_subject, $mail_message); } } // Must the user verify the registration or do we log him/her in right now? if (ForumSettings::get('o_regs_verify') == '1') { // Load the "welcome" template $mail_tpl = trim(file_get_contents(ForumEnv::get('FEATHER_ROOT') . 'featherbb/lang/' . User::get()->language . '/mail_templates/welcome.tpl')); $mail_tpl = Container::get('hooks')->fire('model.register.insert_user_welcome_mail_tpl', $mail_tpl); // The first row contains the subject $first_crlf = strpos($mail_tpl, "\n"); $mail_subject = trim(substr($mail_tpl, 8, $first_crlf - 8)); $mail_subject = Container::get('hooks')->fire('model.register.insert_user_welcome_mail_subject', $mail_subject); $mail_message = trim(substr($mail_tpl, $first_crlf)); $mail_subject = str_replace('<board_title>', ForumSettings::get('o_board_title'), $mail_subject); $mail_message = str_replace('<base_url>', Router::pathFor('home'), $mail_message); $mail_message = str_replace('<username>', $user['username'], $mail_message); $mail_message = str_replace('<password>', $user['password1'], $mail_message); $mail_message = str_replace('<login_url>', Router::pathFor('login'), $mail_message); $mail_message = str_replace('<board_mailer>', ForumSettings::get('o_board_title'), $mail_message); $mail_message = Container::get('hooks')->fire('model.register.insert_user_welcome_mail_message', $mail_message); Container::get('email')->feather_mail($user['email1'], $mail_subject, $mail_message); return Router::redirect(Router::pathFor('home'), __('Reg email') . ' <a href="mailto:' . Utils::escape(ForumSettings::get('o_admin_email')) . '">' . Utils::escape(ForumSettings::get('o_admin_email')) . '</a>.'); } $user_object = new \stdClass(); $user_object->id = $new_uid; $user_object->username = $user['username']; $expire = time() + ForumSettings::get('o_timeout_visit'); $jwt = AuthModel::generate_jwt($user_object, $expire); AuthModel::feather_setcookie('Bearer ' . $jwt, $expire); // Refresh cache Container::get('cache')->store('users_info', Cache::get_users_info()); Container::get('hooks')->fire('model.register.insert_user'); return Router::redirect(Router::pathFor('home'), __('Reg complete')); }
} if (ForumSettings::get('o_rules') == '1' && (!User::get()->is_guest || User::get()->g_read_board == '1' || ForumSettings::get('o_regs_allow') == '1')) { $navlinks[] = '<li id="navrules"' . ($active_page == 'rules' ? ' class="isactive"' : '') . '><a href="' . Router::pathFor('rules') . '">' . __('Rules') . '</a></li>'; } if (User::get()->g_read_board == '1' && User::get()->g_search == '1') { $navlinks[] = '<li id="navsearch"' . ($active_page == 'search' ? ' class="isactive"' : '') . '><a href="' . Router::pathFor('search') . '">' . __('Search') . '</a></li>'; } if (User::get()->is_guest) { $navlinks[] = '<li id="navregister"' . ($active_page == 'register' ? ' class="isactive"' : '') . '><a href="' . Router::pathFor('register') . '">' . __('Register') . '</a></li>'; $navlinks[] = '<li id="navlogin"' . ($active_page == 'login' ? ' class="isactive"' : '') . '><a href="' . Router::pathFor('login') . '">' . __('Login') . '</a></li>'; } else { $navlinks[] = '<li id="navprofile"' . ($active_page == 'profile' ? ' class="isactive"' : '') . '><a href="' . Router::pathFor('userProfile', ['id' => User::get()->id]) . '">' . __('Profile') . '</a></li>'; if (User::get()->is_admmod) { $navlinks[] = '<li id="navadmin"' . ($active_page == 'admin' ? ' class="isactive"' : '') . '><a href="' . Router::pathFor('adminIndex') . '">' . __('Admin') . '</a></li>'; } $navlinks[] = '<li id="navlogout"><a href="' . Router::pathFor('logout', ['token' => Random::hash(User::get()->id . Random::hash(Utils::getIp()))]) . '">' . __('Logout') . '</a></li>'; } // Are there any additional navlinks we should insert into the array before imploding it? $hooksLinks = Container::get('hooks')->fire('view.header.navlinks', []); $extraLinks = ForumSettings::get('o_additional_navlinks') . "\n" . implode("\n", $hooksLinks); if (User::get()->g_read_board == '1' && $extraLinks != '') { if (preg_match_all('%([0-9]+)\\s*=\\s*(.*?)\\n%s', $extraLinks . "\n", $results)) { // Insert any additional links into the $links array (at the correct index) $num_links = count($results[1]); for ($i = 0; $i < $num_links; ++$i) { array_splice($navlinks, $results[1][$i], 0, array('<li id="navextra' . ($i + 1) . '"' . ($active_page == 'navextra' . ($i + 1) ? ' class="isactive"' : '') . '>' . $results[2][$i] . '</li>')); } } } echo "\t\t\t" . implode("\n\t\t\t", $navlinks); ?>
function set_default_user() { $remote_addr = Utils::getIp(); // Fetch guest user $select_set_default_user = array('u.*', 'g.*', 'o.logged', 'o.last_post', 'o.last_search'); $where_set_default_user = array('u.id' => '1'); $result = \DB::for_table('users')->table_alias('u')->select_many($select_set_default_user)->inner_join('groups', array('u.group_id', '=', 'g.g_id'), 'g')->left_outer_join('online', array('o.ident', '=', $remote_addr), 'o', true)->where($where_set_default_user)->find_result_set(); if (!$result) { exit('Unable to fetch guest information. Your database must contain both a guest user and a guest user group.'); } foreach ($result as User::get()) { } // Update online list if (!User::get()->logged) { User::get()->logged = time(); // With MySQL/MySQLi/SQLite, REPLACE INTO avoids a user having two rows in the online table switch (ForumSettings::get('db_type')) { case 'mysql': case 'mysqli': case 'mysql_innodb': case 'mysqli_innodb': case 'sqlite': case 'sqlite3': \DB::for_table('online')->raw_execute('REPLACE INTO ' . ForumSettings::get('db_prefix') . 'online (user_id, ident, logged) VALUES(1, :ident, :logged)', array(':ident' => $remote_addr, ':logged' => User::get()->logged)); break; default: \DB::for_table('online')->raw_execute('INSERT INTO ' . ForumSettings::get('db_prefix') . 'online (user_id, ident, logged) SELECT 1, :ident, :logged WHERE NOT EXISTS (SELECT 1 FROM ' . ForumSettings::get('db_prefix') . 'online WHERE ident=:ident)', array(':ident' => $remote_addr, ':logged' => User::get()->logged)); break; } } else { \DB::for_table('online')->where('ident', $remote_addr)->update_many('logged', time()); } User::get()->disp_topics = ForumSettings::get('o_disp_topics_default'); User::get()->disp_posts = ForumSettings::get('o_disp_posts_default'); User::get()->timezone = ForumSettings::get('o_default_timezone'); User::get()->dst = ForumSettings::get('o_default_dst'); User::get()->language = ForumSettings::get('o_default_lang'); User::get()->style = ForumSettings::get('o_default_style'); User::get()->is_guest = true; User::get()->is_admmod = false; }
public function increment_post_count($post, $new_tid) { Container::get('hooks')->fire('model.post.increment_post_count_start', $post, $new_tid); if (!User::get()->is_guest) { $increment = DB::for_table('users')->where('id', User::get()->id)->find_one()->set('last_post', $post['time'])->set_expr('num_posts', 'num_posts+1'); $increment = Container::get('hooks')->fireDB('model.post.increment_post_count_query', $increment); $increment = $increment->save(); // Promote this user to a new group if enabled if (User::get()->g_promote_next_group != 0 && User::get()->num_posts + 1 >= User::get()->g_promote_min_posts) { $new_group_id = User::get()->g_promote_next_group; $promote = DB::for_table('users')->where('id', User::get()->id)->find_one()->set('group_id', $new_group_id); $promote = Container::get('hooks')->fireDB('model.post.increment_post_count_query', $promote); $promote = $promote->save(); } // Topic tracking stuff... $tracked_topics = Track::get_tracked_topics(); $tracked_topics['topics'][$new_tid] = time(); Track::set_tracked_topics($tracked_topics); } else { // Update the last_post field for guests $last_post = DB::for_table('online')->where('ident', Utils::getIp())->find_one()->set('last_post', $post['time']); $last_post = Container::get('hooks')->fireDB('model.post.increment_post_count_last_post', $last_post); $last_post = $last_post->save(); } Container::get('hooks')->fire('model.post.increment_post_count'); }
public function __invoke($req, $res, $next) { $authCookie = Container::get('cookie')->get(ForumSettings::get('cookie_name')); if ($jwt = $this->get_cookie_data($authCookie)) { $user = AuthModel::load_user($jwt->data->userId); $expires = $jwt->exp > Container::get('now') + ForumSettings::get('o_timeout_visit') ? Container::get('now') + 1209600 : Container::get('now') + ForumSettings::get('o_timeout_visit'); $user->is_guest = false; $user->is_admmod = $user->g_id == ForumEnv::get('FEATHER_ADMIN') || $user->g_moderator == '1'; if (!$user->disp_topics) { $user->disp_topics = ForumSettings::get('o_disp_topics_default'); } if (!$user->disp_posts) { $user->disp_posts = ForumSettings::get('o_disp_posts_default'); } if (!file_exists(ForumEnv::get('FEATHER_ROOT') . 'featherbb/lang/' . $user->language)) { $user->language = ForumSettings::get('o_default_lang'); } if (!file_exists(ForumEnv::get('FEATHER_ROOT') . 'style/themes/' . $user->style . '/style.css')) { $user->style = ForumSettings::get('o_default_style'); } // Refresh cookie to avoid re-logging between idle $jwt = AuthModel::generate_jwt($user, $expires); AuthModel::feather_setcookie('Bearer ' . $jwt, $expires); // Add user to DIC Container::set('user', $user); $this->update_online(); } else { $user = AuthModel::load_user(1); $user->disp_topics = ForumSettings::get('o_disp_topics_default'); $user->disp_posts = ForumSettings::get('o_disp_posts_default'); $user->timezone = ForumSettings::get('o_default_timezone'); $user->dst = ForumSettings::get('o_default_dst'); $user->language = ForumSettings::get('o_default_lang'); $user->style = ForumSettings::get('o_default_style'); $user->is_guest = true; $user->is_admmod = false; // Update online list if (!$user->logged) { $user->logged = time(); // With MySQL/MySQLi/SQLite, REPLACE INTO avoids a user having two rows in the online table switch (ForumSettings::get('db_type')) { case 'mysql': case 'mysqli': case 'mysql_innodb': case 'mysqli_innodb': case 'sqlite': case 'sqlite3': DB::for_table('online')->raw_execute('REPLACE INTO ' . ForumSettings::get('db_prefix') . 'online (user_id, ident, logged) VALUES(1, :ident, :logged)', array(':ident' => Utils::getIp(), ':logged' => $user->logged)); break; default: DB::for_table('online')->raw_execute('INSERT INTO ' . ForumSettings::get('db_prefix') . 'online (user_id, ident, logged) SELECT 1, :ident, :logged WHERE NOT EXISTS (SELECT 1 FROM ' . ForumSettings::get('db_prefix') . 'online WHERE ident=:ident)', array(':ident' => Utils::getIp(), ':logged' => $user->logged)); break; } } else { DB::for_table('online')->where('ident', Utils::getIp())->update_many('logged', time()); } // $jwt = AuthModel::generate_jwt($user, Container::get('now') + 31536000); // AuthModel::feather_setcookie('Bearer '.$jwt, Container::get('now') + 31536000); // Add $user as guest to DIC Container::set('user', $user); } translate('common'); // Load bans from cache if (!Container::get('cache')->isCached('bans')) { Container::get('cache')->store('bans', Cache::get_bans()); } // Add bans to the container Container::set('bans', Container::get('cache')->retrieve('bans')); // Check if current user is banned $this->check_bans(); // Update online list $this->update_users_online(); return $next($req, $res); }
public function send($req, $res, $args) { if (!isset($args['uid'])) { $args['uid'] = null; } if (!isset($args['tid'])) { $args['tid'] = null; } if (Request::isPost()) { // First raw validation $data = array_merge(array('username' => null, 'subject' => null, 'message' => null, 'smilies' => 0, 'preview' => null), Request::getParsedBody()); $data = array_map(array('FeatherBB\\Core\\Utils', 'trim'), $data); $conv = false; if (!is_null($args['tid'])) { if ($args['tid'] < 1) { throw new Error('Wrong conversation ID', 400); } if (!($conv = $this->model->getConversation($args['tid'], User::get()->id))) { throw new Error('Unknown conversation ID', 400); } } // Preview message if (Input::post('preview')) { // Make breadcrumbs $this->crumbs[] = __('Reply', 'private_messages'); $this->crumbs[] = __('Preview'); Utils::generateBreadcrumbs($this->crumbs); Container::get('hooks')->fire('conversationsPlugin.send.preview'); $msg = Container::get('parser')->parse_message($data['req_message'], $data['smilies']); View::setPageInfo(array('parsed_message' => $msg, 'username' => Utils::escape($data['username']), 'subject' => Utils::escape($data['subject']), 'message' => Utils::escape($data['req_message'])))->addTemplate('send.php')->display(); } else { // Prevent flood if (!is_null($data['preview']) && User::get()['last_post'] != '' && Container::get('now') - User::get()['last_post'] < Container::get('prefs')->get(User::get(), 'post.min_interval')) { throw new Error(sprintf(__('Flood start'), Container::get('prefs')->get(User::get(), 'post.min_interval'), Container::get('prefs')->get(User::get(), 'post.min_interval') - (Container::get('now') - User::get()['last_post'])), 429); } if (!$conv) { // Validate username / TODO : allow multiple usernames if (!($user = $this->model->isAllowed($data['username']))) { throw new Error('You can\'t send an PM to ' . ($data['username'] ? $data['username'] : '******'), 400); } // Avoid self messages if ($user->id == User::get()->id) { throw new Error('No self message', 403); } // Validate subject if (ForumSettings::get('o_censoring') == '1') { $data['subject'] = Utils::trim(Utils::censor($data['subject'])); } if (empty($data['subject'])) { throw new Error('No subject or censored subject', 400); } else { if (Utils::strlen($data['subject']) > 70) { throw new Error('Too long subject', 400); } else { if (ForumSettings::get('p_subject_all_caps')['p_subject_all_caps'] == '0' && Utils::is_all_uppercase($data['subject']) && !User::get()->is_admmod) { throw new Error('All caps subject forbidden', 400); } } } } // TODO : inbox full // Validate message if (ForumSettings::get('o_censoring') == '1') { $data['req_message'] = Utils::trim(Utils::censor($data['req_message'])); } if (empty($data['req_message'])) { throw new Error('No message or censored message', 400); } else { if (Utils::strlen($data['req_message']) > ForumEnv::get('FEATHER_MAX_POSTSIZE')) { throw new Error('Too long message', 400); } else { if (ForumSettings::get('p_subject_all_caps')['p_subject_all_caps'] == '0' && Utils::is_all_uppercase($data['subject']) && !User::get()->is_admmod) { throw new Error('All caps message forbidden', 400); } } } // Send ... TODO : when perms will be ready // Check if the receiver has the PM enabled // Check if he has reached his max limit of PM // Block feature ? if (!$conv) { $conv_data = array('subject' => $data['subject'], 'poster' => User::get()->username, 'poster_id' => User::get()->id, 'num_replies' => 0, 'last_post' => Container::get('now'), 'last_poster' => User::get()->username); $args['tid'] = $this->model->addConversation($conv_data); } if ($args['tid']) { $msg_data = array('poster' => User::get()->username, 'poster_id' => User::get()->id, 'poster_ip' => Utils::getIp(), 'message' => $data['req_message'], 'hide_smilies' => $data['smilies'], 'sent' => Container::get('now')); if ($conv) { // Reply to an existing conversation if ($msg_id = $this->model->addMessage($msg_data, $args['tid'])) { return Router::redirect(Router::pathFor('Conversations.home'), sprintf(__('Reply success', 'private_messages'), $conv->subject)); } } else { // Add message in conversation + add receiver (create new conversation) if ($msg_id = $this->model->addMessage($msg_data, $args['tid'], array($user->id, User::get()->id))) { return Router::redirect(Router::pathFor('Conversations.home'), sprintf(__('Send success', 'private_messages'), $user->username)); } } } else { throw new Error('Unable to create conversation'); } } } else { Container::get('hooks')->fire('conversationsPlugin.send.display'); // New conversation if (!is_null($args['uid'])) { if ($args['uid'] < 2) { throw new Error('Wrong user ID', 400); } if ($user = $this->model->getUserByID($args['uid'])) { View::setPageInfo(array('username' => Utils::escape($user->username))); } else { throw new Error('Unable to find user', 400); } } // Reply if (!is_null($args['tid'])) { if ($args['tid'] < 1) { throw new Error('Wrong conversation ID', 400); } if ($conv = $this->model->getConversation($args['tid'], User::get()->id)) { $inbox = DB::for_table('pms_folders')->find_one($conv->folder_id); $this->crumbs[Router::pathFor('Conversations.home', ['inbox_id' => $inbox['id']])] = $inbox['name']; $this->crumbs[] = __('Reply', 'private_messages'); $this->crumbs[] = $conv['subject']; Utils::generateBreadcrumbs($this->crumbs); return View::setPageInfo(array('current_inbox' => $inbox, 'conv' => $conv, 'msg_data' => $this->model->getMessagesFromConversation($args['tid'], User::get()->id, 5)))->addTemplate('reply.php')->display(); } else { throw new Error('Unknown conversation ID', 400); } } $this->crumbs[] = __('Send', 'private_messages'); if (isset($user)) { $this->crumbs[] = $user->username; } Utils::generateBreadcrumbs($this->crumbs); View::addTemplate('send.php')->display(); } }
public function get_search_results() { $search = array(); $search = Container::get('hooks')->fire('model.search.get_search_results_start', $search); $action = Input::query('action') ? Input::query('action') : null; $forums = Input::query('forums') ? is_array(Input::query('forums')) ? Input::query('forums') : array_filter(explode(',', Input::query('forums'))) : (Input::query('forums') ? array(Input::query('forums')) : array()); $sort_dir = Input::query('sort_dir') && Input::query('sort_dir') == 'DESC' ? 'DESC' : 'ASC'; $forums = array_map('intval', $forums); // Allow the old action names for backwards compatibility reasons if ($action == 'show_user') { $action = 'show_user_posts'; } elseif ($action == 'show_24h') { $action = 'show_recent'; } // If a search_id was supplied if (Input::query('search_id')) { $search_id = intval(Input::query('search_id')); if ($search_id < 1) { throw new Error(__('Bad request'), 400); } } elseif ($action == 'search') { $keywords = Input::query('keywords') ? utf8_strtolower(Utils::trim(Input::query('keywords'))) : null; $author = Input::query('author') ? utf8_strtolower(Utils::trim(Input::query('author'))) : null; if (preg_match('%^[\\*\\%]+$%', $keywords) || Utils::strlen(str_replace(array('*', '%'), '', $keywords)) < ForumEnv::get('FEATHER_SEARCH_MIN_WORD') && !$this->search->is_cjk($keywords)) { $keywords = ''; } if (preg_match('%^[\\*\\%]+$%', $author) || Utils::strlen(str_replace(array('*', '%'), '', $author)) < 2) { $author = ''; } if (!$keywords && !$author) { throw new Error(__('No terms'), 400); } if ($author) { $author = str_replace('*', '%', $author); } $show_as = Input::query('show_as') && Input::query('show_as') == 'topics' ? 'topics' : 'posts'; $sort_by = Input::query('sort_by') ? intval(Input::query('sort_by')) : 0; $search_in = !Input::query('search_in') || Input::query('search_in') == '0' ? 0 : (Input::query('search_in') == '1' ? 1 : -1); } elseif ($action == 'show_user_posts' || $action == 'show_user_topics' || $action == 'show_subscriptions') { $user_id = Input::query('user_id') ? intval(Input::query('user_id')) : User::get()->id; if ($user_id < 2) { throw new Error(__('Bad request'), 404); } // Subscribed topics can only be viewed by admins, moderators and the users themselves if ($action == 'show_subscriptions' && !User::get()->is_admmod && $user_id != User::get()->id) { throw new Error(__('No permission'), 403); } } elseif ($action == 'show_recent') { $interval = Input::query('value') ? intval(Input::query('value')) : 86400; } elseif ($action == 'show_replies') { if (User::get()->is_guest) { throw new Error(__('Bad request'), 404); } } elseif ($action != 'show_new' && $action != 'show_unanswered') { throw new Error(__('Bad request'), 404); } // If a valid search_id was supplied we attempt to fetch the search results from the db if (isset($search_id)) { $ident = User::get()->is_guest ? Utils::getIp() : User::get()->username; $search_data = DB::for_table('search_cache')->where('id', $search_id)->where('ident', $ident); $search_data = Container::get('hooks')->fireDB('model.search.get_search_results_search_data_query', $search_data); $search_data = $search_data->find_one_col('search_data'); if ($search_data) { $temp = unserialize($search_data); $temp = Container::get('hooks')->fire('model.search.get_search_results_temp', $temp); $search_ids = unserialize($temp['search_ids']); $num_hits = $temp['num_hits']; $sort_by = $temp['sort_by']; $sort_dir = $temp['sort_dir']; $show_as = $temp['show_as']; $search_type = $temp['search_type']; unset($temp); } else { throw new Error(__('No hits'), 404); } } else { $keyword_results = $author_results = array(); // Search a specific forum? $forum_sql = !empty($forums) || empty($forums) && ForumSettings::get('o_search_all_forums') == '0' && !User::get()->is_admmod ? ' AND t.forum_id IN (' . implode(',', $forums) . ')' : ''; if (!empty($author) || !empty($keywords)) { // Flood protection if (User::get()->last_search && time() - User::get()->last_search < User::get()->g_search_flood && time() - User::get()->last_search >= 0) { throw new Error(sprintf(__('Search flood'), User::get()->g_search_flood, User::get()->g_search_flood - (time() - User::get()->last_search)), 429); } if (!User::get()->is_guest) { $update_last_search = DB::for_table('users')->where('id', User::get()->id); } else { $update_last_search = DB::for_table('online')->where('ident', Utils::getIp()); } $update_last_search = Container::get('hooks')->fireDB('model.search.get_search_results_update_last_search', $update_last_search); $update_last_search = $update_last_search->update_many('last_search', time()); switch ($sort_by) { case 1: $sort_by_sql = $show_as == 'topics' ? 't.poster' : 'p.poster'; $sort_type = SORT_STRING; break; case 2: $sort_by_sql = 't.subject'; $sort_type = SORT_STRING; break; case 3: $sort_by_sql = 't.forum_id'; $sort_type = SORT_NUMERIC; break; case 4: $sort_by_sql = 't.last_post'; $sort_type = SORT_NUMERIC; break; default: $sort_by_sql = $show_as == 'topics' ? 't.last_post' : 'p.posted'; $sort_type = SORT_NUMERIC; break; } $sort_by = Container::get('hooks')->fire('model.search.get_search_results_sort_by', $sort_by); // If it's a search for keywords if ($keywords) { // split the keywords into words $keywords_array = $this->search->split_words($keywords, false); $keywords_array = Container::get('hooks')->fire('model.search.get_search_results_keywords_array', $keywords_array); if (empty($keywords_array)) { throw new Error(__('No hits'), 400); } // Should we search in message body or topic subject specifically? $search_in_cond = $search_in ? $search_in > 0 ? ' AND m.subject_match = 0' : ' AND m.subject_match = 1' : ''; $search_in_cond = Container::get('hooks')->fire('model.search.get_search_results_search_cond', $search_in_cond); $word_count = 0; $match_type = 'and'; $sort_data = array(); foreach ($keywords_array as $cur_word) { switch ($cur_word) { case 'and': case 'or': case 'not': $match_type = $cur_word; break; default: if ($this->search->is_cjk($cur_word)) { $where_cond = str_replace('*', '%', $cur_word); $where_cond_cjk = $search_in ? $search_in > 0 ? 'p.message LIKE %:where_cond%' : 't.subject LIKE %:where_cond%' : 'p.message LIKE %:where_cond% OR t.subject LIKE %:where_cond%'; $result = DB::for_table('posts')->raw_query('SELECT p.id AS post_id, p.topic_id, ' . $sort_by_sql . ' AS sort_by FROM ' . ForumSettings::get('db_prefix') . 'posts AS p INNER JOIN ' . ForumSettings::get('db_prefix') . 'topics AS t ON t.id=p.topic_id LEFT JOIN ' . ForumSettings::get('db_prefix') . 'forum_perms AS fp ON (fp.forum_id=t.forum_id AND fp.group_id=' . User::get()->g_id . ') WHERE (' . $where_cond_cjk . ') AND (fp.read_forum IS NULL OR fp.read_forum=1)' . $forum_sql, array(':where_cond' => $where_cond)); } else { $result = DB::for_table('posts')->raw_query('SELECT m.post_id, p.topic_id, ' . $sort_by_sql . ' AS sort_by FROM ' . ForumSettings::get('db_prefix') . 'search_words AS w INNER JOIN ' . ForumSettings::get('db_prefix') . 'search_matches AS m ON m.word_id = w.id INNER JOIN ' . ForumSettings::get('db_prefix') . 'posts AS p ON p.id=m.post_id INNER JOIN ' . ForumSettings::get('db_prefix') . 'topics AS t ON t.id=p.topic_id LEFT JOIN ' . ForumSettings::get('db_prefix') . 'forum_perms AS fp ON (fp.forum_id=t.forum_id AND fp.group_id=' . User::get()->g_id . ') WHERE w.word LIKE :where_cond' . $search_in_cond . ' AND (fp.read_forum IS NULL OR fp.read_forum=1)' . $forum_sql, array(':where_cond' => str_replace('*', '%', $cur_word))); } $result = Container::get('hooks')->fireDB('model.search.get_search_results_search_first_query', $result); $result = $result->find_many(); $row = array(); foreach ($result as $temp) { $row[$temp['post_id']] = $temp['topic_id']; if (!$word_count) { $keyword_results[$temp['post_id']] = $temp['topic_id']; $sort_data[$temp['post_id']] = $temp['sort_by']; } elseif ($match_type == 'or') { $keyword_results[$temp['post_id']] = $temp['topic_id']; $sort_data[$temp['post_id']] = $temp['sort_by']; } elseif ($match_type == 'not') { unset($keyword_results[$temp['post_id']]); unset($sort_data[$temp['post_id']]); } } if ($match_type == 'and' && $word_count) { foreach ($keyword_results as $post_id => $topic_id) { if (!isset($row[$post_id])) { unset($keyword_results[$post_id]); unset($sort_data[$post_id]); } } } ++$word_count; $pdo = DB::get_db(); $pdo = null; break; } } $keyword_results = Container::get('hooks')->fire('model.search.get_search_results_search_keyword_results', $keyword_results); // Sort the results - annoyingly array_multisort re-indexes arrays with numeric keys, so we need to split the keys out into a separate array then combine them again after $post_ids = array_keys($keyword_results); $topic_ids = array_values($keyword_results); array_multisort(array_values($sort_data), $sort_dir == 'DESC' ? SORT_DESC : SORT_ASC, $sort_type, $post_ids, $topic_ids); // combine the arrays back into a key => value array $keyword_results = array_combine($post_ids, $topic_ids); unset($sort_data, $post_ids, $topic_ids); } // If it's a search for author name (and that author name isn't Guest) if ($author && $author != 'guest' && $author != utf8_strtolower(__('Guest'))) { $username_exists = DB::for_table('users')->select('id')->where_like('username', $author); $username_exists = Container::get('hooks')->fireDB('model.search.get_search_results_username_exists', $username_exists); $username_exists = $username_exists->find_many(); if ($username_exists) { $user_ids = array(); foreach ($username_exists as $row) { $user_ids[] = $row['id']; } $result = DB::for_table('posts')->raw_query('SELECT p.id AS post_id, p.topic_id FROM ' . ForumSettings::get('db_prefix') . 'posts AS p INNER JOIN ' . ForumSettings::get('db_prefix') . 'topics AS t ON t.id=p.topic_id LEFT JOIN ' . ForumSettings::get('db_prefix') . 'forum_perms AS fp ON (fp.forum_id=t.forum_id AND fp.group_id=' . User::get()->g_id . ') WHERE (fp.read_forum IS NULL OR fp.read_forum=1) AND p.poster_id IN(' . implode(',', $user_ids) . ')' . $forum_sql . ' ORDER BY ' . $sort_by_sql . ' ' . $sort_dir); $result = Container::get('hooks')->fireDB('model.search.get_search_results_search_second_query', $result); $result = $result->find_many(); foreach ($result as $temp) { $author_results[$temp['post_id']] = $temp['topic_id']; } $pdo = DB::get_db(); $pdo = null; } } // If we searched for both keywords and author name we want the intersection between the results if ($author && $keywords) { $search_ids = array_intersect_assoc($keyword_results, $author_results); $search_type = array('both', array($keywords, Utils::trim(Input::query('author'))), implode(',', $forums), $search_in); } elseif ($keywords) { $search_ids = $keyword_results; $search_type = array('keywords', $keywords, implode(',', $forums), $search_in); } else { $search_ids = $author_results; $search_type = array('author', Utils::trim(Input::query('author')), implode(',', $forums), $search_in); } $search_ids = Container::get('hooks')->fire('model.search.get_search_results_search_ids', $search_ids); $search_type = Container::get('hooks')->fire('model.search.get_search_results_search_type', $search_type); unset($keyword_results, $author_results); if ($show_as == 'topics') { $search_ids = array_values($search_ids); } else { $search_ids = array_keys($search_ids); } $search_ids = array_unique($search_ids); $search_ids = Container::get('hooks')->fire('model.search.get_search_results_search_ids', $search_ids); $search_type = Container::get('hooks')->fire('model.search.get_search_results_search_type', $search_type); $num_hits = count($search_ids); if (!$num_hits) { throw new Error(__('No hits'), 400); } } elseif ($action == 'show_new' || $action == 'show_recent' || $action == 'show_replies' || $action == 'show_user_posts' || $action == 'show_user_topics' || $action == 'show_subscriptions' || $action == 'show_unanswered') { $search_type = array('action', $action); $show_as = 'topics'; // We want to sort things after last post $sort_by = 0; $sort_dir = 'DESC'; $result['where'] = array(array('fp.read_forum' => 'IS NULL'), array('fp.read_forum' => '1')); // If it's a search for new posts since last visit if ($action == 'show_new') { if (User::get()->is_guest) { throw new Error(__('No permission'), 403); } $result = DB::for_table('topics')->table_alias('t')->select('t.id')->left_outer_join('forum_perms', array('fp.forum_id', '=', 't.forum_id'), 'fp')->left_outer_join('forum_perms', array('fp.group_id', '=', User::get()->g_id), null, true)->where_any_is($result['where'])->where_gt('t.last_post', User::get()->last_visit)->where_null('t.moved_to')->order_by_desc('t.last_post'); if (Input::query('fid')) { $result = $result->where('t.forum_id', intval(Input::query('fid'))); } $result = Container::get('hooks')->fireDB('model.search.get_search_results_topic_query', $result); $result = $result->find_many(); $num_hits = count($result); if (!$num_hits) { return Router::redirect(Router::pathFor('home'), __('No new posts')); } } elseif ($action == 'show_recent') { $result = DB::for_table('topics')->table_alias('t')->select('t.id')->left_outer_join('forum_perms', array('fp.forum_id', '=', 't.forum_id'), 'fp')->left_outer_join('forum_perms', array('fp.group_id', '=', User::get()->g_id), null, true)->where_any_is($result['where'])->where_gt('t.last_post', time() - $interval)->where_null('t.moved_to')->order_by_desc('t.last_post'); if (Input::query('fid')) { $result = $result->where('t.forum_id', intval(Input::query('fid'))); } $result = Container::get('hooks')->fireDB('model.search.get_search_results_topic_query', $result); $result = $result->find_many(); $num_hits = count($result); if (!$num_hits) { return Router::redirect(Router::pathFor('home'), __('No recent posts')); } } elseif ($action == 'show_replies') { $result = DB::for_table('topics')->table_alias('t')->select('t.id')->inner_join('posts', array('t.id', '=', 'p.topic_id'), 'p')->left_outer_join('forum_perms', array('fp.forum_id', '=', 't.forum_id'), 'fp')->left_outer_join('forum_perms', array('fp.group_id', '=', User::get()->g_id), null, true)->where_any_is($result['where'])->where('p.poster_id', User::get()->id)->group_by('t.id'); if (ForumSettings::get('db_type') == 'pgsql') { $result = $result->group_by('t.last_post'); } $result = Container::get('hooks')->fireDB('model.search.get_search_results_topic_query', $result); $result = $result->find_many(); $num_hits = count($result); if (!$num_hits) { return Router::redirect(Router::pathFor('home'), __('No user posts')); } } elseif ($action == 'show_user_posts') { $show_as = 'posts'; $result = DB::for_table('posts')->table_alias('p')->select('p.id')->inner_join('topics', array('p.topic_id', '=', 't.id'), 't')->left_outer_join('forum_perms', array('fp.forum_id', '=', 't.forum_id'), 'fp')->left_outer_join('forum_perms', array('fp.group_id', '=', User::get()->g_id), null, true)->where_any_is($result['where'])->where('p.poster_id', $user_id)->order_by_desc('p.posted'); $result = Container::get('hooks')->fireDB('model.search.get_search_results_post_query', $result); $result = $result->find_many(); $num_hits = count($result); if (!$num_hits) { return Router::redirect(Router::pathFor('search'), __('No user posts')); } // Pass on the user ID so that we can later know whose posts we're searching for $search_type[2] = $user_id; } elseif ($action == 'show_user_topics') { $result = DB::for_table('topics')->table_alias('t')->select('t.id')->inner_join('posts', array('t.first_post_id', '=', 'p.id'), 'p')->left_outer_join('forum_perms', array('fp.forum_id', '=', 't.forum_id'), 'fp')->left_outer_join('forum_perms', array('fp.group_id', '=', User::get()->g_id), null, true)->where_any_is($result['where'])->where('p.poster_id', $user_id)->order_by_desc('t.last_post'); $result = Container::get('hooks')->fireDB('model.search.get_search_results_topic_query', $result); $result = $result->find_many(); $num_hits = count($result); if (!$num_hits) { return Router::redirect(Router::pathFor('search'), __('No user topics')); } // Pass on the user ID so that we can later know whose topics we're searching for $search_type[2] = $user_id; } elseif ($action == 'show_subscriptions') { if (User::get()->is_guest) { throw new Error(__('Bad request'), 404); } $result = DB::for_table('topics')->table_alias('t')->select('t.id')->inner_join('topic_subscriptions', array('t.id', '=', 's.topic_id'), 's')->inner_join('topic_subscriptions', array('s.user_id', '=', $user_id), null, true)->left_outer_join('forum_perms', array('fp.forum_id', '=', 't.forum_id'), 'fp')->left_outer_join('forum_perms', array('fp.group_id', '=', User::get()->g_id), null, true)->where_any_is($result['where'])->order_by_desc('t.last_post'); $result = Container::get('hooks')->fireDB('model.search.get_search_results_topic_query', $result); $result = $result->find_many(); $num_hits = count($result); if (!$num_hits) { return Router::redirect(Router::pathFor('search'), __('No subscriptions')); } // Pass on user ID so that we can later know whose subscriptions we're searching for $search_type[2] = $user_id; } else { $result = DB::for_table('topics')->table_alias('t')->select('t.id')->left_outer_join('forum_perms', array('fp.forum_id', '=', 't.forum_id'), 'fp')->left_outer_join('forum_perms', array('fp.group_id', '=', User::get()->g_id), null, true)->where('t.num_replies', 0)->where_null('t.moved_to')->where_any_is($result['where'])->order_by_desc('t.last_post'); $result = Container::get('hooks')->fireDB('model.search.get_search_results_topic_query', $result); $result = $result->find_many(); $num_hits = count($result); if (!$num_hits) { return Router::redirect(Router::pathFor('home'), __('No unanswered')); } } $search_ids = array(); foreach ($result as $row) { $search_ids[] = $row['id']; } $pdo = DB::get_db(); $pdo = null; } else { throw new Error(__('Bad request'), 404); } // Prune "old" search results $old_searches = array(); $result = DB::for_table('online')->select('ident'); $result = Container::get('hooks')->fireDB('model.search.get_search_results_prune_search', $result); $result = $result->find_many(); if ($result) { foreach ($result as $row) { $old_searches[] = $row['ident']; } $delete_cache = DB::for_table('search_cache')->where_not_in('ident', $old_searches); $delete_cache = Container::get('hooks')->fireDB('model.search.get_search_results_delete_cache', $delete_cache); $delete_cache = $delete_cache->delete_many(); } // Fill an array with our results and search properties $temp = serialize(array('search_ids' => serialize($search_ids), 'num_hits' => $num_hits, 'sort_by' => $sort_by, 'sort_dir' => $sort_dir, 'show_as' => $show_as, 'search_type' => $search_type)); $search_id = mt_rand(1, 2147483647); $ident = User::get()->is_guest ? Utils::getIp() : User::get()->username; $cache['insert'] = array('id' => $search_id, 'ident' => $ident, 'search_data' => $temp); $cache = DB::for_table('search_cache')->create()->set($cache['insert']); $cache = Container::get('hooks')->fireDB('model.search.get_search_results_update_cache', $cache); $cache = $cache->save(); } // If we're on the new posts search, display a "mark all as read" link if (!User::get()->is_guest && $search_type[0] == 'action' && $search_type[1] == 'show_new') { $search['forum_actions'][] = '<a href="' . Router::pathFor('markRead') . '">' . __('Mark all as read') . '</a>'; } // Fetch results to display if (!empty($search_ids)) { // We have results $search['is_result'] = true; switch ($sort_by) { case 1: $sort_by_sql = $show_as == 'topics' ? 't.poster' : 'p.poster'; break; case 2: $sort_by_sql = 't.subject'; break; case 3: $sort_by_sql = 't.forum_id'; break; default: $sort_by_sql = $show_as == 'topics' ? 't.last_post' : 'p.posted'; break; } // Determine the topic or post offset (based on $_GET['p']) $per_page = $show_as == 'posts' ? User::get()->disp_posts : User::get()->disp_topics; $num_pages = ceil($num_hits / $per_page); $p = !Input::query('p') || Input::query('p') <= 1 || Input::query('p') > $num_pages ? 1 : intval(Input::query('p')); $start_from = $per_page * ($p - 1); $search['start_from'] = $start_from; // Generate paging links $search['paging_links'] = '<span class="pages-label">' . __('Pages') . ' </span>' . Url::paginate_old($num_pages, $p, '?search_id=' . $search_id); // throw away the first $start_from of $search_ids, only keep the top $per_page of $search_ids $search_ids = array_slice($search_ids, $start_from, $per_page); // Run the query and fetch the results if ($show_as == 'posts') { $result['select'] = array('pid' => 'p.id', 'pposter' => 'p.poster', 'pposted' => 'p.posted', 'p.poster_id', 'p.message', 'p.hide_smilies', 'tid' => 't.id', 't.poster', 't.subject', 't.first_post_id', 't.last_post', 't.last_post_id', 't.last_poster', 't.num_replies', 't.forum_id', 'f.forum_name'); $result = DB::for_table('posts')->table_alias('p')->select_many($result['select'])->inner_join('topics', array('t.id', '=', 'p.topic_id'), 't')->inner_join('forums', array('f.id', '=', 't.forum_id'), 'f')->where_in('p.id', $search_ids)->order_by($sort_by_sql, $sort_dir); $result = Container::get('hooks')->fireDB('model.search.get_search_results_select_posts_query', $result); } else { $result['select'] = array('tid' => 't.id', 't.poster', 't.subject', 't.last_post', 't.last_post_id', 't.last_poster', 't.num_replies', 't.closed', 't.sticky', 't.forum_id', 'f.forum_name'); $result = DB::for_table('topics')->table_alias('t')->select_many($result['select'])->inner_join('forums', array('f.id', '=', 't.forum_id'), 'f')->where_in('t.id', $search_ids)->order_by($sort_by_sql, $sort_dir); $result = Container::get('hooks')->fireDB('model.search.get_search_results_select_topics_query', $result); } $result = $result->find_array(); $search['search_set'] = array(); foreach ($result as $row) { $search['search_set'][] = $row; } $search['crumbs_text']['show_as'] = __('Search'); if ($search_type[0] == 'action') { if ($search_type[1] == 'show_user_topics') { $search['crumbs_text']['search_type'] = '<a href="' . Router::pathFor('search') . '?action=show_user_topics&user_id=' . $search_type[2] . '">' . sprintf(__('Quick search show_user_topics'), Utils::escape($search['search_set'][0]['poster'])) . '</a>'; } elseif ($search_type[1] == 'show_user_posts') { $search['crumbs_text']['search_type'] = '<a href="' . Router::pathFor('search') . '?action=show_user_posts&user_id=' . $search_type[2] . '">' . sprintf(__('Quick search show_user_posts'), Utils::escape($search['search_set'][0]['pposter'])) . '</a>'; } elseif ($search_type[1] == 'show_subscriptions') { // Fetch username of subscriber $subscriber_id = $search_type[2]; $subscriber_name = DB::for_table('users')->where('id', $subscriber_id); $subscriber_name = Container::get('hooks')->fireDB('model.search.get_search_results_subscriber_name', $result); $subscriber_name = $subscriber_name->find_one_col('username'); if (!$subscriber_name) { throw new Error(__('Bad request'), 404); } $search['crumbs_text']['search_type'] = '<a href="' . Router::pathFor('search') . '?action=show_subscription&user_id=' . $subscriber_id . '">' . sprintf(__('Quick search show_subscriptions'), Utils::escape($subscriber_name)) . '</a>'; } else { $search_url = str_replace('_', '/', $search_type[1]); $search['crumbs_text']['search_type'] = '<a href="' . Router::pathFor('search') . $search_url . '">' . __('Quick search ' . $search_type[1]) . '</a>'; } } else { $keywords = $author = ''; if ($search_type[0] == 'both') { list($keywords, $author) = $search_type[1]; $search['crumbs_text']['search_type'] = sprintf(__('By both show as ' . $show_as), Utils::escape($keywords), Utils::escape($author)); } elseif ($search_type[0] == 'keywords') { $keywords = $search_type[1]; $search['crumbs_text']['search_type'] = sprintf(__('By keywords show as ' . $show_as), Utils::escape($keywords)); } elseif ($search_type[0] == 'author') { $author = $search_type[1]; $search['crumbs_text']['search_type'] = sprintf(__('By user show as ' . $show_as), Utils::escape($author)); } $search['crumbs_text']['search_type'] = '<a href="' . Router::pathFor('search') . '?action=search&keywords=' . urlencode($keywords) . '&author=' . urlencode($author) . '&forums=' . $search_type[2] . '&search_in=' . $search_type[3] . '&sort_by=' . $sort_by . '&sort_dir=' . $sort_dir . '&show_as=' . $show_as . '">' . $search['crumbs_text']['search_type'] . '</a>'; } } $search['show_as'] = $show_as; $search = Container::get('hooks')->fire('model.search.get_search_results', $search); return $search; }