summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniel Friesel <derf@finalrewind.org>2019-03-19 18:20:05 +0100
committerDaniel Friesel <derf@finalrewind.org>2019-03-19 18:20:05 +0100
commit01df965d66fa7223e98036908ed4f60dda5942f8 (patch)
tree9a7efc5a2d1025305c8a3ccd54333ff8e39e87fb
parente24f89530376641f56d3b037c2a7dcd485b1ccd8 (diff)
support logging of cancelled journeys
-rwxr-xr-xindex.pl84
-rw-r--r--public/static/css/local.css4
-rw-r--r--public/static/js/travelynx-actions.js20
-rw-r--r--public/static/js/travelynx-actions.min.js2
-rw-r--r--templates/departures.html.ep14
-rw-r--r--templates/landingpage.html.ep27
-rw-r--r--templates/layouts/default.html.ep2
7 files changed, 130 insertions, 23 deletions
diff --git a/index.pl b/index.pl
index 2df0048..0f5622b 100755
--- a/index.pl
+++ b/index.pl
@@ -33,11 +33,13 @@ my $cache_iris_rt = Cache::File->new(
my $dbname = $ENV{TRAVELYNX_DB_FILE} // 'travelynx.sqlite';
my %action_type = (
- checkin => 1,
- checkout => 2,
- undo => 3,
+ checkin => 1,
+ checkout => 2,
+ undo => 3,
+ cancelled_from => 4,
+ cancelled_to => 5,
);
-my @action_types = (qw(checkin checkout undo));
+my @action_types = (qw(checkin checkout undo cancelled_from cancelled_to));
my %token_type = (
status => 1,
history => 2,
@@ -476,7 +478,9 @@ sub get_station {
}
helper 'checkin' => sub {
- my ( $self, $station, $train_id ) = @_;
+ my ( $self, $station, $train_id, $action_id ) = @_;
+
+ $action_id //= $action_type{checkin};
my $status = get_departures($station);
if ( $status->{errstr} ) {
@@ -504,10 +508,17 @@ helper 'checkin' => sub {
# XXX same workaround: We can't checkin immediately after checkout.
sleep(1);
}
+ elsif ( $user->{cancelled} ) {
+
+ # Same
+ sleep(1);
+ $self->cancelled_to($station);
+ sleep(1);
+ }
my $success = $self->app->action_query->execute(
$self->current_user->{id},
- $action_type{checkin},
+ $action_id,
$self->get_station_id(
ds100 => $status->{station_ds100},
name => $status->{station_name}
@@ -563,13 +574,15 @@ helper 'undo' => sub {
};
helper 'checkout' => sub {
- my ( $self, $station, $force ) = @_;
+ my ( $self, $station, $force, $action_id ) = @_;
+
+ $action_id //= $action_type{checkout};
my $status = get_departures( $station, 180 );
my $user = $self->get_user_status;
my $train_id = $user->{train_id};
- if ( not $user->{checked_in} ) {
+ if ( not $user->{checked_in} and not $user->{cancelled} ) {
return 'You are not checked into any train';
}
if ( $status->{errstr} and not $force ) {
@@ -582,7 +595,7 @@ helper 'checkout' => sub {
if ($force) {
my $success = $self->app->action_query->execute(
$self->current_user->{id},
- $action_type{checkout},
+ $action_id,
$self->get_station_id(
ds100 => $status->{station_ds100},
name => $status->{station_name}
@@ -892,6 +905,7 @@ helper 'get_user_status' => sub {
}
return {
checked_in => ( $cols[0] == $action_type{checkin} ),
+ cancelled => ( $cols[0] == $action_type{cancelled_from} ),
timestamp => $action_ts,
timestamp_delta => $now->epoch - $action_ts->epoch,
sched_ts => $sched_ts,
@@ -1070,8 +1084,11 @@ get '/api/v0/:action/:token' => sub {
$self->render(
json => {
deprecated => \0,
- checked_in => $status->{checked_in} ? \1 : \0,
- station => {
+ checked_in => (
+ $status->{checked_in}
+ or $status->{cancelled}
+ ) ? \1 : \0,
+ station => {
ds100 => $status->{station_ds100},
name => $status->{station_name},
uic => $station_eva,
@@ -1302,7 +1319,7 @@ post '/action' => sub {
if ( $params->{action} eq 'checkin' ) {
my ( $train, $error )
- = $self->checkin( $params->{station}, $params->{train}, );
+ = $self->checkin( $params->{station}, $params->{train} );
if ($error) {
$self->render(
@@ -1321,7 +1338,7 @@ post '/action' => sub {
}
}
elsif ( $params->{action} eq 'checkout' ) {
- my $error = $self->checkout( $params->{station}, $params->{force}, );
+ my $error = $self->checkout( $params->{station}, $params->{force} );
if ($error) {
$self->render(
@@ -1357,6 +1374,47 @@ post '/action' => sub {
);
}
}
+ elsif ( $params->{action} eq 'cancelled_from' ) {
+ my ( undef, $error )
+ = $self->checkin( $params->{station}, $params->{train},
+ $action_type{cancelled_from} );
+
+ if ($error) {
+ $self->render(
+ json => {
+ success => 0,
+ error => $error,
+ },
+ );
+ }
+ else {
+ $self->render(
+ json => {
+ success => 1,
+ },
+ );
+ }
+ }
+ elsif ( $params->{action} eq 'cancelled_to' ) {
+ my $error = $self->checkout( $params->{station}, 1,
+ $action_type{cancelled_to} );
+
+ if ($error) {
+ $self->render(
+ json => {
+ success => 0,
+ error => $error,
+ },
+ );
+ }
+ else {
+ $self->render(
+ json => {
+ success => 1,
+ },
+ );
+ }
+ }
else {
$self->render(
json => {
diff --git a/public/static/css/local.css b/public/static/css/local.css
index 7502b64..68f9ab1 100644
--- a/public/static/css/local.css
+++ b/public/static/css/local.css
@@ -1,6 +1,8 @@
.action-checkin,
.action-checkout,
-.action-undo {
+.action-undo,
+.action-cancelled-from,
+.action-cancelled-to {
cursor: pointer;
}
diff --git a/public/static/js/travelynx-actions.js b/public/static/js/travelynx-actions.js
index 0a3d092..d47df77 100644
--- a/public/static/js/travelynx-actions.js
+++ b/public/static/js/travelynx-actions.js
@@ -44,6 +44,24 @@ $(document).ready(function() {
var req = {
action: 'undo',
};
- tvly_run(link, req, window.location.href);
+ tvly_run(link, req, '/');
+ });
+ $('.action-cancelled-from').click(function() {
+ var link = $(this);
+ var req = {
+ action: 'cancelled_from',
+ station: link.data('station'),
+ train: link.data('train'),
+ };
+ tvly_run(link, req, '/');
+ });
+ $('.action-cancelled-to').click(function() {
+ var link = $(this);
+ var req = {
+ action: 'cancelled_to',
+ station: link.data('station'),
+ force: true,
+ };
+ tvly_run(link, req, '/');
});
});
diff --git a/public/static/js/travelynx-actions.min.js b/public/static/js/travelynx-actions.min.js
index 9c37d8d..4fe0e76 100644
--- a/public/static/js/travelynx-actions.min.js
+++ b/public/static/js/travelynx-actions.min.js
@@ -1 +1 @@
-function tvly_run(n,t,i,a){var c='<i class="material-icons">error</i>',o=$('<div class="progress"><div class="indeterminate"></div></div>');n.hide(),n.after(o),$.post("/action",t,function(t){t.success?$(location).attr("href",i):(M.toast({html:c+" "+t.error}),o.remove(),a&&a(),n.append(" "+c),n.show())})}$(document).ready(function(){$(".action-checkin").click(function(){var t=$(this);tvly_run(t,{action:"checkin",station:t.data("station"),train:t.data("train")},"/")}),$(".action-checkout").click(function(){var t=$(this),n={action:"checkout",station:t.data("station"),force:t.data("force")};tvly_run(t,n,"/s/"+n.station,function(){t.append(" – Ohne Echtzeitdaten auschecken?"),t.data("force",!0)})}),$(".action-undo").click(function(){tvly_run($(this),{action:"undo"},window.location.href)})});
+function tvly_run(n,t,a,c){var i='<i class="material-icons">error</i>',o=$('<div class="progress"><div class="indeterminate"></div></div>');n.hide(),n.after(o),$.post("/action",t,function(t){t.success?$(location).attr("href",a):(M.toast({html:i+" "+t.error}),o.remove(),c&&c(),n.append(" "+i),n.show())})}$(document).ready(function(){$(".action-checkin").click(function(){var t=$(this);tvly_run(t,{action:"checkin",station:t.data("station"),train:t.data("train")},"/")}),$(".action-checkout").click(function(){var t=$(this),n={action:"checkout",station:t.data("station"),force:t.data("force")};tvly_run(t,n,"/s/"+n.station,function(){t.append(" – Ohne Echtzeitdaten auschecken?"),t.data("force",!0)})}),$(".action-undo").click(function(){tvly_run($(this),{action:"undo"},"/")}),$(".action-cancelled-from").click(function(){var t=$(this);tvly_run(t,{action:"cancelled_from",station:t.data("station"),train:t.data("train")},"/")}),$(".action-cancelled-to").click(function(){var t=$(this);tvly_run(t,{action:"cancelled_to",station:t.data("station"),force:!0},"/")})});
diff --git a/templates/departures.html.ep b/templates/departures.html.ep
index ee87496..47c4872 100644
--- a/templates/departures.html.ep
+++ b/templates/departures.html.ep
@@ -52,22 +52,24 @@
</thead>
<tbody>
% for my $result (@{$results}) {
- % my $class = "";
+ % my $td_class = '';
+ % my $link_class = 'action-checkin';
% if ($result->departure_is_cancelled) {
- % $class = "cancelled";
+ % $td_class = "cancelled";
+ % $link_class = 'action-cancelled-from';
% }
<tr>
<td>
- <a class="action-checkin" data-station="<%= $ds100 %>" data-train="<%= $result->train_id %>">
+ <a class="<%= $link_class %>" data-station="<%= $ds100 %>" data-train="<%= $result->train_id %>">
<%= $result->line %>
</a>
</td>
- <td class="<%= $class %>">
- <a class="action-checkin" data-station="<%= $ds100 %>" data-train="<%= $result->train_id %>">
+ <td class="<%= $td_class %>">
+ <a class="<%= $link_class %>" data-station="<%= $ds100 %>" data-train="<%= $result->train_id %>">
<%= $result->destination %>
</a>
</td>
- <td class="<%= $class %>"><%= $result->departure->strftime('%H:%M') %>
+ <td class="<%= $td_class %>"><%= $result->departure->strftime('%H:%M') %>
% if ($result->departure_delay) {
(+<%= $result->departure_delay %>)
% }
diff --git a/templates/landingpage.html.ep b/templates/landingpage.html.ep
index dcc0083..83ad2a1 100644
--- a/templates/landingpage.html.ep
+++ b/templates/landingpage.html.ep
@@ -37,6 +37,33 @@
</div>
</div>
% }
+ % elsif ($status->{cancelled}) {
+ <div class="card yellow lighten-4">
+ <div class="card-content">
+ <span class="card-title">Zugausfall dokumentieren</span>
+ <p>Prinzipiell wärest du nun eingecheckt in
+ <%= $status->{train_type} %> <%= $status->{train_no} %>
+ ab <%= $status->{station_name} %>, doch dieser Zug fällt aus.
+ % if ($status->{timestamp_delta} < 3600) {
+ <a class="action-undo"><i class="material-icons">undo</i> Checkinversuch rückgängig</a>
+ % }
+ </p>
+ <p>Falls du den Zugausfall z.B. für ein Fahrgastrechteformular
+ dokumentieren möchtest, wähle bitte jetzt deine geplante
+ Zielstation aus. Achtung: Momentan wird dabei keine
+ Soll-Ankunftszeit gespeichert, das zu beheben steht auf
+ der Todoliste.</p>
+ <table>
+ <tbody>
+ % my $is_after = 0;
+ % for my $station (@{$status->{route_after}}) {
+ <tr><td><a class="action-cancelled-to" data-station="<%= $station %>"><%= $station %></a></td></tr>
+ % }
+ </tbody>
+ </table>
+ </div>
+ </div>
+ % }
% else {
<div class="card grey darken-4">
<div class="card-content white-text">
diff --git a/templates/layouts/default.html.ep b/templates/layouts/default.html.ep
index 8f5bdc2..2589788 100644
--- a/templates/layouts/default.html.ep
+++ b/templates/layouts/default.html.ep
@@ -5,7 +5,7 @@
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="theme-color" content="#673ab7">
- % my $av = 'v3'; # asset version
+ % my $av = 'v4'; # asset version
%= stylesheet "/static/${av}/css/materialize.min.css"
%= stylesheet "/static/${av}/css/material-icons.css"
%= stylesheet "/static/${av}/css/local.css"