Stop using session for time/day
Stop using session for time/day

file:a/about.php -> file:b/about.php
--- a/about.php
+++ b/about.php
@@ -36,7 +36,7 @@
     Native clients also available for iPhone(<a href="http://itunes.apple.com/au/app/cbrtimetable/id444287349?mt=8">cbrTimetable by Sandor Kolotenko</a>
     , <a href="http://itunes.apple.com/au/app/act-buses/id376634797?mt=8">ACT Buses by David Sullivan</a>) 
     , Android (<a href="https://market.android.com/details?id=com.action">MyBus 2.0 by Imagine Team</a>) 
-    and Windows Phone 7 (<a href="http://www.windowsphone.com/en-AU/apps/d840375e-429c-4aa4-a358-80eec6ea9e66">TransHub Canberra by Soul Solutions</a>)
+    and Windows Phone 7 (<a href="http://www.windowsphone.com/en-AU/apps/d840375e-429c-4aa4-a358-80eec6ea9e66">TransHub Canberra by Soul Solutions</a>) Other web clients include <a href="http://canberra.itranzit.com/option.html">iTranzit</a>.
     <br />
     GTFS-realtime API:
     Alerts and Trip Updates (but only Cancelled or Stop Skipped)

--- a/aws/busuidb.sh
+++ b/aws/busuidb.sh
@@ -11,4 +11,7 @@
 #psql -d transitdata -c "GRANT SELECT,INSERT ON	TABLE myway_observations,myway_routes,myway_stops,myway_timingdeltas TO transitdata;"
 #psql -d transitdata -c	"GRANT SELECT,INSERT,UPDATE ON TABLE myway_routes,myway_stops TO transitdata;"
 ##psql -d transitdata -c "GRANT SELECT ON ALL TABLES IN SCHEMA public TO transitdata;"
+## INSERT INTO geometry_columns(f_table_catalog, f_table_schema, f_table_name, f_geometry_column, coord_dimension, srid, "type")
+##SELECT '', 'public', 'shapes', 'shape_pt', ST_CoordDim(shape_pt), ST_SRID(shape_pt), GeometryType(shape_pt)
+##FROM shapes LIMIT 1;
 php /var/www/updatedb.php

--- a/geo/route.kml.php
+++ b/geo/route.kml.php
@@ -21,8 +21,8 @@
  echo '<description><![CDATA[ <a href="'.$link.'">'.$route['route_short_name']." ".$route['route_long_name']."</a>]]> </description>";
 echo "<styleUrl>#yellowLineGreenPoly</styleUrl>";
 
-	$trips = getRouteTrips($routeid);
-	echo getTripShape($trips[0]['trip_id']);
+	$trip = getRouteNextTrip($routeid);
+	echo getTripShape($trip['trip_id']);
 
 echo "</Placemark>\n</Document></kml>\n";
 ?>

--- a/include/common-db.inc.php
+++ b/include/common-db.inc.php
@@ -27,7 +27,9 @@
 }
 
 function databaseError($errMsg) {
-    die($errMsg);
+    if ($errMsg[1] != "") {
+    die(print_r($errMsg,true));
+    }
 }
 
 include ('db/route-dao.inc.php');

--- a/include/common-request.inc.php
+++ b/include/common-request.inc.php
@@ -57,15 +57,15 @@
 if (isset($_REQUEST['stopids'])) {
     $stopids = explode(",", filter_var($_REQUEST['stopids'], FILTER_SANITIZE_STRING));
 }
+if (isset($_REQUEST['routeids'])) {
+    $routeids = explode(",", filter_var($_REQUEST['routeids'], FILTER_SANITIZE_STRING));
+}
 if (isset($_REQUEST['tripid'])) {
     $tripid = filter_var($_REQUEST['tripid'], FILTER_SANITIZE_STRING);
 }
 if (isset($_REQUEST['stopid'])) {
     $stopid = filter_var($_REQUEST['stopid'], FILTER_SANITIZE_NUMBER_INT);
 }
-if (isset($_REQUEST['routeid'])) {
-    $routeid = filter_var($_REQUEST['routeid'], FILTER_SANITIZE_NUMBER_INT);
-}
 if (isset($_REQUEST['geolocate'])) {
     $geolocate = filter_var($_REQUEST['geolocate'], FILTER_SANITIZE_URL);
 }

--- a/include/common-session.inc.php
+++ b/include/common-session.inc.php
@@ -17,14 +17,6 @@
  */
 // you have to open the session to be able to modify or remove it
 session_start();
-if (isset($_REQUEST['service_period'])) {
-    $_SESSION['service_period'] = filter_var($_REQUEST['service_period'], FILTER_SANITIZE_STRING);
-    sessionUpdated();
-}
-if (isset($_REQUEST['time'])) {
-    $_SESSION['time'] = filter_var($_REQUEST['time'], FILTER_SANITIZE_STRING);
-    sessionUpdated();
-}
 if (isset($_REQUEST['geolocate']) && $_REQUEST['geolocate'] != "Enter co-ordinates or address here") {
     $geocoded = false;
     if (isset($_REQUEST['lat']) && isset($_REQUEST['lon'])) {
@@ -70,7 +62,7 @@
 
 //debug(print_r($_SESSION, true) , "session");
 function current_time() {
-    return ($_SESSION['time'] ? $_SESSION['time'] : date("H:i:s"));
+    return ($_REQUEST['time'] ? $_REQUEST['time'] : date("H:i:s"));
 }
 
 ?>

--- a/include/common-transit.inc.php
+++ b/include/common-transit.inc.php
@@ -20,15 +20,17 @@
     'saturday',
     'weekday'
 );
-
+function service_period_day ($spid) {
+    $idParts = explode("-",$spid);
+        return strtolower($idParts[2]);
+}
 function service_period($date = "") {
 
-    if (isset($_SESSION['service_period']))
-        return $_SESSION['service_period'];
+    if (isset($_REQUEST['service_period']))
+        return $_REQUEST['service_period'];
     $override = getServiceOverride($date);
     if ($override['service_id']) {
-        $idParts = explode("-",$override['service_id']);
-        return strtolower($idParts[2]);
+        return service_period_day ($override['service_id']);
     }
 
     switch (date('w', ($date != "" ? $date : time()))) {
@@ -50,6 +52,9 @@
             //return 'weekday';
             return Array("2010-BELCMAST-Weekday-15","2010-TUGGMAST-Weekday-14"); 
     }
+}
+function valid_service_ids() {
+    return array_merge(service_ids(""),service_ids('saturday'),service_ids('sunday'));
 }
 
 function midnight_seconds($time = "") {

--- a/include/db/route-dao.inc.php
+++ b/include/db/route-dao.inc.php
@@ -29,6 +29,7 @@
     }
     return $query->fetch(PDO :: FETCH_ASSOC);
 }
+
 function getRoutesByShortName($routeShortName) {
     global $conn;
     $query = "Select distinct route_id, route_short_name from routes where route_short_name = :routeShortName";
@@ -45,8 +46,11 @@
 
 function getRouteHeadsigns($routeID) {
     global $conn;
-    $query = "select distinct stops.stop_name, trip_headsign,direction_id from routes join trips on trips.route_id = routes.route_id
-join stop_times on stop_times.trip_id = trips.trip_id join stops on stop_times.stop_id = stops.stop_id where trips.route_id = :routeID and stop_times.stop_sequence = 1";
+    $query = "select stops.stop_name, direction_id,max(service_id) as service_id, count(*)
+        from routes join trips on trips.route_id = routes.route_id
+join stop_times on stop_times.trip_id = trips.trip_id join stops on 
+stop_times.stop_id = stops.stop_id where trips.route_id = :routeID 
+and stop_times.stop_sequence = 1 group by stops.stop_name, direction_id having count(*) > 2";
     debug($query, "database");
     $query = $conn->prepare($query);
     $query->bindParam(":routeID", $routeID);
@@ -55,9 +59,14 @@
         databaseError($conn->errorInfo());
         return Array();
     }
-return $query->fetchAll();
-}
-
+    return $query->fetchAll();
+}
+function getRouteDescription($routeID) {
+    $trip = getRouteNextTrip($routeID);
+    $start = getTripStartingPoint($trip['trip_id']); 
+    $end = getTripDestination($trip['trip_id']);
+    return "From ".$start['stop_name']." to ".$end['stop_name'];
+}
 function getRouteByFullName($routeFullName) {
     global $conn;
     $query = "Select * from routes where route_short_name||route_long_name = :routeFullName LIMIT 1";
@@ -85,7 +94,7 @@
     return $query->fetchAll();
 }
 
-function getRoutesByNumber($routeNumber = "") {
+function getRoutesByNumber($routeNumber = "", $directionID = "",$service_period = "") {
     global $conn;
     if ($routeNumber != "") {
         $query = "Select distinct routes.route_id,routes.route_short_name,routes.route_long_name,service_id from routes  join trips on trips.route_id =
@@ -134,15 +143,16 @@
 
 function getRouteNextTrip($routeID) {
     global $conn;
-    $query = "select * from routes join trips on trips.route_id = routes.route_id
-join stop_times on stop_times.trip_id = trips.trip_id where
-arrival_time > :currentTime and routes.route_id = :routeID order by
+   
+    $query = "select routes.route_id,direction_id,trips.trip_id,departure_time from routes join trips on trips.route_id = routes.route_id
+join stop_times on stop_times.trip_id = trips.trip_id where  arrival_time > :currentTime and routes.route_id = :routeID order by
 arrival_time limit 1";
     debug($query, "database");
     $query = $conn->prepare($query);
     $query->bindParam(":currentTime", current_time());
     $query->bindParam(":routeID", $routeID);
     $query->execute();
+    databaseError($conn->errorInfo());
     if (!$query) {
         databaseError($conn->errorInfo());
         return Array();
@@ -179,40 +189,61 @@
     return Array();
 }
 
-function getRouteTrips($routeID) {
-    global $conn;
-    $query = "select routes.route_id,trips.trip_id,service_id,arrival_time, stop_id, stop_sequence from routes join trips on trips.route_id = routes.route_id
-join stop_times on stop_times.trip_id = trips.trip_id where routes.route_id = :routeID and stop_sequence = '1' order by
-arrival_time ";
-    debug($query, "database");
-    $query = $conn->prepare($query);
-    $query->bindParam(":routeID", $routeID);
-    $query->execute();
-    if (!$query) {
-        databaseError($conn->errorInfo());
-        return Array();
-    }
-    return $query->fetchAll();
-}
-
-function getRoutesByDestination($destination = "", $service_period = "") {
+function getRoutesTrips($routeIDs, $directionID = "", $service_period = "") {
     global $conn;
     if ($service_period == "")
         $service_period = service_period();
+    $service_ids = service_ids($service_period);
+    $sidA = $service_ids[0];
+    $sidB = $service_ids[1];
+    $directionSQL = "";
+    if ($directionID != "")
+        $directionSQL = " and direction_id = :directionID ";
+    $query = "select routes.route_id,trips.trip_id,service_id,arrival_time, stop_id, stop_sequence from routes join trips on trips.route_id = routes.route_id
+join stop_times on stop_times.trip_id = trips.trip_id where (service_id=:service_periodA OR service_id=:service_periodB)
+AND (routes.route_id = :routeIDA OR routes.route_id = :routeIDB) " . $directionSQL . " and stop_sequence = '1' order by
+arrival_time ";
+    debug($query, "database");
+    $query = $conn->prepare($query);
+    $query->bindParam(":routeIDA", $routeIDs[0]);
+    $query->bindParam(":routeIDB", $routeIDs[1]);
+    $query->bindParam(":service_periodA", $sidA);
+    $query->bindParam(":service_periodB", $sidB);
+    if ($directionSQL != "")
+        $query->bindParam(":directionID", $directionID);
+    $query->execute();
+    if (!$query) {
+        databaseError($conn->errorInfo());
+        return Array();
+    }
+    return $query->fetchAll();
+}
+
+function getRoutesByDestination($destination = "", $service_period = "") {
+    global $conn;
+    if ($service_period == "")
+        $service_period = service_period();
+    $service_ids = service_ids($service_period);
+    $sidA = $service_ids[0];
+    $sidB = $service_ids[1];
     if ($destination != "") {
         $query = "SELECT DISTINCT trips.route_id,route_short_name,route_long_name, service_id
 FROM stop_times join trips on trips.trip_id =
 stop_times.trip_id join routes on trips.route_id = routes.route_id
-WHERE route_long_name = :destination AND  service_id=:service_period order by route_short_name";
+WHERE route_long_name = :destination AND (service_id=:service_periodA OR service_id=:service_periodB)
+ order by route_short_name";
     } else {
         $query = "SELECT DISTINCT route_long_name
 FROM stop_times join trips on trips.trip_id =
 stop_times.trip_id join routes on trips.route_id = routes.route_id
-WHERE service_id= :service_period order by route_long_name";
-    }
-    debug($query, "database");
-    $query = $conn->prepare($query);
-    $query->bindParam(":service_period", $service_period);
+WHERE (service_id=:service_periodA OR service_id=:service_periodB)
+ order by route_long_name";
+    }
+    debug($query, "database");
+    $query = $conn->prepare($query);
+
+    $query->bindParam(":service_periodA", $sidA);
+    $query->bindParam(":service_periodB", $sidB);
     if ($destination != "")
         $query->bindParam(":destination", $destination);
     $query->execute();
@@ -226,14 +257,20 @@
 function getRoutesBySuburb($suburb, $service_period = "") {
     if ($service_period == "")
         $service_period = service_period();
+    $service_ids = service_ids($service_period);
+    $sidA = $service_ids[0];
+    $sidB = $service_ids[1];
     global $conn;
     $query = "SELECT DISTINCT service_id,trips.route_id,route_short_name,route_long_name
 FROM stop_times join trips on trips.trip_id = stop_times.trip_id
 join routes on trips.route_id = routes.route_id
 join stops on stops.stop_id = stop_times.stop_id
-WHERE zone_id LIKE ':suburb AND service_id=:service_period ORDER BY route_short_name";
-    debug($query, "database");
-    $query = $conn->prepare($query);
+WHERE zone_id LIKE ':suburb AND (service_id=:service_periodA OR service_id=:service_periodB)
+ ORDER BY route_short_name";
+    debug($query, "database");
+    $query = $conn->prepare($query);
+    $query->bindParam(":service_periodA", $sidA);
+    $query->bindParam(":service_periodB", $sidB);
     $query->bindParam(":service_period", $service_period);
     $suburb = "%" . $suburb . ";%";
     $query->bindParam(":suburb", $suburb);
@@ -248,7 +285,7 @@
 function getRoutesNearby($lat, $lng, $limit = "", $distance = 500) {
     if ($service_period == "")
         $service_period = service_period();
-        $service_ids = service_ids($service_period);
+    $service_ids = service_ids($service_period);
     $sidA = $service_ids[0];
     $sidB = $service_ids[1];
     if ($limit != "")

--- a/include/db/stop-dao.inc.php
+++ b/include/db/stop-dao.inc.php
@@ -176,7 +176,7 @@
         
     global $conn;
     if ($afterTime != "") {
-        $query = " SELECT stop_times.trip_id,stop_times.arrival_time,stop_times.stop_id,stop_sequence,service_id,trips.route_id,route_short_name,route_long_name,end_times.arrival_time as end_time
+        $query = " SELECT stop_times.trip_id,stop_times.arrival_time,stop_times.stop_id,stop_sequence,service_id,trips.route_id,trips.direction_id,route_short_name,route_long_name,end_times.arrival_time as end_time
 FROM stop_times
 join trips on trips.trip_id =
 stop_times.trip_id

--- a/include/db/trip-dao.inc.php
+++ b/include/db/trip-dao.inc.php
@@ -33,17 +33,31 @@
     }
     return $query->fetch(PDO :: FETCH_ASSOC);
 }
-
-function getTripShape($tripID) {
-    // todo, use shapes table if shape_id specified
-    global $conn;
-    $query = "SELECT ST_AsKML(ST_MakeLine(geometry(a.position))) as the_route
-FROM (SELECT position,
+function getTripStops($tripID) {
+    global $conn;
+    $query = "SELECT stop_id, stop_name, ST_AsKML(position) as positionkml,
 	stop_sequence, trips.trip_id
 FROM stop_times
 join trips on trips.trip_id = stop_times.trip_id
 join stops on stops.stop_id = stop_times.stop_id
-WHERE trips.trip_id = :tripID ORDER BY stop_sequence) as a group by a.trip_id";
+WHERE trips.trip_id = :tripID ORDER BY stop_sequence";
+    debug($query, "database");
+    $query = $conn->prepare($query);
+    $query->bindParam(":tripID", $tripID);
+    $query->execute();
+    if (!$query) {
+        databaseError($conn->errorInfo());
+        return Array();
+    }
+    return $query->fetchColumn(0);
+}
+function getTripShape($tripID) {
+    // todo, use shapes table if shape_id specified
+    global $conn;
+    $query = "SELECT ST_AsKML(ST_MakeLine(geometry(a.shape_pt))) as the_route
+FROM (SELECT shapes.shape_id,shape_pt from shapes
+inner join trips on shapes.shape_id = trips.shape_id
+WHERE trips.trip_id = :tripID ORDER BY shape_pt_sequence) as a group by a.shape_id";
     debug($query, "database");
     $query = $conn->prepare($query);
     $query->bindParam(":tripID", $tripID);
@@ -119,6 +133,22 @@
     $r = $query->fetch(PDO :: FETCH_ASSOC);
     return $r['arrival_time'];
 }
+function getTripStartingPoint($tripID) {
+    global $conn;
+    $query = "SELECT stops.stop_id, stops.stop_name, stops.stop_desc 
+        from stop_times inner join stops on stop_times.stop_id =  stops.stop_id
+	WHERE trip_id = :tripID and stop_sequence = '1' limit 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;
+}
 
 function getTripDestination($tripID) {
     global $conn;

--- a/routeList.php
+++ b/routeList.php
@@ -119,8 +119,28 @@
     }
     else if ($numberSeries) {
         $routes = getRoutesByNumberSeries($numberSeries);
+        $filteredRoutes = Array();
         foreach ($routes as $route) {
-            echo '<li> <a href="trip.php?routeid=' . $route['route_id'] . '"><h3>' . $route['route_short_name'] . "</h3><p>" . $route['route_long_name'] . " (" . ucwords($route['service_id']) . ")</p></a></li>\n";
+            foreach (getRouteHeadsigns($route['route_id']) as $headsign) {
+                $start = $headsign['stop_name'];
+            $serviceday = service_period_day ( $headsign['service_id']);
+            $key = $route['route_short_name'].".".$headsign['direction_id'];
+            if (isset($filteredRoutes[$key])) {
+                $filteredRoutes[$key]['route_ids'][] = $route['route_id'];
+                $filteredRoutes[$key]['route_ids'] = array_unique($filteredRoutes[$key]['route_ids']);
+            } else {
+                $filteredRoutes[$key]['route_short_name'] = $route['route_short_name'];
+                $filteredRoutes[$key]['route_long_name'] = "Starting at ".$start;
+                $filteredRoutes[$key]['service_id'] = $serviceday;
+                $filteredRoutes[$key]['direction_id'] = $headsign['direction_id'];
+            }
+            }
+        }
+        foreach ($filteredRoutes as $key => $route) {
+               echo '<li> <a href="trip.php?routeids=' . implode(",",$route['route_ids']) . '&directionid='.$route['direction_id'].'"><h3>' . $route['route_short_name'] . "</h3>
+                   
+                <p>" . $route['route_long_name'] . " (" . ucwords($route['service_id']) . ")</p>
+                    </a></li>\n";
         }
     }
 } else {

--- a/servicealerts/importer.py
+++ b/servicealerts/importer.py
@@ -1,3 +1,5 @@
+#dependencies http://code.google.com/p/python-twitter/
+
 # info
 # http://stackoverflow.com/questions/4206882/named-entity-recognition-with-preset-list-of-names-for-python-php/4207128#4207128
 # http://alias-i.com/lingpipe/demos/tutorial/ne/read-me.html approximate dist
@@ -12,13 +14,9 @@
 # source: https://gist.github.com/322906/90dea659c04570757cccf0ce1e6d26c9d06f9283
 import nltk
 import twitter
-import tweepy
 import psycopg2
-from iniparse import INIConfig
-
 def insert_service_alert_sitewide(heading, message, url):
-        print "NaN"
-
+        
 def insert_service_alert_for_street(streets, heading, message, url):
     	conn_string = "host='localhost' dbname='energymapper' user='postgres' password='snmc'"
 	# print the connection string we will use to connect
@@ -31,22 +29,30 @@
 		cursor = conn.cursor()
 
 		# execute our Query
-		cursor.execute("")
+		cursor.execute("select max(value), extract(dow from max(time)) as dow, \
+extract(year from max(time))::text || lpad(extract(month from max(time))::text,2,'0') \
+|| lpad(extract(month from max(time))::text,2,'0') as yearmonthweek, to_char(max(time),'J') \
+from environmentdata_values where \"dataSourceID\"='NSWAEMODemand' \
+group by extract(dow from time), extract(year from time),  extract(week from time) \
+order by  extract(year from time),  extract(week from time), extract(dow from time)")
 
 		# retrieve the records from the database
 		records = cursor.fetchall()
 
   	  	for record in records:
 			ys.append(record[0])
-                # >>> cur.execute("INSERT INTO test (num, data) VALUES (%s, %s)", (42, 'bar'))
-                #>>> cur.statusmessage
-                #'INSERT 0 1'
+# >>> cur.execute("INSERT INTO test (num, data) VALUES (%s, %s)", (42, 'bar'))
+#>>> cur.statusmessage
+#'INSERT 0 1'
 	except:
 		# Get the most recent exception
 		exceptionType, exceptionValue, exceptionTraceback = sys.exc_info()
 		# Exit the script and print an error telling what happened.
 		sys.exit("Database connection failed!\n ->%s" % (exceptionValue))
 		
+def get_tweets(user):
+    tapi = twitter.Api()
+    return tapi.GetUserTimeline(user)
 
 def extract_entity_names(t):
     entity_names = []
@@ -79,16 +85,4 @@
 
     # Print unique entity names
     print set(entity_names)
-cfg = INIConfig(open('/tmp/aws.ini'))
 
-auth = tweepy.OAuthHandler(cfg.api_keys.twitter_consumer_key, cfg.api_keys.twitter_consumer_secret)
-auth.set_access_token(cfg.api_keys.twitter_access_token, cfg.api_keys.twitter_access_token_secret)
-
-api = tweepy.API(auth)
-
-# If the authentication was successful, you should
-# see the name of the account print out
-print api.me().name
-# https://github.com/tweepy/tweepy/blob/master/tweepy/api.py
-print api.user_timeline(screen_name="ACTPol_Traffic")
-print api.update_status(status="test")

--- a/servicealerts/index.php
+++ b/servicealerts/index.php
@@ -2,12 +2,17 @@
 include ('../include/common.inc.php');
 
 include_header("Service Alerts", "index");
+echo '<ul data-role="listview" data-theme="e" data-groupingtheme="e">';
+	
  if ($_SESSION['authed'] == true) {
- 	echo '<ul data-role="listview" data-theme="e" data-groupingtheme="e">
-		<li><a href="servicealert_editor.php"><h3>servicealert_editor</h3>
-		<p>servicealert_editor</p></a></li>
-            </ul>';
- }
+ 	echo'	<li><a href="servicealert_editor.php"><h3>servicealert_editor</h3>
+		<p>servicealert_editor</p></a></li>';
+          }
+ 	echo'	<li><a href="servicealert_viewer.php"><h3>Service Alert Viewer</h3>
+		<p>Browse current network alerts</p></a></li>';
+          
+           echo'  </ul>';
+
 ?>	    </div>
 <?php
 include_footer()

--- /dev/null
+++ b/servicealerts/servicealert_viewer.php
@@ -1,1 +1,53 @@
+<?php
+/*
+ *    Copyright 2010,2011 Alexander Sadleir 
 
+  Licensed under the Apache License, Version 2.0 (the "License");
+  you may not use this file except in compliance with the License.
+  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+ */
+include ('../include/common.inc.php');
+include_header("Service Alert Viewer", "serviceAlertViewer");
+/**
+ * Currently support:
+ * network inform
+ * stop remove: route patch, stop remove
+ * - stop search
+ * street inform: route inform, stop inform
+ * - street search
+ */
+if (!isset($_REQUEST['view'])) {
+
+?>
+Active and Future Alerts:
+<table>
+    <?php
+    foreach (getFutureAlerts() as $alert) {
+        echo "<tr><td>{$alert['header']}</td><td>" . substr($alert['description'], 0, 999) . '</td><td><a href="?view=' . $alert['id'] . '">View</a></td></tr>';
+    }
+    ?>
+</table>
+<?php
+} else {
+$alert = getServiceAlert($_REQUEST['view']);
+echo "<h1>{$alert['header']}</h1>
+<h2> From ".date("c",$alert['start'])." to ".date("c",$alert['end'])."</h2>
+<small>{$alert['description']}</small><br>
+Source: <A href='{$alert['url']}'>{$alert['url']}</a><br>"; 
+    echo "Informed Entities for ID {$_REQUEST['view']}:";
+    echo '<table>';
+    foreach (getInformedAlerts($_REQUEST['view'], "", "") as $informed) {
+        echo "<tr><td>{$informed['informed_class']}</td><td>{$informed['informed_id']}</td><td>{$informed['informed_action']}" . '</td></tr>';
+    }
+    echo '</table>';
+}
+include_footer();
+?>

file:a/stop.php -> file:b/stop.php
--- a/stop.php
+++ b/stop.php
@@ -98,12 +98,14 @@
 
 // time settings
 echo '<div id="settings" data-role="collapsible" data-collapsed="true">
-<h3>Change Time (' . (isset($_SESSION['time']) ? $_SESSION['time'] : "Current Time,") . ' ' . ucwords(service_period()) . ')...</h3>
-        <form action="' . basename($_SERVER['PHP_SELF']) . "?" . $_SERVER['QUERY_STRING'] . '" method="post">
+<h3>Change Time (' . (isset($_REQUEST['time']) ? $_REQUEST['time'] : "Current Time,") . ' ' . ucwords(service_period()) . ')...</h3>
+        <form action="' . basename($_SERVER['PHP_SELF']) . '" method="GET">
+            <input type="hidden" name="stopid" id="stopid" value="' . (isset($_REQUEST['stopid']) ? $_REQUEST['stopid'] : "") . '"/>
+                 <input type="hidden" name="stopcode" id="stopcode" value="' . (isset($_REQUEST['stopcode']) ? $_REQUEST['stopcode'] : "") . '"/>
         <div class="ui-body"> 
     		<div data-role="fieldcontain">
 		        <label for="time"> Time: </label>
-		    	<input type="time" name="time" id="time" value="' . (isset($_SESSION['time']) ? $_SESSION['time'] : date("H:i")) . '"/>
+		    	<input type="time" name="time" id="time" value="' . (isset($_REQUEST['time']) ? $_REQUEST['time'] : date("H:i")) . '"/>
 			<a href="#" name="currentTime" id="currentTime" onClick="var d = new Date();' . "$('#time').val(d.getHours() +':'+ (d.getMinutes().toString().length == 1 ? '0'+ d.getMinutes():  d.getMinutes()));" . '">Current Time?</a>
 	        </div>
 		<div data-role="fieldcontain">
@@ -128,14 +130,34 @@
 } else {
     $trips = getStopTripsWithTimes($stopid);
 }
+echo "<div class='ui-header' style='overflow: visible; height: 2.5em'>";
+// later/earlier button setup
+if (sizeof($trips) == 0) {
+    $time = isset($_REQUEST['time']) ? strtotime($_REQUEST['time']) : time();
+    $earlierTime = $time - (90 * 60);
+    $laterTime = $time + (90 * 60);
+} else {
+    $earlierTime = strtotime($trips[0]['arrival_time']) - (90 * 60);
+    $laterTime = strtotime($trips[sizeof($trips) - 1]['arrival_time']) - 60;
+}
+if (sizeof($stopids) > 0) {
+    $stopidurl = "stopids=" . implode(",", $stopids);
+} else {
+    $stopidurl = "stopid=$stopid";
+}
+if (sizeof($trips) > 10) {
+    echo '<a href="stop.php?' . $stopidurl . '&service_period=' . service_period() . '&time=' . date("H:i", $laterTime) . '" data-icon="arrow-r" class="ui-btn-right">Later Trips</a>';
+}
+echo '<a href="stop.php?' . $stopidurl . '&service_period=' . service_period() . '&time=' . date("H:i", $earlierTime) . '" data-icon="arrow-l" class="ui-btn-left">Earlier Trips</a>';
+echo "</div>";
 if (sizeof($trips) == 0) {
     echo "<li style='text-align: center;'>No trips in the near future.</li>";
 } else {
     foreach ($trips as $trip) {
         echo '<li>';
-        
-                $destination = getTripDestination($trip['trip_id']);
-        echo '<a href="trip.php?stopid=' . $stopid . '&amp;tripid=' . $trip['trip_id'] . '"><h3>' . $trip['route_short_name'] . " " . $destination['stop_name'] . "</h3><p>";
+
+        $destination = getTripDestination($trip['trip_id']);
+        echo '<a href="trip.php?stopid=' . $stopid . '&amp;tripid=' . $trip['trip_id'] . '"><h3>' . $trip['route_short_name'] . " towards " . $destination['stop_name'] . "</h3><p>";
         $viaPoints = viaPointNames($trip['trip_id'], $trip['stop_sequence']);
         if ($viaPoints != "")
             echo '<br><span class="viaPoints">Via: ' . $viaPoints . '</span>';

--- a/stopList.php
+++ b/stopList.php
@@ -102,7 +102,7 @@
                     // subsequent duplicates
                     $stopsGrouped["stop_ids"][] = $stop['stop_id'];
                     echo '<li>';
-                    echo '<a href="stop.php?stopids=' . implode(",", $stopsGrouped['stop_ids']) . '">';
+                    echo '<a href="stop.php?stopids=' . implode(",", $stopsGrouped['stop_ids']) . '&stopcodes=' . implode(",", $stopsGrouped['stop_codes']) . '">';
                     if (isset($_SESSION['lat']) && isset($_SESSION['lon'])) {
                         echo '<span class="ui-li-count">' . distance($stop['stop_lat'], $stop['stop_lon'], $_SESSION['lat'], $_SESSION['lon'], true) . 'm away</span>';
                     }

file: