Refactor to use PostGIS database instead of gtfs tools
[busui.git] / include / db / trip-dao.inc.php
blob:a/include/db/trip-dao.inc.php -> blob:b/include/db/trip-dao.inc.php
<?php <?php
function getTrip($tripID) { function getTrip($tripID)
/* def handle_json_GET_triprows(self, params):  
"""Return a list of rows from the feed file that are related to this {
trip.""" global $conn;
schedule = self.server.schedule $query = "Select * from trips
try: join routes on trips.route_id = routes.route_id
trip = schedule.GetTrip(params.get('trip', None)) where trip_id = :tripID
except KeyError: LIMIT 1";
# if a non-existent trip is searched for, the return nothing debug($query, "database");
return $query = $conn -> prepare($query);
route = schedule.GetRoute(trip.route_id) $query -> bindParam(":tripID", $tripID);
trip_row = dict(trip.iteritems()) $query -> execute();
route_row = dict(route.iteritems()) if (!$query) {
return [['trips.txt', trip_row], ['routes.txt', route_row]] databaseError($conn -> errorInfo());
*/ return Array();
} }
function getTripShape() { return $query -> fetch(PDO :: FETCH_ASSOC);
/* def handle_json_GET_tripstoptimes(self, params): }
schedule = self.server.schedule function getTripShape($tripID)
try:  
trip = schedule.GetTrip(params.get('trip')) {
except KeyError: global $conn;
# if a non-existent trip is searched for, the return nothing $query = "SELECT ST_AsKML(ST_MakeLine(geometry(a.position))) as the_route
return FROM (SELECT position,
time_stops = trip.GetTimeInterpolatedStops() stop_sequence, trips.trip_id
stops = [] FROM stop_times
times = [] join trips on trips.trip_id = stop_times.trip_id
for arr,ts,is_timingpoint in time_stops: join stops on stops.stop_id = stop_times.stop_id
stops.append(StopToTuple(ts.stop)) WHERE trips.trip_id = :tripID ORDER BY stop_sequence) as a group by a.trip_id";
times.append(arr) debug($query, "database");
return [stops, times] $query = $conn -> prepare($query);
  $query -> bindParam(":tripID", $tripID);
def handle_json_GET_tripshape(self, params): $query -> execute();
schedule = self.server.schedule if (!$query) {
try: databaseError($conn -> errorInfo());
trip = schedule.GetTrip(params.get('trip')) return Array();
except KeyError: }
# if a non-existent trip is searched for, the return nothing return $query -> fetchColumn(0);
return }
points = [] function getTimeInterpolatedTrip($tripID, $range = "")
if trip.shape_id:  
shape = schedule.GetShape(trip.shape_id) {
for (lat, lon, dist) in shape.points: global $conn;
points.append((lat, lon)) $query = "SELECT stop_times.trip_id,arrival_time,stop_times.stop_id,stop_lat,stop_lon,stop_name,stop_code,
else: stop_sequence,service_id,trips.route_id,route_short_name,route_long_name
time_stops = trip.GetTimeStops() FROM stop_times
for arr,dep,stop in time_stops: join trips on trips.trip_id = stop_times.trip_id
points.append((stop.stop_lat, stop.stop_lon)) join routes on trips.route_id = routes.route_id
return points*/ join stops on stops.stop_id = stop_times.stop_id
} WHERE trips.trip_id = :tripID $range ORDER BY stop_sequence";
function tripStopTimes($tripID, $after_time, $limit) { debug($query, "database");
/* rv = [] $query = $conn -> prepare($query);
  $query -> bindParam(":tripID", $tripID);
stoptimes = self.GetStopTimes() $query -> execute();
# If there are no stoptimes [] is the correct return value but if the start if (!$query) {
# or end are missing times there is no correct return value. databaseError($conn -> errorInfo());
if not stoptimes: return Array();
return [] }
if (stoptimes[0].GetTimeSecs() is None or $stopTimes = $query -> fetchAll();
stoptimes[-1].GetTimeSecs() is None): $cur_timepoint = Array();
raise ValueError("%s must have time at first and last stop" % (self)) $next_timepoint = Array();
  $distance_between_timepoints = 0.0;
cur_timepoint = None $distance_traveled_between_timepoints = 0.0;
next_timepoint = None $rv = Array();
distance_between_timepoints = 0 foreach ($stopTimes as $i => $stopTime) {
distance_traveled_between_timepoints = 0 if ($stopTime['arrival_time'] != "") {
  // is timepoint
for i, st in enumerate(stoptimes): $cur_timepoint = $stopTime;
if st.GetTimeSecs() != None: $distance_between_timepoints = 0.0;
cur_timepoint = st $distance_traveled_between_timepoints = 0.0;
distance_between_timepoints = 0 if ($i + 1 < sizeof($stopTimes)) {
distance_traveled_between_timepoints = 0 $k = $i + 1;
if i + 1 < len(stoptimes): $distance_between_timepoints += distance($stopTimes[$k - 1]["stop_lat"], $stopTimes[$k - 1]["stop_lon"], $stopTimes[$k]["stop_lat"], $stopTimes[$k]["stop_lon"]);
k = i + 1 while ($stopTimes[$k]["arrival_time"] == "" && $k + 1 < sizeof($stopTimes)) {
distance_between_timepoints += util.ApproximateDistanceBetweenStops(stoptimes[k-1].stop, stoptimes[k].stop) $k += 1;
while stoptimes[k].GetTimeSecs() == None: // echo "k".$k;
k += 1 $distance_between_timepoints += distance($stopTimes[$k - 1]["stop_lat"], $stopTimes[$k - 1]["stop_lon"], $stopTimes[$k]["stop_lat"], $stopTimes[$k]["stop_lon"]);
distance_between_timepoints += util.ApproximateDistanceBetweenStops(stoptimes[k-1].stop, stoptimes[k].stop) }
next_timepoint = stoptimes[k] $next_timepoint = $stopTimes[$k];
rv.append( (st.GetTimeSecs(), st, True) )  
else: }
distance_traveled_between_timepoints += util.ApproximateDistanceBetweenStops(stoptimes[i-1].stop, st.stop) $rv[] = $stopTime;
distance_percent = distance_traveled_between_timepoints / distance_between_timepoints }
total_time = next_timepoint.GetTimeSecs() - cur_timepoint.GetTimeSecs() else {
time_estimate = distance_percent * total_time + cur_timepoint.GetTimeSecs() // is untimed point
rv.append( (int(round(time_estimate)), st, False) ) // echo "i".$i;
  $distance_traveled_between_timepoints += distance($stopTimes[$i - 1]["stop_lat"], $stopTimes[$i - 1]["stop_lon"], $stopTimes[$i]["stop_lat"], $stopTimes[$i]["stop_lon"]);
return rv*/ // echo "$distance_traveled_between_timepoints / $distance_between_timepoints<br>";
} $distance_percent = $distance_traveled_between_timepoints / $distance_between_timepoints;
  if ($next_timepoint["arrival_time"] != "") {
function tripStartTime($tripID) { $total_time = strtotime($next_timepoint["arrival_time"]) - strtotime($cur_timepoint["arrival_time"]);
$query = 'SELECT arrival_secs,departure_secs FROM stop_times WHERE trip_id=? ORDER BY stop_sequence LIMIT 1'; // echo strtotime($next_timepoint["arrival_time"])." - ".strtotime($cur_timepoint["arrival_time"])."<br>";
  $time_estimate = ($distance_percent * $total_time) + strtotime($cur_timepoint["arrival_time"]);
} $stopTime["arrival_time"] = date("H:i:s", $time_estimate);
  }
function viaPoints($tripid, $stopid, $timingPointsOnly = false) else {
{ $stopTime["arrival_time"] = $cur_timepoint["arrival_time"];
global $APIurl; }
$url = $APIurl . "/json/tripstoptimes?trip=" . $tripid; $rv[] = $stopTime;
$json = json_decode(getPage($url));  
debug(print_r($json, true));  
$stops = $json[0]; }
$times = $json[1]; }
$foundStop = false; // var_dump($rv);
$viaPoints = Array(); return $rv;
foreach ($stops as $key => $row) { }
if ($foundStop) { function getTripPreviousTimePoint($tripID, $stop_sequence)
if (!$timingPointsOnly || !startsWith($row[5], "Wj")) {  
$viaPoints[] = Array( {
"id" => $row[0], global $conn;
"name" => $row[1], $query = " SELECT trip_id,stop_id,
"time" => $times[$key] stop_sequence
); FROM stop_times
} WHERE trip_id = :tripID and stop_sequence < :stop_sequence
} and stop_times.arrival_time IS NOT NULL ORDER BY stop_sequence DESC LIMIT 1";
else { debug($query, "database");
if ($row[0] == $stopid) $foundStop = true; $query = $conn -> prepare($query);
} $query -> bindParam(":tripID", $tripID);
} $query -> bindParam(":stop_sequence", $stop_sequence);
return $viaPoints; $query -> execute();
} if (!$query) {
function viaPointNames($tripid, $stopid) databaseError($conn -> errorInfo());
{ return Array();
$points = viaPoints($tripid, $stopid, true); }
$pointNames = Array(); return $query -> fetch(PDO :: FETCH_ASSOC);
foreach ($points as $point) { }
$pointNames[] = $point['name']; function getTripNextTimePoint($tripID, $stop_sequence)
}  
return implode(", ", $pointNames); {
} global $conn;
  $query = " SELECT trip_id,stop_id,
  stop_sequence
  FROM stop_times
  WHERE trip_id = :tripID and stop_sequence > :stop_sequence
  and stop_times.arrival_time IS NOT NULL ORDER BY stop_sequence LIMIT 1";
  debug($query, "database");
  $query = $conn -> prepare($query);
  $query -> bindParam(":tripID", $tripID);
  $query -> bindParam(":stop_sequence", $stop_sequence);
  $query -> execute();
  if (!$query) {
  databaseError($conn -> errorInfo());
  return Array();
  }
  return $query -> fetch(PDO :: FETCH_ASSOC);
  }
  function getTimeInterpolatedTripAtStop($tripID, $stop_sequence)
   
  {
  global $conn;
  // limit interpolation to between nearest actual points.
  $prevTimePoint = getTripPreviousTimePoint($tripID, $stop_sequence);
  $nextTimePoint = getTripNextTimePoint($tripID, $stop_sequence);
  // echo " prev {$lowestDelta['stop_sequence']} next {$nextTimePoint['stop_sequence']} ";
  $range = "";
  if ($prevTimePoint != "") $range .= " AND stop_sequence >= '{$prevTimePoint['stop_sequence']}'";
  if ($nextTimePoint != "") $range .= " AND stop_sequence <= '{$nextTimePoint['stop_sequence']}'";
  foreach (getTimeInterpolatedTrip($tripID, $range) as $tripStop) {
  if ($tripStop['stop_sequence'] == $stop_sequence) return $tripStop;
  }
  return Array();
  }
  function getTripStartTime($tripID)
   
  {
  global $conn;
  $query = "Select * from stop_times
  where trip_id = :tripID
  AND arrival_time IS NOT NULL
  AND stop_sequence = '1'";
  debug($query, "database");
  $query = $conn -> prepare($query);
  $query -> bindParam(":tripID", $tripID);
  $query -> execute();
  if (!$query) {
  databaseError($conn -> errorInfo());
  return Array();
  }
  $r = $query -> fetch(PDO :: FETCH_ASSOC);
  return $r['arrival_time'];
  }
  function getTripEndTime($tripID)
   
  {
  global $conn;
  $query = "SELECT trip_id,max(arrival_time) as arrival_time from stop_times
  WHERE stop_times.arrival_time IS NOT NULL and trip_id = :tripID group by trip_id";
  debug($query, "database");
  $query = $conn -> prepare($query);
  $query -> bindParam(":tripID", $tripID);
  $query -> execute();
  if (!$query) {
  databaseError($conn -> errorInfo());
  return Array();
  }
  $r = $query -> fetch(PDO :: FETCH_ASSOC);
  return $r['arrival_time'];
  }
  function getActiveTrips($time)
   
  {
  global $conn;
  if ($time == "") $time = current_time();
  $query = "Select distinct stop_times.trip_id, start_times.arrival_time as start_time, end_times.arrival_time as end_time from stop_times, (SELECT trip_id,arrival_time from stop_times WHERE stop_times.arrival_time IS NOT NULL
  AND stop_sequence = '1') as start_times, (SELECT trip_id,max(arrival_time) as arrival_time from stop_times WHERE stop_times.arrival_time IS NOT NULL group by trip_id) as end_times
  WHERE start_times.trip_id = end_times.trip_id AND stop_times.trip_id = end_times.trip_id AND :time > start_times.arrival_time AND :time < end_times.arrival_time";
  debug($query, "database");
  $query = $conn -> prepare($query);
  $query -> bindParam(":time", $time);
  $query -> execute();
  if (!$query) {
  databaseError($conn -> errorInfo());
  return Array();
  }
  return $query -> fetchAll();
  }
  function viaPoints($tripID, $stop_sequence = "", $timing_points_only = true)
   
  {
  global $conn;
  $query = "SELECT stops.stop_id, stop_name, arrival_time
  FROM stop_times join stops on stops.stop_id = stop_times.stop_id
  WHERE stop_times.trip_id = :tripID
  " . ($stop_sequence != "" ? " AND stop_sequence > :stop_sequence " : "") . ($timing_points_only ? "AND substr(stop_code,1,2) != 'Wj' ": ""). " ORDER BY stop_sequence";
  debug($query, "database");
  $query = $conn -> prepare($query);
  if ($stop_sequence != "") $query -> bindParam(":stop_sequence", $stop_sequence);
  $query -> bindParam(":tripID", $tripID);
  $query -> execute();
  if (!$query) {
  databaseError($conn -> errorInfo());
  return Array();
  }
  return $query -> fetchAll();
  }
  function viaPointNames($tripid, $stop_sequence = "")
   
  {
  $viaPointNames = Array();
  foreach (viaPoints($tripid, $stop_sequence) as $point) {
  $viaPointNames[] = $point['stop_name'];
  }
  if (sizeof($viaPointNames) > 0) {
  return r_implode(", ", $viaPointNames);
  }
  else {
  return "";
  }
  }
?> ?>