Skip to content

Commit

Permalink
🗃️ migrate trips table to use ID instead of IBNR
Browse files Browse the repository at this point in the history
see #2411
  • Loading branch information
MrKrisKrisu committed Mar 11, 2024
1 parent bb2365e commit 1047f57
Show file tree
Hide file tree
Showing 3 changed files with 86 additions and 20 deletions.
24 changes: 12 additions & 12 deletions app/Http/Controllers/HafasController.php
Original file line number Diff line number Diff line change
Expand Up @@ -419,8 +419,8 @@ public static function fetchHafasTrip(string $tripID, string $lineName): Trip {
'linename' => $tripJson->line->name,
'journey_number' => $tripJson->line?->fahrtNr === "0" ? null : $tripJson->line?->fahrtNr,
'operator_id' => $operator?->id,
'origin' => $origin->ibnr,
'destination' => $destination->ibnr,
'origin_id' => $origin->id,
'destination_id' => $destination->id,
'polyline_id' => $polyline->id,
'departure' => $tripJson->plannedDeparture,
'arrival' => $tripJson->plannedArrival,
Expand Down Expand Up @@ -493,16 +493,16 @@ public static function fetchHafasTrip(string $tripID, string $lineName): Trip {

public static function refreshStopovers(stdClass $rawHafas): stdClass {
$stopoversUpdated = 0;
$payloadArrival = [];
$payloadArrival = [];
$payloadDeparture = [];
$payloadCancelled = [];
foreach ($rawHafas->stopovers ?? [] as $stopover) {
if (!isset($stopover->arrivalDelay) && !isset($stopover->departureDelay) && !isset($stopover->cancelled)) {
continue; // No realtime data present for this stopover, keep existing data
}

$stop = self::parseHafasStopObject($stopover->stop);
$arrivalPlanned = Carbon::parse($stopover->plannedArrival)->tz(config('app.timezone'));
$stop = self::parseHafasStopObject($stopover->stop);
$arrivalPlanned = Carbon::parse($stopover->plannedArrival)->tz(config('app.timezone'));
$departurePlanned = Carbon::parse($stopover->plannedDeparture)->tz(config('app.timezone'));

$basePayload = [
Expand All @@ -513,19 +513,19 @@ public static function refreshStopovers(stdClass $rawHafas): stdClass {
];

if (isset($stopover->arrivalDelay) && isset($stopover->arrival)) {
$arrivalReal = Carbon::parse($stopover->arrival)->tz(config('app.timezone'));
$payloadArrival[] = array_merge($basePayload, [ 'arrival_real' => $arrivalReal ]);
$arrivalReal = Carbon::parse($stopover->arrival)->tz(config('app.timezone'));
$payloadArrival[] = array_merge($basePayload, ['arrival_real' => $arrivalReal]);
}

if (isset($stopover->departureDelay) && isset($stopover->departure)) {
$departureReal = Carbon::parse($stopover->departure)->tz(config('app.timezone'));
$payloadDeparture[] = array_merge($basePayload, [ 'departure_real' => $departureReal ]);
$departureReal = Carbon::parse($stopover->departure)->tz(config('app.timezone'));
$payloadDeparture[] = array_merge($basePayload, ['departure_real' => $departureReal]);
}

// In case of cancellation, arrivalDelay/departureDelay will be null while the cancelled attribute will be present and true
// If cancelled is false / missing while other RT data is present (see initial if expression), it will be upserted to false
// This behavior is required for potential withdrawn cancellations
$payloadCancelled[] = array_merge($basePayload, [ 'cancelled' => $stopover->cancelled ?? false ]);
$payloadCancelled[] = array_merge($basePayload, ['cancelled' => $stopover->cancelled ?? false]);

$stopoversUpdated++;
}
Expand All @@ -534,8 +534,8 @@ public static function refreshStopovers(stdClass $rawHafas): stdClass {

return (object) [
"stopovers" => $stopoversUpdated,
"rows" => [
"arrival" => Stopover::upsert($payloadArrival, $key, ['arrival_real']),
"rows" => [
"arrival" => Stopover::upsert($payloadArrival, $key, ['arrival_real']),
"departure" => Stopover::upsert($payloadDeparture, $key, ['departure_real']),
"cancelled" => Stopover::upsert($payloadCancelled, $key, ['cancelled'])
]
Expand Down
15 changes: 7 additions & 8 deletions app/Models/Trip.php
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@
* @property string $linename
* @property string $journey_number
* @property int $operator_id
* @property int $origin
* @property int $destination
* @property int $origin_id
* @property int $destination_id
* @property int $polyline_id
* @property UTCDateTime $departure
* @property UTCDateTime $arrival
Expand All @@ -32,7 +32,6 @@
*
* @todo rename table only to "Trip" (without Hafas)
* @todo rename "linename" to "line_name" (or something else, but not "linename")
* @todo migrate origin & destination to use "id" instead of "ibnr" and rename to "origin_id" & "destination_id"
*/
class Trip extends Model
{
Expand All @@ -41,7 +40,7 @@ class Trip extends Model

protected $table = 'hafas_trips';
protected $fillable = [
'trip_id', 'category', 'number', 'linename', 'journey_number', 'operator_id', 'origin', 'destination',
'trip_id', 'category', 'number', 'linename', 'journey_number', 'operator_id', 'origin_id', 'destination_id',
'polyline_id', 'departure', 'arrival', 'source', 'user_id', 'last_refreshed',
];
protected $hidden = ['created_at', 'updated_at'];
Expand All @@ -51,8 +50,8 @@ class Trip extends Model
'category' => HafasTravelType::class,
'journey_number' => 'integer',
'operator_id' => 'integer',
'origin' => 'integer',
'destination' => 'integer',
'origin_id' => 'integer',
'destination_id' => 'integer',
'polyline_id' => 'integer',
'departure' => UTCDateTime::class,
'arrival' => UTCDateTime::class,
Expand All @@ -66,11 +65,11 @@ public function polyline(): HasOne {
}

public function originStation(): BelongsTo {
return $this->belongsTo(Station::class, 'origin', 'ibnr');
return $this->belongsTo(Station::class, 'origin_id', 'id');
}

public function destinationStation(): BelongsTo {
return $this->belongsTo(Station::class, 'destination', 'ibnr');
return $this->belongsTo(Station::class, 'destination_id', 'id');
}

public function operator(): BelongsTo {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
<?php

use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Schema;

return new class extends Migration
{
public function up(): void {
Schema::table('hafas_trips', static function(Blueprint $table) {
//Columns need to be nullable for the migration
$table->unsignedBigInteger('origin_id')->nullable()->after('origin');
$table->unsignedBigInteger('destination_id')->nullable()->after('destination');

$table->foreign('origin_id')->references('id')->on('train_stations');
$table->foreign('destination_id')->references('id')->on('train_stations');
});

DB::table('hafas_trips')->update([
'origin_id' => DB::raw('(SELECT id FROM train_stations WHERE ibnr = hafas_trips.origin)'),
'destination_id' => DB::raw('(SELECT id FROM train_stations WHERE ibnr = hafas_trips.destination)'),
]);

Schema::table('hafas_trips', static function(Blueprint $table) {
$table->dropForeign(['origin']);
$table->dropForeign(['destination']);

$table->dropColumn('origin');
$table->dropColumn('destination');
});

Schema::table('hafas_trips', static function(Blueprint $table) {
//Then make the columns not nullable
$table->unsignedBigInteger('origin_id')->nullable(false)->change();
$table->unsignedBigInteger('destination_id')->nullable(false)->change();
});
}

public function down(): void {
Schema::table('hafas_trips', static function(Blueprint $table) {
$table->unsignedBigInteger('origin')->nullable()->after('origin_id');
$table->unsignedBigInteger('destination')->nullable()->after('destination_id');

$table->foreign('origin')->references('ibnr')->on('train_stations');
$table->foreign('destination')->references('ibnr')->on('train_stations');
});

DB::table('hafas_trips')->update([
'origin' => DB::raw('(SELECT ibnr FROM train_stations WHERE id = hafas_trips.origin_id)'),
'destination' => DB::raw('(SELECT ibnr FROM train_stations WHERE id = hafas_trips.destination_id)'),
]);

Schema::table('hafas_trips', static function(Blueprint $table) {
$table->dropForeign(['origin_id']);
$table->dropForeign(['destination_id']);

$table->dropColumn('origin_id');
$table->dropColumn('destination_id');
});

Schema::table('hafas_trips', static function(Blueprint $table) {
$table->unsignedBigInteger('origin')->nullable(false)->change();
$table->unsignedBigInteger('destination')->nullable(false)->change();
});
}
};

0 comments on commit 1047f57

Please sign in to comment.