X-Git-Url: https://git.mxchange.org/?a=blobdiff_plain;f=plugins%2FUserFlag%2Fadminprofileflag.php;h=df0450f66a53d6cbd4a80c13d963cee3b3acec94;hb=22047f6412811cb340aee6ba49d15257581b5aa9;hp=1ac76b506589125b3036c4a50fd1c2b5e09a51c8;hpb=6a1afda259c5223449f679a64f932e36df5ebe39;p=quix0rs-gnu-social.git diff --git a/plugins/UserFlag/adminprofileflag.php b/plugins/UserFlag/adminprofileflag.php index 1ac76b5065..df0450f66a 100644 --- a/plugins/UserFlag/adminprofileflag.php +++ b/plugins/UserFlag/adminprofileflag.php @@ -40,9 +40,11 @@ if (!defined('STATUSNET')) { * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 * @link http://status.net/ */ - class AdminprofileflagAction extends Action { + var $page = null; + var $profiles = null; + /** * Take arguments for running * @@ -50,11 +52,51 @@ class AdminprofileflagAction extends Action * * @return boolean success flag */ - function prepare($args) { parent::prepare($args); + $user = common_current_user(); + + // User must be logged in. + + if (!common_logged_in()) { + $this->clientError(_('Not logged in.')); + return; + } + + $user = common_current_user(); + + // ...because they're logged in + + assert(!empty($user)); + + // It must be a "real" login, not saved cookie login + + if (!common_is_real_login()) { + // Cookie theft is too easy; we require automatic + // logins to re-authenticate before admining the site + common_set_returnto($this->selfUrl()); + if (Event::handle('RedirectToLogin', array($this, $user))) { + common_redirect(common_local_url('login'), 303); + } + } + + // User must have the right to review flags + + if (!$user->hasRight(UserFlagPlugin::REVIEWFLAGS)) { + $this->clientError(_('You cannot review profile flags.')); + return false; + } + + $this->page = $this->trimmed('page'); + + if (empty($this->page)) { + $this->page = 1; + } + + $this->profiles = $this->getProfiles(); + return true; } @@ -65,7 +107,6 @@ class AdminprofileflagAction extends Action * * @return void */ - function handle($args) { parent::handle($args); @@ -73,8 +114,15 @@ class AdminprofileflagAction extends Action $this->showPage(); } - function title() { - return _('Flagged profiles'); + /** + * Title of this page + * + * @return string Title of the page + */ + function title() + { + // TRANS: Title for page with a list of profiles that were flagged for review. + return _m('Flagged profiles'); } /** @@ -82,16 +130,21 @@ class AdminprofileflagAction extends Action * * @return void */ - function showContent() { - $profile = $this->getProfiles(); + $pl = new FlaggedProfileList($this->profiles, $this); - $pl = new FlaggedProfileList($profile, $this); + $cnt = $pl->show(); - $pl->show(); + $this->pagination($this->page > 1, $cnt > PROFILES_PER_PAGE, + $this->page, 'adminprofileflag'); } + /** + * Retrieve this action's profiles + * + * @return Profile $profile Profile query results + */ function getProfiles() { $ufp = new User_flag_profile(); @@ -103,7 +156,12 @@ class AdminprofileflagAction extends Action $ufp->whereAdd('cleared is NULL'); $ufp->groupBy('profile_id'); - $ufp->orderBy('flag_count DESC'); + $ufp->orderBy('flag_count DESC, profile_id DESC'); + + $offset = ($this->page-1) * PROFILES_PER_PAGE; + $limit = PROFILES_PER_PAGE + 1; + + $ufp->limit($offset, $limit); $profiles = array(); @@ -122,19 +180,53 @@ class AdminprofileflagAction extends Action } } -class FlaggedProfileList extends ProfileList { - +/** + * Specialization of ProfileList to show flagging information + * + * Most of the hard part is done in FlaggedProfileListItem. + * + * @category Widget + * @package StatusNet + * @author Evan Prodromou + * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 + * @link http://status.net/ + */ +class FlaggedProfileList extends ProfileList +{ + /** + * Factory method for creating new list items + * + * @param Profile $profile Profile to create an item for + * + * @return ProfileListItem newly-created item + */ function newListItem($profile) { return new FlaggedProfileListItem($this->profile, $this->action); } } +/** + * Specialization of ProfileListItem to show flagging information + * + * @category Widget + * @package StatusNet + * @author Evan Prodromou + * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 + * @link http://status.net/ + */ class FlaggedProfileListItem extends ProfileListItem { - var $user = null; + const MAX_FLAGGERS = 5; + + var $user = null; var $r2args = null; + /** + * Overload parent's action list with our own moderation-oriented buttons + * + * @return void + */ function showActions() { $this->user = common_current_user(); @@ -145,15 +237,26 @@ class FlaggedProfileListItem extends ProfileListItem $this->startActions(); if (Event::handle('StartProfileListItemActionElements', array($this))) { + $this->out->elementStart('li', 'entity_moderation'); + // TRANS: Header for moderation menu with action buttons for flagged profiles (like 'sandbox', 'silence', ...). + $this->out->element('p', null, _m('Moderate')); + $this->out->elementStart('ul'); $this->showSandboxButton(); $this->showSilenceButton(); $this->showDeleteButton(); $this->showClearButton(); + $this->out->elementEnd('ul'); + $this->out->elementEnd('li'); Event::handle('EndProfileListItemActionElements', array($this)); } $this->endActions(); } + /** + * Show a button to sandbox the profile + * + * @return void + */ function showSandboxButton() { if ($this->user->hasRight(Right::SANDBOXUSER)) { @@ -169,6 +272,11 @@ class FlaggedProfileListItem extends ProfileListItem } } + /** + * Show a button to silence the profile + * + * @return void + */ function showSilenceButton() { if ($this->user->hasRight(Right::SILENCEUSER)) { @@ -184,6 +292,11 @@ class FlaggedProfileListItem extends ProfileListItem } } + /** + * Show a button to delete user and profile + * + * @return void + */ function showDeleteButton() { @@ -195,7 +308,93 @@ class FlaggedProfileListItem extends ProfileListItem } } + /** + * Show a button to clear flags + * + * @return void + */ function showClearButton() { + if ($this->user->hasRight(UserFlagPlugin::CLEARFLAGS)) { + $this->out->elementStart('li', 'entity_clear'); + $cf = new ClearFlagForm($this->out, $this->profile, $this->r2args); + $cf->show(); + $this->out->elementEnd('li'); + } + } + + /** + * Overload parent function to add flaggers list + * + * @return void + */ + function endProfile() + { + $this->showFlaggersList(); + parent::endProfile(); + } + + /** + * Show a list of people who've flagged this profile + * + * @return void + */ + function showFlaggersList() + { + $flaggers = array(); + + $ufp = new User_flag_profile(); + + $ufp->selectAdd(); + $ufp->selectAdd('user_id'); + $ufp->profile_id = $this->profile->id; + $ufp->orderBy('created'); + + if ($ufp->find()) { // XXX: this should always happen + while ($ufp->fetch()) { + $user = User::staticGet('id', $ufp->user_id); + if (!empty($user)) { // XXX: this would also be unusual + $flaggers[] = clone($user); + } + } + } + + $cnt = count($flaggers); + $others = 0; + + if ($cnt > self::MAX_FLAGGERS) { + $flaggers = array_slice($flaggers, 0, self::MAX_FLAGGERS); + $others = $cnt - self::MAX_FLAGGERS; + } + + $lnks = array(); + + foreach ($flaggers as $flagger) { + + $url = common_local_url('showstream', + array('nickname' => $flagger->nickname)); + + $lnks[] = XMLStringer::estring('a', array('href' => $url, + 'class' => 'flagger'), + $flagger->nickname); + } + + if ($cnt > 0) { + if ($others > 0) { + $flagging_users = implode(', ', $lnks); + // TRANS: Message displayed on a profile if it has been flagged. + // TRANS: %1$s is a comma separated list of at most 5 user nicknames that flagged. + // TRANS: %2$d is a positive integer of additional flagging users. Also used for the plural. + $text .= sprintf(_m('Flagged by %1$s and %2$d other', 'Flagged by %1$s and %2$d others', $others), $flagging_users, $others); + } else { + // TRANS: Message displayed on a profile if it has been flagged. + // TRANS: %s is a comma separated list of at most 5 user nicknames that flagged. + $text .= sprintf(_m('Flagged by %s'), $flagging_users); + } + + $this->out->elementStart('p', array('class' => 'flaggers')); + $this->out->raw($text); + $this->out->elementEnd('p'); + } } }