Skip to content

Commit

Permalink
[ATAK] Enforce character limit on issue text.
Browse files Browse the repository at this point in the history
Construct the description open311-adapter side using title, URL and detail values from FMS.
Truncate the detail to ensure the whole issue text is less than some config defined character limit.
  • Loading branch information
neprune committed Sep 5, 2023
1 parent 47b4ed4 commit ba4efaf
Show file tree
Hide file tree
Showing 4 changed files with 89 additions and 6 deletions.
1 change: 1 addition & 0 deletions conf/council-brent_atak.yml-example
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ api_url: https://testatak.krinkels.com/ords/hws/atak/v1
# api_url: https://atak.krinkels.com/ords/hws/atak/v1
project_code: C23005
project_name: LB BRENT GM SERVICES
max_issue_text_characters: 900

services:
LITTER_BIN_NEEDS_EMPTYING:
Expand Down
36 changes: 31 additions & 5 deletions perllib/Open311/Endpoint/Integration/ATAK.pm
Original file line number Diff line number Diff line change
Expand Up @@ -67,13 +67,13 @@ sub post_service_request {
} $self->_get_attachments($args->{media_url});
}

my $issue_template = "Category: %s\nLocation: %s\n\n%s\n";

my $issue_text = sprintf(
$issue_template,
my $issue_text = $self->_format_issue_text(
$self->endpoint_config->{max_issue_text_characters},
$service->service_name,
$args->{attributes}->{location_name} || '',
$args->{description},
$args->{attributes}->{report_url},
$args->{attributes}->{title},
$args->{attributes}->{detail},
);

my $issue = {
Expand Down Expand Up @@ -108,6 +108,32 @@ sub post_service_request {
)
}

sub _format_issue_text {
my ($self, $char_limit, $category, $location_name, $url, $title, $detail) = @_;

# Populate everything except the detail field which we may need to truncate.
my $issue_text = sprintf(
"Category: %s\nLocation: %s\n\nlocation of problem: %s\n\ndetail: %%s\n\nurl: %s\n\nSubmitted via FixMyStreet\n",
$category, $location_name, $title, $url
);

# +2 for the not yet used format directive for detail (%s).
my $max_detail_chars = $char_limit - length($issue_text) + 2;

# We need at least 3 characters of leeway so we can use an ellipsis to indicate
# the detail as truncated.
if ($max_detail_chars < 3 && length($detail) >= $max_detail_chars) {
die "Issue text is too large to send even before including the report detail: " . $issue_text;
}

if (length($detail) > $max_detail_chars) {
$detail = substr($detail, 0, $max_detail_chars - 3) . "...";
}

return sprintf($issue_text, $detail);

}

sub _get_attachments {
my ($self, $urls) = @_;

Expand Down
24 changes: 24 additions & 0 deletions perllib/Open311/Endpoint/Service/UKCouncil/ATAK.pm
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,30 @@ sub _build_attributes {
automated => 'hidden_field',
allow_any_attributes => 1,
),

Open311::Endpoint::Service::Attribute->new(
code => "report_url",
description => "Report URL",
datatype => "string",
required => 1,
automated => 'server_set',
),

Open311::Endpoint::Service::Attribute->new(
code => "title",
description => "Title",
datatype => "string",
required => 1,
automated => 'server_set',
),

Open311::Endpoint::Service::Attribute->new(
code => "detail",
description => "Detail",
datatype => "text",
required => 1,
automated => 'server_set',
),
);

return \@attributes;
Expand Down
34 changes: 33 additions & 1 deletion t/open311/endpoint/brent.t
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ use Test::More;
use Test::MockModule;
use Test::LongString;
use Test::MockTime ':all';
use Test::Exception;

# Set up

Expand Down Expand Up @@ -75,6 +76,7 @@ sub atak_config {
group => "Parks and open spaces",
},
},
max_issue_text_characters => 900,
issue_status_tracking_file => $atak_status_tracking_file,
update_storage_file => $atak_update_storage_file,
issue_status_tracking_max_age_days => 365,
Expand Down Expand Up @@ -590,7 +592,9 @@ subtest "POST Parks littering ATAK service request OK" => sub {
is $headers{Authorization}, 'AUTH-123';

my $data = decode_json($headers{Content})->{tasks}->[0];
is $data->{issue}, "Category: Parks littering\nLocation: Location name\n\nLots of litter in the park\n";
is $data->{issue}, "Category: Parks littering\nLocation: Location name\n\n" .
"location of problem: title\n\ndetail: detail\n\nurl: url\n\n" .
"Submitted via FixMyStreet\n";
is $data->{client_ref}, '42';
is $data->{project_name}, 'LB BRENT';
is $data->{project_code}, 'C123';
Expand Down Expand Up @@ -627,6 +631,9 @@ subtest "POST Parks littering ATAK service request OK" => sub {
'attribute[easting]' => EASTING,
'attribute[northing]' => NORTHING,
'attribute[fixmystreet_id]' => 42,
'attribute[report_url]' => 'url',
'attribute[detail]' => 'detail',
'attribute[title]' => 'title',
);
ok $res->is_success, 'valid request';

Expand Down Expand Up @@ -935,4 +942,29 @@ subtest "GET ATAK service request updates OK" => sub {
);
};

subtest "ATAK issue text formatting" => sub {

dies_ok { $atak_endpoint->_format_issue_text(
120, 'category', 'location name', 'url', 'title', 'detail'
) }, "formatting issue text fails when inputs are too big";

my $issue_text = $atak_endpoint->_format_issue_text(
121, 'category', 'location name', 'url', 'title', 'detail'
);
is $issue_text, "Category: category\nLocation: location name\n\nlocation of problem: title\n\n" .
"detail: ...\n\nurl: url\n\nSubmitted via FixMyStreet\n";

my $issue_text = $atak_endpoint->_format_issue_text(
122, 'category', 'location name', 'url', 'title', 'detail'
);
is $issue_text, "Category: category\nLocation: location name\n\nlocation of problem: title\n\n" .
"detail: d...\n\nurl: url\n\nSubmitted via FixMyStreet\n";

my $issue_text = $atak_endpoint->_format_issue_text(
127, 'category', 'location name', 'url', 'title', 'detail'
);
is $issue_text, "Category: category\nLocation: location name\n\nlocation of problem: title\n\n" .
"detail: detail\n\nurl: url\n\nSubmitted via FixMyStreet\n";
};

done_testing;

0 comments on commit ba4efaf

Please sign in to comment.