diff --git a/app/Database/seeds/settings.yml b/app/Database/seeds/settings.yml
index eea0e228..606bc67b 100644
--- a/app/Database/seeds/settings.yml
+++ b/app/Database/seeds/settings.yml
@@ -159,6 +159,13 @@
options: ''
type: string
description: 'Your SimBrief API key'
+- key: simbrief.only_bids
+ name: 'Only allow for bids'
+ group: simbrief
+ value: true
+ options: ''
+ type: boolean
+ description: 'Only allow briefs to be created for bidded flights'
- key: simbrief.expire_days
name: 'SimBrief Expire Time'
group: simbrief
diff --git a/app/Http/Controllers/Frontend/FlightController.php b/app/Http/Controllers/Frontend/FlightController.php
index 66fc542d..b0c3bb4a 100644
--- a/app/Http/Controllers/Frontend/FlightController.php
+++ b/app/Http/Controllers/Frontend/FlightController.php
@@ -9,11 +9,12 @@ use App\Repositories\AirportRepository;
use App\Repositories\Criteria\WhereCriteria;
use App\Repositories\FlightRepository;
use App\Repositories\SubfleetRepository;
+use App\Repositories\UserRepository;
use App\Services\GeoService;
-use Flash;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Log;
+use Laracasts\Flash\Flash;
use Prettus\Repository\Criteria\RequestCriteria;
use Prettus\Repository\Exceptions\RepositoryException;
@@ -24,6 +25,7 @@ class FlightController extends Controller
private $flightRepo;
private $subfleetRepo;
private $geoSvc;
+ private $userRepo;
/**
* @param AirlineRepository $airlineRepo
@@ -31,19 +33,22 @@ class FlightController extends Controller
* @param FlightRepository $flightRepo
* @param GeoService $geoSvc
* @param SubfleetRepository $subfleetRepo
+ * @param UserRepository $userRepo
*/
public function __construct(
AirlineRepository $airlineRepo,
AirportRepository $airportRepo,
FlightRepository $flightRepo,
GeoService $geoSvc,
- SubfleetRepository $subfleetRepo
+ SubfleetRepository $subfleetRepo,
+ UserRepository $userRepo
) {
$this->airlineRepo = $airlineRepo;
$this->airportRepo = $airportRepo;
$this->flightRepo = $flightRepo;
$this->geoSvc = $geoSvc;
$this->subfleetRepo = $subfleetRepo;
+ $this->userRepo = $userRepo;
}
/**
@@ -113,6 +118,7 @@ class FlightController extends Controller
'dep_icao' => $request->input('dep_icao'),
'subfleet_id' => $request->input('subfleet_id'),
'simbrief' => !empty(setting('simbrief.api_key')),
+ 'simbrief_bids' => setting('simbrief.only_bids'),
]);
}
@@ -125,19 +131,25 @@ class FlightController extends Controller
*/
public function bids(Request $request)
{
- $user = Auth::user();
+ $user = $this->userRepo
+ ->with(['bids', 'bids.flight'])
+ ->find(Auth::user()->id);
- $flights = $user->flights()->paginate();
- $saved_flights = $flights->pluck('id')->toArray();
+ $flights = collect();
+ $saved_flights = [];
+ foreach ($user->bids as $bid) {
+ $flights->add($bid->flight);
+ $saved_flights[] = $bid->flight->id;
+ }
- return view('flights.index', [
- 'title' => trans_choice('flights.mybid', 2),
- 'airlines' => $this->airlineRepo->selectBoxList(true),
- 'airports' => $this->airportRepo->selectBoxList(true),
- 'flights' => $flights,
- 'saved' => $saved_flights,
- 'subfleets' => $this->subfleetRepo->selectBoxList(true),
- 'simbrief' => !empty(setting('simbrief.api_key')),
+ return view('flights.bids', [
+ 'airlines' => $this->airlineRepo->selectBoxList(true),
+ 'airports' => $this->airportRepo->selectBoxList(true),
+ 'flights' => $flights,
+ 'saved' => $saved_flights,
+ 'subfleets' => $this->subfleetRepo->selectBoxList(true),
+ 'simbrief' => !empty(setting('simbrief.api_key')),
+ 'simbrief_bids' => setting('simbrief.only_bids'),
]);
}
diff --git a/app/Models/SimBriefXML.php b/app/Models/SimBriefXML.php
index 3ed1b00a..c95d29fb 100644
--- a/app/Models/SimBriefXML.php
+++ b/app/Models/SimBriefXML.php
@@ -26,6 +26,21 @@ class SimBriefXML extends SimpleXMLElement
return str_pad($fl, 3, '0', STR_PAD_LEFT);
}
+ /**
+ * Return the URL to the vmsACARS flight plan file
+ *
+ * @return string|null
+ */
+ public function getAcarsXmlUrl()
+ {
+ if (!empty($this->fms_downloads->vms)) {
+ $base_url = $this->fms_downloads->directory;
+ return $base_url.$this->fms_downloads->vms->link;
+ }
+
+ return null;
+ }
+
/**
* Retrieve all of the flightplans
*
diff --git a/app/Services/SimBriefService.php b/app/Services/SimBriefService.php
index 37aa65d5..c47191e8 100644
--- a/app/Services/SimBriefService.php
+++ b/app/Services/SimBriefService.php
@@ -7,6 +7,7 @@ use App\Models\Acars;
use App\Models\Enums\AcarsType;
use App\Models\Pirep;
use App\Models\SimBrief;
+use App\Models\SimBriefXML;
use Carbon\Carbon;
use GuzzleHttp\Client as GuzzleClient;
use GuzzleHttp\Exception\GuzzleException;
@@ -31,7 +32,7 @@ class SimBriefService extends Service
*
* @return SimBrief|null
*/
- public function checkForOfp(string $user_id, string $ofp_id, string $flight_id): SimBrief
+ public function checkForOfp(string $user_id, string $ofp_id, string $flight_id)
{
$uri = str_replace('{id}', $ofp_id, config('phpvms.simbrief_url'));
@@ -52,20 +53,27 @@ class SimBriefService extends Service
$body = $response->getBody()->getContents();
+ /** @var SimBriefXML $ofp */
+ $ofp = simplexml_load_string($body, SimBriefXML::class);
+
$attrs = [
'user_id' => $user_id,
'flight_id' => $flight_id,
- 'ofp_xml' => $body,
+ 'ofp_xml' => $ofp->asXML(),
];
- // TODO: Retrieve the ACARS XML and store that. For now, replace the doctype
+ // Try to download the XML file for ACARS. If it doesn't work, try to modify the main OFP
+ $acars_xml = $this->getAcarsOFP($ofp);
+ if (empty($acars_xml)) {
+ $new_doctype = '';
+ $acars_xml = str_replace('', $new_doctype, $body);
+ $acars_xml = str_replace('', '', $acars_xml);
+ $acars_xml = str_replace("\n", '', $acars_xml);
- $new_doctype = '';
- $acars_xml = str_replace('', $new_doctype, $body);
- $acars_xml = str_replace('', '', $acars_xml);
- $acars_xml = str_replace("\n", '', $acars_xml);
-
- $attrs['acars_xml'] = simplexml_load_string($acars_xml)->asXML();
+ $attrs['acars_xml'] = simplexml_load_string($acars_xml)->asXML();
+ } else {
+ $attrs['acars_xml'] = $acars_xml->asXML();
+ }
// Save this into the Simbrief table, if it doesn't already exist
return SimBrief::updateOrCreate(
@@ -74,6 +82,38 @@ class SimBriefService extends Service
);
}
+ /**
+ * @param \App\Models\SimBriefXML $ofp
+ *
+ * @return \SimpleXMLElement|null
+ */
+ public function getAcarsOFP(SimBriefXML $ofp)
+ {
+ $url = $ofp->getAcarsXmlUrl();
+ if (empty($url)) {
+ return null;
+ }
+
+ $opts = [
+ 'connect_timeout' => 2, // wait two seconds by default
+ 'allow_redirects' => true,
+ ];
+
+ try {
+ $response = $this->httpClient->request('GET', $url, $opts);
+ if ($response->getStatusCode() !== 200) {
+ return null;
+ }
+ } catch (GuzzleException $e) {
+ Log::error('Simbrief HTTP Error: '.$e->getMessage());
+ dd($e);
+ return null;
+ }
+
+ $body = $response->getBody()->getContents();
+ return simplexml_load_string($body);
+ }
+
/**
* Create a prefiled PIREP from a given brief.
*
diff --git a/resources/lang/en/flights.php b/resources/lang/en/flights.php
index cf6afbbe..92fb7236 100644
--- a/resources/lang/en/flights.php
+++ b/resources/lang/en/flights.php
@@ -6,7 +6,7 @@ return [
'flighttype' => 'Flight Type',
'flighthours' => 'Flight Hours',
'route' => 'Route',
- 'mybid' => 'My Bid|My Bids',
+ 'mybid' => 'My Bids',
'search' => 'Search',
'addremovebid' => 'Add/Remove Bid',
'bidremoved' => 'Your bid was removed.',
diff --git a/resources/lang/es/flights.php b/resources/lang/es/flights.php
index d4393879..792eaf66 100644
--- a/resources/lang/es/flights.php
+++ b/resources/lang/es/flights.php
@@ -6,7 +6,7 @@ return [
'flighttype' => 'Tipo de vuelo',
'flighthours' => 'Horas de vuelo',
'route' => 'Ruta',
- 'mybid' => 'Mi reserva|Mis reservas',
+ 'mybid' => 'Mis reservas',
'search' => 'Buscar',
'addremovebid' => 'Añadir/Quitar reserva',
'bidremoved' => 'Tu reserva ha sido eliminada.',
diff --git a/resources/lang/it/flights.php b/resources/lang/it/flights.php
index 2ee71cd2..986e6377 100644
--- a/resources/lang/it/flights.php
+++ b/resources/lang/it/flights.php
@@ -6,7 +6,7 @@ return [
'flighttype' => 'Tipo di Volo',
'flighthours' => 'Ore di Volo',
'route' => 'Rotta',
- 'mybid' => 'Mia prenotazione|Mie Prenotazioni',
+ 'mybid' => 'Mie Prenotazioni',
'addremovebid' => 'Aggiungi/Rimuovi Prenotazione',
'bidremoved' => 'La tua prenotazione è stata rimossa.',
'bidadded' => 'La tua prenotazione è stata aggiunta.',
diff --git a/resources/views/layouts/default/flights/bids.blade.php b/resources/views/layouts/default/flights/bids.blade.php
new file mode 100644
index 00000000..e5625b1e
--- /dev/null
+++ b/resources/views/layouts/default/flights/bids.blade.php
@@ -0,0 +1,15 @@
+@extends('app')
+@section('title', __('flights.mybid'))
+
+@section('content')
+
+ @include('flash::message')
+
+
{{ __('flights.mybid') }}
+ @include('flights.table')
+
+
+@endsection
+
+@include('flights.scripts')
+
diff --git a/resources/views/layouts/default/flights/index.blade.php b/resources/views/layouts/default/flights/index.blade.php
index c93b9ba5..46dd4860 100644
--- a/resources/views/layouts/default/flights/index.blade.php
+++ b/resources/views/layouts/default/flights/index.blade.php
@@ -5,7 +5,7 @@
@include('flash::message')
-
{{ $title ?? trans_choice('common.flight', 2) }}
+ {{ trans_choice('common.flight', 2) }}
@include('flights.table')
diff --git a/resources/views/layouts/default/flights/simbrief_form.blade.php b/resources/views/layouts/default/flights/simbrief_form.blade.php
index 9607876a..25fc0e96 100644
--- a/resources/views/layouts/default/flights/simbrief_form.blade.php
+++ b/resources/views/layouts/default/flights/simbrief_form.blade.php
@@ -39,8 +39,115 @@
diff --git a/resources/views/layouts/default/flights/table.blade.php b/resources/views/layouts/default/flights/table.blade.php
index 0a179809..c2803195 100644
--- a/resources/views/layouts/default/flights/table.blade.php
+++ b/resources/views/layouts/default/flights/table.blade.php
@@ -71,10 +71,12 @@
@if ($simbrief !== false)
-
- Create SimBrief Flight Plan
-
+ @if ($simbrief_bids === false || ($simbrief_bids === true && in_array($flight->id, $saved, true)))
+
+ Create SimBrief Flight Plan
+
+ @endif
@endif
'OMDB',
]);
- $this->mockXmlResponse('briefing.xml');
+ $this->mockXmlResponse([
+ 'simbrief/briefing.xml',
+ 'simbrief/acars_briefing.xml',
+ ]);
/** @var SimBriefService $sb */
$sb = app(SimBriefService::class);
@@ -44,7 +47,7 @@ class SimBriefTest extends TestCase
// Spot check reading of the files
$files = $briefing->files;
- $this->assertEquals(45, $files->count());
+ $this->assertEquals(47, $files->count());
$this->assertEquals(
'http://www.simbrief.com/ofp/flightplans/OMAAOMDB_PDF_1584226092.pdf',
$files->firstWhere('name', 'PDF Document')['url']
diff --git a/tests/TestCase.php b/tests/TestCase.php
index 5a97d530..a08caa78 100755
--- a/tests/TestCase.php
+++ b/tests/TestCase.php
@@ -132,19 +132,22 @@ class TestCase extends Illuminate\Foundation\Testing\TestCase
/**
* Return a mock Guzzle Client with a response loaded from $mockFile
*
- * @param $mockFile
+ * @param array|string $files
*/
- public function mockGuzzleClient($mockFile): void
+ public function mockGuzzleClient($files): void
{
- $mock = new MockHandler([
- new Response(
- 200,
- [
- 'Content-Type' => 'application/json; charset=utf-8',
- ],
- $this->readDataFile($mockFile)
- ),
- ]);
+ if (!is_array($files)) {
+ $files = [$files];
+ }
+
+ $responses = [];
+ foreach ($files as $file) {
+ $responses[] = new Response(200, [
+ 'Content-Type' => 'application/json; charset=utf-8',
+ ], $this->readDataFile($file));
+ }
+
+ $mock = new MockHandler($responses);
$handler = HandlerStack::create($mock);
$guzzleClient = new Client(['handler' => $handler]);
@@ -152,19 +155,22 @@ class TestCase extends Illuminate\Foundation\Testing\TestCase
}
/**
- * @param string $filename
+ * @param array|string $files The filename or files to respond with
*/
- public function mockXmlResponse($filename)
+ public function mockXmlResponse($files)
{
- $mock = new MockHandler([
- new Response(
- 200,
- [
- 'Content-Type' => 'text/xml',
- ],
- $this->readDataFile($filename)
- ),
- ]);
+ if (!is_array($files)) {
+ $files = [$files];
+ }
+
+ $responses = [];
+ foreach ($files as $file) {
+ $responses[] = new Response(200, [
+ 'Content-Type' => 'text/xml',
+ ], $this->readDataFile($file));
+ }
+
+ $mock = new MockHandler($responses);
$handler = HandlerStack::create($mock);
$guzzleClient = new Client(['handler' => $handler]);
diff --git a/tests/data/simbrief/acars_briefing.xml b/tests/data/simbrief/acars_briefing.xml
new file mode 100644
index 00000000..aa62dd9b
--- /dev/null
+++ b/tests/data/simbrief/acars_briefing.xml
@@ -0,0 +1,475 @@
+
+
+
+ 19722791
+ 120867
+ 1585313544
+ lido2
+ 2001
+ lbs
+
+
+ 1
+ VMS
+ 99
+ 0
+ PAYLOAD/CARGO LIMITED BY MLW
+
+ 1
+ CI5
+ 250/300/78
+ 78/300/250
+ CI0
+ RES
+ 5
+ 23000
+ MKJP/0230
+ 11
+ 56792
+ 12
+ 064
+ 018
+ 273
+ 319
+ 307
+ 5723
+ 388
+ .63
+ 171
+ LEXUV3 KEMBO G633 NALRO GUBEL3
+ LEXUV3 KEMBO G633 NALRO GUBEL3
+ LEXUV3 KEMBO G633 NALRO GUBEL3
+
+
+ MKJP
+ KIN
+
+ 18
+ 17.935556
+ -76.787500
+ NORMAN MANLEY INTL
+ 12
+
+
+ MWCR
+ GCM
+
+ 8
+ 19.292781
+ -81.357767
+ ROBERTS INTL
+ 08
+
+
+ MKJS
+ MBJ
+
+ 4
+ 18.503669
+ -77.913389
+ SANGSTER INTL
+ 07
+ 31000
+ 232
+ 201
+ 233
+ 103
+ 109
+ 411
+ 410
+ M001
+ 018
+ 018
+ 57000
+ P12
+ 2575
+ 4302
+ NALRO2 NALRO DCT OTEKO DCT IMONI OMAXI5
+ NALRO2 NALRO DCT OTEKO DCT IMONI OMAXI5
+
+
+
+
+
+ UKIMO
+ UKIMO
+ wpt
+ 17.918556
+ -76.743300
+ CLB
+ LEXUV3
+ 1
+ 5
+ 112
+ 119
+ 111
+ 118
+ 4900
+
+
+ PEMPE
+ PEMPE
+ wpt
+ 17.809956
+ -76.789128
+ CLB
+ LEXUV3
+ 1
+ 7
+ 201
+ 210
+ 199
+ 207
+ 10800
+
+
+ LEXUV
+ LEXUV
+ wpt
+ 17.853819
+ -76.902525
+ CLB
+ LEXUV3
+ 1
+ 7
+ 292
+ 300
+ 293
+ 301
+ 14200
+
+
+ KEMBO
+ KEMBO
+ wpt
+ 18.218889
+ -77.354722
+ CLB
+ LEXUV3
+ 0
+ 34
+ 310
+ 318
+ 311
+ 319
+ 22200
+
+
+ TOC
+ TOP OF CLIMB
+ ltlg
+ 18.288425
+ -77.494553
+ CLB
+ G633
+ 0
+ 9
+ 297
+ 305
+ 298
+ 306
+ 23000
+
+
+ SIA
+ SANGSTER
+ vor
+ 18.501047
+ -77.924100
+ CRZ
+ G633
+ 0
+ 28
+ 297
+ 305
+ 298
+ 305
+ 23000
+
+
+ PETSI
+ PETSI
+ wpt
+ 18.660278
+ -78.595833
+ CRZ
+ G633
+ 0
+ 39
+ 284
+ 291
+ 285
+ 292
+ 23000
+
+
+ FROST
+ FROST
+ wpt
+ 18.756944
+ -79.009167
+ CRZ
+ G633
+ 0
+ 24
+ 283
+ 291
+ 284
+ 291
+ 23000
+
+
+ OTEKO
+ OTEKO
+ wpt
+ 18.870278
+ -79.500000
+ CRZ
+ G633
+ 0
+ 29
+ 283
+ 290
+ 285
+ 292
+ 23000
+
+
+ NALRO
+ NALRO
+ wpt
+ 19.030822
+ -80.206147
+ CRZ
+ G633
+ 0
+ 41
+ 283
+ 290
+ 285
+ 291
+ 23000
+
+
+ TOD
+ TOP OF DESCENT
+ ltlg
+ 19.126848
+ -80.634858
+ CRZ
+ GUBEL3
+ 1
+ 25
+ 283
+ 289
+ 286
+ 292
+ 23000
+
+
+ D107Q
+ D107Q
+ wpt
+ 19.225436
+ -81.080228
+ DSC
+ GUBEL3
+ 1
+ 26
+ 283
+ 288
+ 285
+ 290
+ 10500
+
+
+ D080O
+ D080O
+ wpt
+ 19.350150
+ -81.115561
+ DSC
+ GUBEL3
+ 1
+ 8
+ 345
+ 350
+ 348
+ 353
+ 6700
+
+
+ GUBEL
+ GUBEL
+ wpt
+ 19.338075
+ -81.166667
+ DSC
+ GUBEL3
+ 1
+ 3
+ 255
+ 261
+ 255
+ 260
+ 5300
+
+
+ MWCR
+ ROBERTS INTL
+ apt
+ 19.292781
+ -81.357767
+ DSC
+ GUBEL3
+ 1
+ 34
+ 255
+ 261
+ 255
+ 260
+ 2500
+
+
+
+ (FPL-VMS99-IS
+-A320/M-SDE3FGHIRWY/LB1
+-MKJP1230
+-N0388F230 LEXUV3 KEMBO G633 NALRO GUBEL3
+-MWCR0100 MKJS
+-PBN/A1B1C1D1O1S1 DOF/140101 REG/N320SB OPR/VMS PER/C RMK/TCAS)
+ N0388F230 LEXUV3 KEMBO G633 NALRO GUBEL3
+ N0388F230 LEXUV3 KEMBO G633 NALRO GUBEL3
+ VMS99
+ 0388
+ N
+ 230
+ F
+ PBN/A1B1C1D1O1S1 DOF/140101 REG/N320SB OPR/VMS PER/C RMK/TCAS
+ MKJK
+ MKJK
+ MKJK
+
+
+
+
+ A320
+ 320
+ A320-200
+ N320SB
+ 205
+
+ M-SDE3FGHIRWY/LB1
+ 180
+ 1
+
+
+ 220
+ 5723
+ 1411
+ 4302
+ 3967
+ 0
+ 0
+ 15403
+ 15403
+ 15623
+ 9900
+ 5643
+ 42600
+
+
+ 3651
+ 7620
+ 1388579400
+ 1388579700
+ 1388587320
+ 1388587500
+ 8100
+ 1388579400
+ 1388579700
+ 1388583351
+ 1388583531
+ 4131
+ -5
+ -5
+ 300
+ 180
+ 2700
+ 10496
+ 900
+ 0
+ 0
+
+
+ 96518
+ 171
+ 230
+ 0
+ 39307
+ 135825
+ 137789
+ 151228
+ 151228
+ 171961
+ L
+ 145505
+ 145505
+ 151448
+
+
+ VMS
+ 99
+ A320
+ MKJP
+ MWCR
+ 1388534400
+ 43200
+ 1800
+ LEXUV3 KEMBO G633 NALRO GUBEL3
+ 7200
+ 900
+
+
+
+ auto
+ MKJS
+
+ NABEEL SHAHZAD
+ 120867
+ 1
+ auto
+ 0
+ auto
+ 45
+ auto
+ auto
+ auto
+ auto
+ auto
+ auto
+ auto
+ auto
+ AUTO
+ lido
+ 1
+ 1
+ 0
+ 1
+ 1
+ 1
+ 0
+ 1
+
+
+
+
+
+
+
+
+
+ false
+
+
+
diff --git a/tests/data/briefing.xml b/tests/data/simbrief/briefing.xml
similarity index 99%
rename from tests/data/briefing.xml
rename to tests/data/simbrief/briefing.xml
index 16387d9d..3c6359d5 100644
--- a/tests/data/briefing.xml
+++ b/tests/data/simbrief/briefing.xml
@@ -4277,6 +4277,10 @@ NIL
X-Plane 9/10
OMAAOMDB_XP9_1584226092.fms
+
+ phpVMS ACARS
+ MKJPMWCR_VMS_1585313544.xml
+
http://www.simbrief.com/ofp/flightplans/
@@ -4460,6 +4464,10 @@ NIL
X-Plane 9/10
OMAAOMDB_XP9_1584226092.fms
+
+ phpVMS ACARS
+ MKJPMWCR_VMS_1585313544.xml
+
http://www.simbrief.com/ofp/uads/