/** * Handles AJAX from /admin/tags * Used to delete and rename tags */ public function ajax_tags($handler_vars) { Utils::check_request_method(array('POST')); $wsse = Utils::WSSE($handler_vars['nonce'], $handler_vars['timestamp']); if ($handler_vars['digest'] != $wsse['digest']) { Session::error(_t('WSSE authentication failed.')); echo Session::messages_get(true, array('Format', 'json_messages')); return; } $tag_names = array(); $theme_dir = Plugins::filter('admin_theme_dir', Site::get_dir('admin_theme', true)); $this->theme = Themes::create('admin', 'RawPHPEngine', $theme_dir); $action = $this->handler_vars['action']; switch ($action) { case 'delete': foreach ($_POST as $id => $delete) { // skip POST elements which are not tag ids if (preg_match('/^tag_\\d+/', $id) && $delete) { $id = substr($id, 4); $tag = Tags::get_by_id($id); $tag_names[] = $tag->term_display; Tags::vocabulary()->delete_term($tag); } } $msg_status = _n(_t('Tag %s has been deleted.', array(implode('', $tag_names))), _t('%d tags have been deleted.', array(count($tag_names))), count($tag_names)); Session::notice($msg_status); break; case 'rename': if (!isset($this->handler_vars['master'])) { Session::error(_t('Error: New name not specified.')); echo Session::messages_get(true, array('Format', 'json_messages')); return; } $master = $this->handler_vars['master']; $tag_names = array(); foreach ($_POST as $id => $rename) { // skip POST elements which are not tag ids if (preg_match('/^tag_\\d+/', $id) && $rename) { $id = substr($id, 4); $tag = Tags::get_by_id($id); $tag_names[] = $tag->term_display; } } Tags::vocabulary()->merge($master, $tag_names); $msg_status = sprintf(_n('Tag %1$s has been renamed to %2$s.', 'Tags %1$s have been renamed to %2$s.', count($tag_names)), implode($tag_names, ', '), $master); Session::notice($msg_status); break; } $this->theme->tags = Tags::vocabulary()->get_tree(); $this->theme->max = Tags::vocabulary()->max_count(); echo json_encode(array('msg' => Session::messages_get(true, 'array'), 'tags' => $this->theme->fetch('tag_collection'))); }
/** * Handles AJAX from /comments. * Used to edit comments inline. */ public function action_auth_ajax_in_edit(ActionHandler $handler) { Utils::check_request_method(array('POST')); $handler_vars = $handler->handler_vars; $wsse = Utils::WSSE($handler_vars['nonce'], $handler_vars['timestamp']); if ($handler_vars['digest'] != $wsse['digest']) { Session::error(_t('WSSE authentication failed.')); echo Session::messages_get(true, array('Format', 'json_messages')); return; } $comment = Comment::get($handler_vars['id']); if (!ACL::access_check($comment->get_access(), 'edit')) { Session::error(_t('You do not have permission to edit this comment.')); echo Session::messages_get(true, array('Format', 'json_messages')); return; } if (isset($handler_vars['author']) && $handler_vars['author'] != '') { $comment->name = $handler_vars['author']; } if (isset($handler_vars['url'])) { $comment->url = $handler_vars['url']; } if (isset($handler_vars['email']) && $handler_vars['email'] != '') { $comment->email = $handler_vars['email']; } if (isset($handler_vars['content']) && $handler_vars['content'] != '') { $comment->content = $handler_vars['content']; } if (isset($handler_vars['time']) && $handler_vars['time'] != '' && isset($handler_vars['date']) && $handler_vars['date'] != '') { $seconds = date('s', strtotime($comment->date)); $date = date('Y-m-d H:i:s', strtotime($handler_vars['date'] . ' ' . $handler_vars['time'] . ':' . $seconds)); $comment->date = $date; } $comment->update(); Session::notice(_t('Updated 1 comment.')); echo Session::messages_get(true, array('Format', 'json_messages')); }
/** * Handles AJAX requests to update comments, comment moderation */ public function ajax_update_comment( $handler_vars ) { Utils::check_request_method( array( 'POST' ) ); // check WSSE authentication $wsse = Utils::WSSE( $handler_vars['nonce'], $handler_vars['timestamp'] ); if ( $handler_vars['digest'] != $wsse['digest'] ) { Session::error( _t( 'WSSE authentication failed.' ) ); echo Session::messages_get( true, array( 'Format', 'json_messages' ) ); return; } $ids = array(); foreach ( $_POST as $id => $update ) { // skip POST elements which are not comment ids if ( preg_match( '/^p\d+$/', $id ) && $update ) { $ids[] = (int) substr( $id, 1 ); } } if ( ( ! isset( $ids ) || empty( $ids ) ) && $handler_vars['action'] == 'delete' ) { Session::notice( _t( 'No comments selected.' ) ); echo Session::messages_get( true, array( 'Format', 'json_messages' ) ); return; } $comments = Comments::get( array( 'id' => $ids, 'nolimit' => true ) ); Plugins::act( 'admin_moderate_comments', $handler_vars['action'], $comments, $this ); $status_msg = _t( 'Unknown action "%s"', array( $handler_vars['action'] ) ); switch ( $handler_vars['action'] ) { case 'delete_spam': Comments::delete_by_status( Comment::STATUS_SPAM ); $status_msg = _t( 'Deleted all spam comments' ); break; case 'delete_unapproved': Comments::delete_by_status( Comment::STATUS_UNAPPROVED ); $status_msg = _t( 'Deleted all unapproved comments' ); break; case 'delete': // Comments marked for deletion Comments::delete_these( $comments ); $status_msg = sprintf( _n( 'Deleted %d comment', 'Deleted %d comments', count( $ids ) ), count( $ids ) ); break; case 'spam': // Comments marked as spam Comments::moderate_these( $comments, Comment::STATUS_SPAM ); $status_msg = sprintf( _n( 'Marked %d comment as spam', 'Marked %d comments as spam', count( $ids ) ), count( $ids ) ); break; case 'approve': case 'approved': // Comments marked for approval Comments::moderate_these( $comments, Comment::STATUS_APPROVED ); $status_msg = sprintf( _n( 'Approved %d comment', 'Approved %d comments', count( $ids ) ), count( $ids ) ); break; case 'unapprove': case 'unapproved': // Comments marked for unapproval Comments::moderate_these( $comments, Comment::STATUS_UNAPPROVED ); $status_msg = sprintf( _n( 'Unapproved %d comment', 'Unapproved %d comments', count( $ids ) ), count( $ids ) ); break; default: // Specific plugin-supplied action $status_msg = Plugins::filter( 'admin_comments_action', $status_msg, $handler_vars['action'], $comments ); break; } Session::notice( $status_msg ); echo Session::messages_get( true, array( 'Format', 'json_messages' ) ); }
/** * Handles spam deletion * * @return void **/ public function action_auth_ajax_deleteall($handler) { $result = array(); switch ($handler->handler_vars['target']) { case 'spam': if (!User::identify()->can('manage_all_comments')) { Session::error(_t('You do not have permission to do that action.')); break; } $total = Comments::count_total(Comment::STATUS_SPAM, FALSE); Comments::delete_by_status(Comment::status('spam')); Session::notice(sprintf(_t('Deleted all %s spam comments.'), $total)); break; case 'logs': if (!User::identify()->can('manage_logs')) { Session::error(_t('You do not have permission to do that action.')); break; } $to_delete = EventLog::get(array('date' => 'any', 'nolimit' => 1)); $count = 0; foreach ($to_delete as $log) { $log->delete(); $count++; } Session::notice(sprintf(_t('Deleted all %s log entries.'), $count)); break; } $result['messages'] = Session::messages_get(true, 'array'); echo json_encode($result); }
/** * Handles AJAX from /logs. * Used to delete logs. */ public function ajax_delete_logs($handler_vars) { Utils::check_request_method(array('POST')); $count = 0; $wsse = Utils::WSSE($handler_vars['nonce'], $handler_vars['timestamp']); if ($handler_vars['digest'] != $wsse['digest']) { Session::error(_t('WSSE authentication failed.')); echo Session::messages_get(true, array('Format', 'json_messages')); return; } foreach ($_POST as $id => $delete) { // skip POST elements which are not log ids if (preg_match('/^p\\d+$/', $id) && $delete) { $id = (int) substr($id, 1); $ids[] = array('id' => $id); } } if ((!isset($ids) || empty($ids)) && $handler_vars['action'] != 'purge') { Session::notice(_t('No logs selected.')); echo Session::messages_get(true, array('Format', 'json_messages')); return; } switch ($handler_vars['action']) { case 'delete': $to_delete = EventLog::get(array('date' => 'any', 'where' => $ids, 'nolimit' => 1)); foreach ($to_delete as $log) { $log->delete(); $count++; } Session::notice(_t('Deleted %d logs.', array($count))); break; case 'purge': $result = EventLog::purge(); Session::notice(_t('Logs purged.')); break; } echo Session::messages_get(true, array('Format', 'json_messages')); }
/** * Handles POST requests from the Users listing (ie: creating a new user) */ public function post_users() { $wsse = Utils::WSSE($this->handler_vars['nonce'], $this->handler_vars['timestamp']); if ($this->handler_vars['password_digest'] != $wsse['digest']) { Session::error(_t('WSSE authentication failed.')); return Session::messages_get(true, 'array'); } $this->fetch_users(); $extract = $this->handler_vars->filter_keys('newuser', 'delete', 'new_pass1', 'new_pass2', 'new_email', 'new_username'); foreach ($extract as $key => $value) { ${$key} = $value; } if (isset($newuser)) { $action = 'newuser'; } elseif (isset($delete)) { $action = 'delete'; } $error = ''; if (isset($action) && 'newuser' == $action) { if (!isset($new_pass1) || !isset($new_pass2) || empty($new_pass1) || empty($new_pass2)) { Session::error(_t('Password is required.'), 'adduser'); } else { if ($new_pass1 !== $new_pass2) { Session::error(_t('Password mis-match.'), 'adduser'); } } if (!isset($new_email) || empty($new_email) || !strstr($new_email, '@')) { Session::error(_t('Please supply a valid email address.'), 'adduser'); } if (!isset($new_username) || empty($new_username)) { Session::error(_t('Please supply a user name.'), 'adduser'); } // safety check to make sure no such username exists $user = User::get_by_name($new_username); if (isset($user->id)) { Session::error(_t('That username is already assigned.'), 'adduser'); } if (!Session::has_errors('adduser')) { $user = new User(array('username' => $new_username, 'email' => $new_email, 'password' => Utils::crypt($new_pass1))); if ($user->insert()) { Session::notice(_t("Added user '%s'", array($new_username))); } else { $dberror = DB::get_last_error(); Session::error($dberror[2], 'adduser'); } } else { $settings = array(); if (isset($new_username)) { $settings['new_username'] = $new_username; } if (isset($new_email)) { $settings['new_email'] = $new_email; } $this->theme->assign('settings', $settings); } } else { if (isset($action) && 'delete' == $action) { $this->update_users($this->handler_vars); } } $this->theme->display('users'); }
/** * Update an array of POSTed users. */ public function update_users($handler_vars) { if (isset($handler_vars['delete'])) { $currentuser = User::identify(); $wsse = Utils::WSSE($handler_vars['nonce'], $handler_vars['timestamp']); if (isset($handler_vars['digest']) && $handler_vars['digest'] != $wsse['digest']) { Session::error(_t('WSSE authentication failed.')); return Session::messages_get(true, 'array'); } foreach ($_POST as $id => $delete) { // skip POST elements which are not user ids if (preg_match('/^p\\d+$/', $id) && $delete) { $id = (int) substr($id, 1); $ids[] = array('id' => $id); } } if (isset($handler_vars['checkbox_ids'])) { $checkbox_ids = $handler_vars['checkbox_ids']; foreach ($checkbox_ids as $id => $delete) { if ($delete) { $ids[] = array('id' => $id); } } } $count = 0; if (!isset($ids)) { Session::notice(_t('No users deleted.')); return Session::messages_get(true, 'array'); } foreach ($ids as $id) { $id = $id['id']; $user = User::get_by_id($id); if ($currentuser != $user) { $assign = intval($handler_vars['reassign']); if ($user->id == $assign) { return; } $posts = Posts::get(array('user_id' => $user->id, 'nolimit' => 1)); if (isset($posts[0])) { if (0 == $assign) { foreach ($posts as $post) { $post->delete(); } } else { Posts::reassign($assign, $posts); } } $user->delete(); } else { $msg_status = _t('You cannot delete yourself.'); } $count++; } if (!isset($msg_status)) { $msg_status = sprintf(_t('Deleted %d users.'), $count); } Session::notice($msg_status); } }
/** * Add or delete groups. */ public function update_groups($handler_vars, $ajax = true) { $wsse = Utils::WSSE($handler_vars['nonce'], $handler_vars['timestamp']); if (isset($handler_vars['digest']) && $handler_vars['digest'] != $wsse['digest'] || isset($handler_vars['password_digest']) && $handler_vars['password_digest'] != $wsse['digest']) { Session::error(_t('WSSE authentication failed.')); return Session::messages_get(true, 'array'); } if (isset($handler_vars['password_digest']) || isset($handler_vars['digest'])) { if (isset($handler_vars['action']) && $handler_vars['action'] == 'add' || isset($handler_vars['newgroup'])) { if (isset($handler_vars['newgroup'])) { $name = trim($handler_vars['new_groupname']); } else { $name = trim($handler_vars['name']); } $settings = array('name' => $name); $this->theme->addform = $settings; if (UserGroup::exists($name)) { Session::notice(sprintf(_t('The group %s already exists'), $name)); if ($ajax) { return Session::messages_get(true, 'array'); } else { return; } } elseif (empty($name)) { Session::notice(_t('The group must have a name')); if ($ajax) { return Session::message_get(true, 'array'); } else { return; } } else { $groupdata = array('name' => $name); $group = UserGroup::create($groupdata); Session::notice(sprintf(_t('Added group %s'), $name)); // reload the groups $this->theme->groups = UserGroups::get_all(); $this->theme->addform = array(); } if ($ajax) { return Session::messages_get(true, 'array'); } else { if (!$ajax) { Utils::redirect(URL::get('admin', 'page=groups')); } } } if (isset($handler_vars['action']) && $handler_vars['action'] == 'delete' && $ajax == true) { $ids = array(); foreach ($_POST as $id => $delete) { // skip POST elements which are not group ids if (preg_match('/^p\\d+$/', $id) && $delete) { $id = (int) substr($id, 1); $ids[] = array('id' => $id); } } $count = 0; if (!isset($ids)) { Session::notice(_t('No groups deleted.')); return Session::messages_get(true, 'array'); } foreach ($ids as $id) { $id = $id['id']; $group = UserGroup::get_by_id($id); $group->delete(); $count++; } if (!isset($msg_status)) { $msg_status = sprintf(_t('Deleted %d groups.'), $count); } Session::notice($msg_status); return Session::messages_get(true, 'array'); } } }
/** * Altered copy of AdminHandler::post_publish(): * - Throws exceptions rather than Session notices so we can return errors to AJAX calls; * - Does not redirect but echo a JSON object with the post's ID and slug * * @see AdminHandler::post_publish() * * @param AjaxHandler $that The AjaxHandler instance */ public function action_auth_ajax_autosave($handler) { // @todo until ACL checks forr this are added, make inoperable return null; $response = array(); try { $post_id = 0; if (isset($handler->handler_vars['id'])) { $post_id = intval($handler->handler_vars['id']); } // If an id has been passed in, we're updating an existing post, otherwise we're creating one if (0 !== $post_id) { $post = Post::get(array('id' => $post_id, 'status' => Post::status('any'))); $this->theme->admin_page = sprintf(_t('Publish %s'), Plugins::filter('post_type_display', Post::type_name($post->content_type), 'singular')); $form = $post->get_form('ajax'); $post->title = $form->title->value; if ($form->newslug->value == '') { Session::notice(_t('A post slug cannot be empty. Keeping old slug.')); } elseif ($form->newslug->value != $form->slug->value) { $post->slug = $form->newslug->value; } $post->tags = $form->tags->value; $post->content = $form->content->value; $post->content_type = $form->content_type->value; // if not previously published and the user wants to publish now, change the pubdate to the current date/time // if the post pubdate is <= the current date/time. if ($post->status != Post::status('published') && $form->status->value == Post::status('published') && HabariDateTime::date_create($form->pubdate->value)->int <= HabariDateTime::date_create()->int) { $post->pubdate = HabariDateTime::date_create(); } else { $post->pubdate = HabariDateTime::date_create($form->pubdate->value); } $minor = $form->minor_edit->value && $post->status != Post::status('draft'); $post->status = $form->status->value; } else { $post = new Post(); $form = $post->get_form('ajax'); $form->set_option('form_action', URL::get('admin', 'page=publish')); $postdata = array('slug' => $form->newslug->value, 'title' => $form->title->value, 'tags' => $form->tags->value, 'content' => $form->content->value, 'user_id' => User::identify()->id, 'pubdate' => HabariDateTime::date_create($form->pubdate->value), 'status' => $form->status->value, 'content_type' => $form->content_type->value); $minor = false; $post = Post::create($postdata); } if ($post->pubdate->int > HabariDateTime::date_create()->int && $post->status == Post::status('published')) { $post->status = Post::status('scheduled'); } $post->info->comments_disabled = !$form->comments_enabled->value; Plugins::act('publish_post', $post, $form); $post->update($minor); $permalink = $post->status != Post::status('published') ? $post->permalink . '?preview=1' : $post->permalink; Session::notice(sprintf(_t('The post %1$s has been saved as %2$s.'), sprintf('<a href="%1$s">\'%2$s\'</a>', $permalink, htmlspecialchars($post->title)), Post::status_name($post->status))); if ($post->slug != Utils::slugify($post->title)) { Session::notice(sprintf(_t('The content address is \'%1$s\'.'), $post->slug)); } $response['post_id'] = $post->id; $response['post_slug'] = $post->slug; $response['messages'] = Session::messages_get(true, 'array'); ob_end_clean(); echo json_encode($response); // Prevent rest of adminhandler to run, we only wanted to save! exit; } catch (Exception $e) { $response['error'] = $e->getMessage(); ob_end_clean(); echo json_encode($response); // Prevent rest of adminhandler to run, we only wanted to save! exit; } }