National Rail

When we're having a drink in the pub my parents always ask me to check when the next train is, despite showing them how to add the link to their phone's home screen etc. They are starting to understand Matrix a bit, so now they can just ask Adelaide for the next train time.

There is an API for National Rail, but it wanted me to sign up and this was just easier.

There is a page on National Rail's website that lets me specify the exact starting and destination station (which is all my parents needed): https://ojp.nationalrail.co.uk/service/ldbboard/dep/CHC/ADR/To

get_train_times.php
$filename = "https://ojp.nationalrail.co.uk/service/ldbboard/dep/CHC/ADR/To";
$data = file_get_contents($filename);
 
$doc = new DOMDocument();
@$doc->loadHTML($data);
 
$finder = new DomXPath($doc);
 
// this is the table on the page that has the rows of train depature times
$content_class = "tbl-cont";
$content = $finder->query("//*[contains(@class, '$content_class')]");
$departure_table = $content[0];
 
$row = 0;
foreach($departure_table->getElementsByTagName('tr') as $tr) {
   $tds = $tr->getElementsByTagName('td');
   $cell = 0;
   foreach($tds as $td) {
      $table[$row][$cell] = trim($td->nodeValue);
      $cell++;
   }
   $row++;
}
 
foreach($table as $row=>$cells) {
   $due = $cells[0];
   $destination = trim($cells[1]);
   $status = $cells[2];
   $platform = $cells[3];
   $details = $cells[4];
   // check if a time is mentioned in the status (usually a delayed arrival time), use that as due time instead
   if(preg_match("/\d\d:\d\d/", $status, $other_times))
      $due = $other_times[0];
   $minutes = floor((strtotime($due) - strtotime('now'))/60);
 
   echo "$due to $destination on platform $platform (due in $minutes minutes) [$status]";

This page is also a shortcut on their phones that tells them when the next trains to and from Airdrie are: https://starflyer.armchairscientist.co.uk/data/train.php