diff options
author | Matthew Somerville <matthew-github@dracos.co.uk> | 2019-01-15 12:45:31 +0000 |
---|---|---|
committer | Matthew Somerville <matthew-github@dracos.co.uk> | 2019-01-16 11:08:48 +0000 |
commit | be0944d54e06e77a34f9149ccb63817d5ac7d184 (patch) | |
tree | c354e869af1d1d15f423a16d34317b98b46d1d11 | |
parent | 4dac760f5d5291437667b28b39af41d29545bda3 (diff) |
Allow state editing via moderation.
If a state is passed in (on a cobrand), update problem state and add a
comment to record this (as state changes are updates not moderations).
-rw-r--r-- | CHANGELOG.md | 8 | ||||
-rw-r--r-- | perllib/FixMyStreet/App/Controller/Moderate.pm | 37 | ||||
-rw-r--r-- | t/app/controller/moderate.t | 25 |
3 files changed, 66 insertions, 4 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md index 8bf5b21ea..abca4a7c9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,10 +1,12 @@ ## Releases * Unreleased + - Admin improvements: + - Allow moderation to potentially change state. #2381 - Bugfixes - - Check cached reports do still have photos before being shown. - - Delete cache photos upon photo moderation. - - Remove any use of `my $x if $foo`. + - Check cached reports do still have photos before being shown. #2374 + - Delete cache photos upon photo moderation. #2374 + - Remove any use of `my $x if $foo`. #2377 * v2.5 (21st December 2018) - Front end improvements: diff --git a/perllib/FixMyStreet/App/Controller/Moderate.pm b/perllib/FixMyStreet/App/Controller/Moderate.pm index 8c56a6300..d7f7671e8 100644 --- a/perllib/FixMyStreet/App/Controller/Moderate.pm +++ b/perllib/FixMyStreet/App/Controller/Moderate.pm @@ -81,6 +81,7 @@ sub moderate_report : Chained('report') : PathPart('') : Args(0) { $c->forward('report_moderate_hide'); my @types = grep $_, + $c->forward('moderate_state'), ($c->user->can_moderate_title($problem, 1) ? $c->forward('moderate_text', [ 'title' ]) : ()), @@ -128,6 +129,9 @@ sub moderate_log_entry : Private { my $types_csv = join ', ' => @types; + my $log_reason = "($types_csv)"; + $log_reason = "$reason $log_reason" if $reason; + # We attach the log to the moderation entry if present, or the object if not (hiding) $c->model('DB::AdminLog')->create({ action => 'moderation', @@ -135,7 +139,7 @@ sub moderate_log_entry : Private { admin_user => moderating_user_name($user), object_id => $c->stash->{history}->id || $object->id, object_type => $c->stash->{history}->id ? 'moderation' : $object_type, - reason => (sprintf '%s (%s)', $reason, $types_csv), + reason => $log_reason, }); } @@ -144,6 +148,9 @@ sub report_moderate_audit : Private { my $problem = $c->stash->{problem} or die; + return unless @types; # If nothing moderated, nothing to do + return if @types == 1 && $types[0] eq 'state'; # If only state changed, no log entry needed + $c->forward('moderate_log_entry', [ 'problem', @types ]); if ($problem->user->email_verified && $c->cobrand->send_moderation_notifications) { @@ -299,6 +306,34 @@ sub moderate_category : Private { } } +# Note that if a cobrand allows state moderation, then the moderation reason +# given will be added as an update and thus be publicly available (unlike with +# normal moderation). +sub moderate_state : Private { + my ($self, $c) = @_; + + my $new_state = $c->get_param('state'); + return unless $new_state; + + my $problem = $c->stash->{problem}; + if ($problem->state ne $new_state) { + $problem->state($new_state); + $problem->update; + $problem->add_to_comments( { + text => $c->stash->{moderation_reason}, + created => \'current_timestamp', + confirmed => \'current_timestamp', + user_id => $c->user->id, + name => $c->user->from_body ? $c->user->from_body->name : $c->user->name, + state => 'confirmed', + mark_fixed => 0, + anonymous => $c->user->from_body ? 0 : 1, + problem_state => $new_state, + } ); + return 'state'; + } +} + sub update : Chained('report') : PathPart('update') : CaptureArgs(1) { my ($self, $c, $id) = @_; my $comment = $c->stash->{problem}->comments->find($id); diff --git a/t/app/controller/moderate.t b/t/app/controller/moderate.t index 4eb72ed56..a3474449f 100644 --- a/t/app/controller/moderate.t +++ b/t/app/controller/moderate.t @@ -273,6 +273,30 @@ subtest 'Problem moderation' => sub { is $report->category, 'Lost toys'; }; + subtest 'Moderate state' => sub { + my $mods_count = $report->moderation_original_datas->count; + my ($csrf) = $mech->content =~ /meta content="([^"]*)" name="csrf-token"/; + $mech->post_ok('http://www.example.org/moderate/report/' . $report->id, { + %problem_prepopulated, + state => 'confirmed', + token => $csrf, + }); + $report->discard_changes; + is $report->state, 'confirmed', 'state has not changed'; + is $report->comments->count, 0, 'same state, no update'; + is $report->moderation_original_datas->count, $mods_count, 'No moderation entry either'; + $mech->post_ok('http://www.example.org/moderate/report/' . $report->id, { + %problem_prepopulated, + state => 'in progress', + token => $csrf, + }); + $report->discard_changes; + is $report->state, 'in progress', 'state has changed'; + is $report->comments->count, 1, 'a new update added'; + $report->update({ state => 'confirmed' }); + is $report->moderation_original_datas->count, $mods_count, 'No moderation entry, only state changed'; + }; + subtest 'Moderate location' => sub { FixMyStreet::override_config { MAPIT_URL => 'http://mapit.uk/', @@ -327,6 +351,7 @@ sub create_update { text => 'update good good bad good', state => 'confirmed', mark_fixed => 0, + confirmed => $dt, }); } my %update_prepopulated = ( |