aipp 1.0.0 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +2 -2
- data/CHANGELOG.md +17 -1
- data/README.md +269 -150
- data/exe/aip2aixm +2 -8
- data/exe/aip2ofmx +2 -8
- data/exe/notam2aixm +5 -0
- data/exe/notam2ofmx +5 -0
- data/lib/aipp/aip/README.md +10 -0
- data/lib/aipp/aip/executable.rb +40 -0
- data/lib/aipp/aip/parser.rb +9 -0
- data/lib/aipp/aip/runner.rb +85 -0
- data/lib/aipp/border.rb +2 -2
- data/lib/aipp/debugger.rb +14 -19
- data/lib/aipp/downloader/file.rb +57 -0
- data/lib/aipp/downloader/graphql.rb +29 -0
- data/lib/aipp/downloader/http.rb +48 -0
- data/lib/aipp/downloader.rb +78 -29
- data/lib/aipp/environment.rb +88 -0
- data/lib/aipp/executable.rb +36 -53
- data/lib/aipp/notam/README.md +25 -0
- data/lib/aipp/notam/executable.rb +27 -0
- data/lib/aipp/notam/parser.rb +9 -0
- data/lib/aipp/notam/runner.rb +28 -0
- data/lib/aipp/parser.rb +133 -160
- data/lib/aipp/patcher.rb +4 -5
- data/lib/aipp/regions/LF/README.md +6 -2
- data/lib/aipp/regions/LF/aip/aerodromes.rb +220 -0
- data/lib/aipp/regions/LF/aip/d_p_r_airspaces.rb +53 -0
- data/lib/aipp/regions/LF/aip/dangerous_activities.rb +48 -0
- data/lib/aipp/regions/LF/aip/designated_points.rb +44 -0
- data/lib/aipp/regions/LF/aip/helipads.rb +119 -0
- data/lib/aipp/regions/LF/aip/navigational_aids.rb +82 -0
- data/lib/aipp/regions/LF/aip/obstacles.rb +150 -0
- data/lib/aipp/regions/LF/aip/serviced_airspaces.rb +67 -0
- data/lib/aipp/regions/LF/aip/services.rb +169 -0
- data/lib/aipp/regions/LF/fixtures/aerodromes.yml +2 -2
- data/lib/aipp/regions/LF/helpers/base.rb +32 -32
- data/lib/aipp/regions/LS/README.md +59 -0
- data/lib/aipp/regions/LS/helpers/base.rb +111 -0
- data/lib/aipp/regions/LS/notam/ENR.rb +173 -0
- data/lib/aipp/runner.rb +152 -0
- data/lib/aipp/version.rb +1 -1
- data/lib/aipp.rb +30 -11
- data/lib/core_ext/array.rb +13 -0
- data/lib/core_ext/nokogiri.rb +56 -8
- data/lib/core_ext/string.rb +63 -1
- data.tar.gz.sig +0 -0
- metadata +115 -64
- metadata.gz.sig +0 -0
- data/lib/aipp/aip.rb +0 -166
- data/lib/aipp/regions/LF/aerodromes.rb +0 -223
- data/lib/aipp/regions/LF/d_p_r_airspaces.rb +0 -56
- data/lib/aipp/regions/LF/dangerous_activities.rb +0 -49
- data/lib/aipp/regions/LF/designated_points.rb +0 -47
- data/lib/aipp/regions/LF/helipads.rb +0 -122
- data/lib/aipp/regions/LF/navigational_aids.rb +0 -85
- data/lib/aipp/regions/LF/obstacles.rb +0 -153
- data/lib/aipp/regions/LF/serviced_airspaces.rb +0 -70
- data/lib/aipp/regions/LF/services.rb +0 -172
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: aipp
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 2.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Sven Schwyn
|
@@ -10,27 +10,26 @@ bindir: exe
|
|
10
10
|
cert_chain:
|
11
11
|
- |
|
12
12
|
-----BEGIN CERTIFICATE-----
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
5JcY2h7owdMxXIvgk1oakgldFJc=
|
13
|
+
MIIDODCCAiCgAwIBAgIBATANBgkqhkiG9w0BAQsFADAjMSEwHwYDVQQDDBhydWJ5
|
14
|
+
L0RDPWJpdGNldGVyYS9EQz1jb20wHhcNMjIxMTA2MTIzNjUwWhcNMjMxMTA2MTIz
|
15
|
+
NjUwWjAjMSEwHwYDVQQDDBhydWJ5L0RDPWJpdGNldGVyYS9EQz1jb20wggEiMA0G
|
16
|
+
CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDcLg+IHjXYaUlTSU7R235lQKD8ZhEe
|
17
|
+
KMhoGlSUonZ/zo1OT3KXcqTCP1iMX743xYs6upEGALCWWwq+nxvlDdnWRjF3AAv7
|
18
|
+
ikC+Z2BEowjyeCCT/0gvn4ohKcR0JOzzRaIlFUVInlGSAHx2QHZ2N8ntf54lu7nd
|
19
|
+
L8CiDK8rClsY4JBNGOgH9UC81f+m61UUQuTLxyM2CXfAYkj/sGNTvFRJcNX+nfdC
|
20
|
+
hM9r2kH1+7wsa8yG7wJ2IkrzNACD8v84oE6qVusN8OLEMUI/NaEPVPbw2LUM149H
|
21
|
+
PVa0i729A4IhroNnFNmw4wOC93ARNbM1+LW36PLMmKjKudf5Exg8VmDVAgMBAAGj
|
22
|
+
dzB1MAkGA1UdEwQCMAAwCwYDVR0PBAQDAgSwMB0GA1UdDgQWBBSfK8MtR62mQ6oN
|
23
|
+
yoX/VKJzFjLSVDAdBgNVHREEFjAUgRJydWJ5QGJpdGNldGVyYS5jb20wHQYDVR0S
|
24
|
+
BBYwFIEScnVieUBiaXRjZXRlcmEuY29tMA0GCSqGSIb3DQEBCwUAA4IBAQAYG2na
|
25
|
+
ye8OE2DANQIFM/xDos/E4DaPWCJjX5xvFKNKHMCeQYPeZvLICCwyw2paE7Otwk6p
|
26
|
+
uvbg2Ks5ykXsbk5i6vxDoeeOLvmxCqI6m+tHb8v7VZtmwRJm8so0eSX0WvTaKnIf
|
27
|
+
CAn1bVUggczVdNoBXw9WAILKyw9bvh3Ft740XZrR74sd+m2pGwjCaM8hzLvrVbGP
|
28
|
+
DyYhlBeRWyQKQ0WDIsiTSRhzK8HwSTUWjvPwx7SEdIU/HZgyrk0ETObKPakVu6bH
|
29
|
+
kAyiRqgxF4dJviwtqI7mZIomWL63+kXLgjOjMe1SHxfIPo/0ji6+r1p4KYa7o41v
|
30
|
+
fwIwU1MKlFBdsjkd
|
32
31
|
-----END CERTIFICATE-----
|
33
|
-
date: 2022-
|
32
|
+
date: 2022-11-20 00:00:00.000000000 Z
|
34
33
|
dependencies:
|
35
34
|
- !ruby/object:Gem::Dependency
|
36
35
|
name: airac
|
@@ -39,6 +38,9 @@ dependencies:
|
|
39
38
|
- - "~>"
|
40
39
|
- !ruby/object:Gem::Version
|
41
40
|
version: '1.0'
|
41
|
+
- - ">="
|
42
|
+
- !ruby/object:Gem::Version
|
43
|
+
version: 1.0.1
|
42
44
|
type: :runtime
|
43
45
|
prerelease: false
|
44
46
|
version_requirements: !ruby/object:Gem::Requirement
|
@@ -46,11 +48,37 @@ dependencies:
|
|
46
48
|
- - "~>"
|
47
49
|
- !ruby/object:Gem::Version
|
48
50
|
version: '1.0'
|
51
|
+
- - ">="
|
52
|
+
- !ruby/object:Gem::Version
|
53
|
+
version: 1.0.1
|
49
54
|
- !ruby/object:Gem::Dependency
|
50
55
|
name: aixm
|
51
56
|
requirement: !ruby/object:Gem::Requirement
|
52
57
|
requirements:
|
53
58
|
- - "~>"
|
59
|
+
- !ruby/object:Gem::Version
|
60
|
+
version: '1'
|
61
|
+
- - ">="
|
62
|
+
- !ruby/object:Gem::Version
|
63
|
+
version: 1.3.2
|
64
|
+
type: :runtime
|
65
|
+
prerelease: false
|
66
|
+
version_requirements: !ruby/object:Gem::Requirement
|
67
|
+
requirements:
|
68
|
+
- - "~>"
|
69
|
+
- !ruby/object:Gem::Version
|
70
|
+
version: '1'
|
71
|
+
- - ">="
|
72
|
+
- !ruby/object:Gem::Version
|
73
|
+
version: 1.3.2
|
74
|
+
- !ruby/object:Gem::Dependency
|
75
|
+
name: notam
|
76
|
+
requirement: !ruby/object:Gem::Requirement
|
77
|
+
requirements:
|
78
|
+
- - "~>"
|
79
|
+
- !ruby/object:Gem::Version
|
80
|
+
version: '1'
|
81
|
+
- - ">="
|
54
82
|
- !ruby/object:Gem::Version
|
55
83
|
version: '1.1'
|
56
84
|
type: :runtime
|
@@ -58,6 +86,9 @@ dependencies:
|
|
58
86
|
version_requirements: !ruby/object:Gem::Requirement
|
59
87
|
requirements:
|
60
88
|
- - "~>"
|
89
|
+
- !ruby/object:Gem::Version
|
90
|
+
version: '1'
|
91
|
+
- - ">="
|
61
92
|
- !ruby/object:Gem::Version
|
62
93
|
version: '1.1'
|
63
94
|
- !ruby/object:Gem::Dependency
|
@@ -74,6 +105,34 @@ dependencies:
|
|
74
105
|
- - "~>"
|
75
106
|
- !ruby/object:Gem::Version
|
76
107
|
version: '7'
|
108
|
+
- !ruby/object:Gem::Dependency
|
109
|
+
name: excon
|
110
|
+
requirement: !ruby/object:Gem::Requirement
|
111
|
+
requirements:
|
112
|
+
- - "~>"
|
113
|
+
- !ruby/object:Gem::Version
|
114
|
+
version: '0'
|
115
|
+
type: :runtime
|
116
|
+
prerelease: false
|
117
|
+
version_requirements: !ruby/object:Gem::Requirement
|
118
|
+
requirements:
|
119
|
+
- - "~>"
|
120
|
+
- !ruby/object:Gem::Version
|
121
|
+
version: '0'
|
122
|
+
- !ruby/object:Gem::Dependency
|
123
|
+
name: graphql-client
|
124
|
+
requirement: !ruby/object:Gem::Requirement
|
125
|
+
requirements:
|
126
|
+
- - "~>"
|
127
|
+
- !ruby/object:Gem::Version
|
128
|
+
version: '0'
|
129
|
+
type: :runtime
|
130
|
+
prerelease: false
|
131
|
+
version_requirements: !ruby/object:Gem::Requirement
|
132
|
+
requirements:
|
133
|
+
- - "~>"
|
134
|
+
- !ruby/object:Gem::Version
|
135
|
+
version: '0'
|
77
136
|
- !ruby/object:Gem::Dependency
|
78
137
|
name: nokogiri
|
79
138
|
requirement: !ruby/object:Gem::Requirement
|
@@ -206,20 +265,6 @@ dependencies:
|
|
206
265
|
- - ">="
|
207
266
|
- !ruby/object:Gem::Version
|
208
267
|
version: '0'
|
209
|
-
- !ruby/object:Gem::Dependency
|
210
|
-
name: minitest-reporters
|
211
|
-
requirement: !ruby/object:Gem::Requirement
|
212
|
-
requirements:
|
213
|
-
- - ">="
|
214
|
-
- !ruby/object:Gem::Version
|
215
|
-
version: '0'
|
216
|
-
type: :development
|
217
|
-
prerelease: false
|
218
|
-
version_requirements: !ruby/object:Gem::Requirement
|
219
|
-
requirements:
|
220
|
-
- - ">="
|
221
|
-
- !ruby/object:Gem::Version
|
222
|
-
version: '0'
|
223
268
|
- !ruby/object:Gem::Dependency
|
224
269
|
name: minitest-sound
|
225
270
|
requirement: !ruby/object:Gem::Requirement
|
@@ -249,21 +294,7 @@ dependencies:
|
|
249
294
|
- !ruby/object:Gem::Version
|
250
295
|
version: '0'
|
251
296
|
- !ruby/object:Gem::Dependency
|
252
|
-
name:
|
253
|
-
requirement: !ruby/object:Gem::Requirement
|
254
|
-
requirements:
|
255
|
-
- - ">="
|
256
|
-
- !ruby/object:Gem::Version
|
257
|
-
version: '0'
|
258
|
-
type: :development
|
259
|
-
prerelease: false
|
260
|
-
version_requirements: !ruby/object:Gem::Requirement
|
261
|
-
requirements:
|
262
|
-
- - ">="
|
263
|
-
- !ruby/object:Gem::Version
|
264
|
-
version: '0'
|
265
|
-
- !ruby/object:Gem::Dependency
|
266
|
-
name: spy
|
297
|
+
name: guard
|
267
298
|
requirement: !ruby/object:Gem::Requirement
|
268
299
|
requirements:
|
269
300
|
- - ">="
|
@@ -277,7 +308,7 @@ dependencies:
|
|
277
308
|
- !ruby/object:Gem::Version
|
278
309
|
version: '0'
|
279
310
|
- !ruby/object:Gem::Dependency
|
280
|
-
name: guard
|
311
|
+
name: guard-minitest
|
281
312
|
requirement: !ruby/object:Gem::Requirement
|
282
313
|
requirements:
|
283
314
|
- - ">="
|
@@ -291,7 +322,7 @@ dependencies:
|
|
291
322
|
- !ruby/object:Gem::Version
|
292
323
|
version: '0'
|
293
324
|
- !ruby/object:Gem::Dependency
|
294
|
-
name:
|
325
|
+
name: yard
|
295
326
|
requirement: !ruby/object:Gem::Requirement
|
296
327
|
requirements:
|
297
328
|
- - ">="
|
@@ -313,6 +344,8 @@ email:
|
|
313
344
|
executables:
|
314
345
|
- aip2aixm
|
315
346
|
- aip2ofmx
|
347
|
+
- notam2aixm
|
348
|
+
- notam2ofmx
|
316
349
|
extensions: []
|
317
350
|
extra_rdoc_files:
|
318
351
|
- README.md
|
@@ -324,35 +357,53 @@ files:
|
|
324
357
|
- README.md
|
325
358
|
- exe/aip2aixm
|
326
359
|
- exe/aip2ofmx
|
360
|
+
- exe/notam2aixm
|
361
|
+
- exe/notam2ofmx
|
327
362
|
- lib/aipp.rb
|
328
|
-
- lib/aipp/aip.
|
363
|
+
- lib/aipp/aip/README.md
|
364
|
+
- lib/aipp/aip/executable.rb
|
365
|
+
- lib/aipp/aip/parser.rb
|
366
|
+
- lib/aipp/aip/runner.rb
|
329
367
|
- lib/aipp/border.rb
|
330
368
|
- lib/aipp/debugger.rb
|
331
369
|
- lib/aipp/downloader.rb
|
370
|
+
- lib/aipp/downloader/file.rb
|
371
|
+
- lib/aipp/downloader/graphql.rb
|
372
|
+
- lib/aipp/downloader/http.rb
|
373
|
+
- lib/aipp/environment.rb
|
332
374
|
- lib/aipp/executable.rb
|
375
|
+
- lib/aipp/notam/README.md
|
376
|
+
- lib/aipp/notam/executable.rb
|
377
|
+
- lib/aipp/notam/parser.rb
|
378
|
+
- lib/aipp/notam/runner.rb
|
333
379
|
- lib/aipp/parser.rb
|
334
380
|
- lib/aipp/patcher.rb
|
335
381
|
- lib/aipp/pdf.rb
|
336
382
|
- lib/aipp/regions/LF/README.md
|
337
|
-
- lib/aipp/regions/LF/aerodromes.rb
|
383
|
+
- lib/aipp/regions/LF/aip/aerodromes.rb
|
384
|
+
- lib/aipp/regions/LF/aip/d_p_r_airspaces.rb
|
385
|
+
- lib/aipp/regions/LF/aip/dangerous_activities.rb
|
386
|
+
- lib/aipp/regions/LF/aip/designated_points.rb
|
387
|
+
- lib/aipp/regions/LF/aip/helipads.rb
|
388
|
+
- lib/aipp/regions/LF/aip/navigational_aids.rb
|
389
|
+
- lib/aipp/regions/LF/aip/obstacles.rb
|
390
|
+
- lib/aipp/regions/LF/aip/serviced_airspaces.rb
|
391
|
+
- lib/aipp/regions/LF/aip/services.rb
|
338
392
|
- lib/aipp/regions/LF/borders/france_atlantic_coast.geojson
|
339
393
|
- lib/aipp/regions/LF/borders/france_atlantic_territorial_sea.geojson
|
340
394
|
- lib/aipp/regions/LF/borders/france_ecrins_national_park.geojson
|
341
395
|
- lib/aipp/regions/LF/borders/france_mediterranean_coast.geojson
|
342
|
-
- lib/aipp/regions/LF/d_p_r_airspaces.rb
|
343
|
-
- lib/aipp/regions/LF/dangerous_activities.rb
|
344
|
-
- lib/aipp/regions/LF/designated_points.rb
|
345
396
|
- lib/aipp/regions/LF/fixtures/aerodromes.yml
|
346
|
-
- lib/aipp/regions/LF/helipads.rb
|
347
397
|
- lib/aipp/regions/LF/helpers/base.rb
|
348
398
|
- lib/aipp/regions/LF/helpers/surface.rb
|
349
399
|
- lib/aipp/regions/LF/helpers/usage_limitation.rb
|
350
|
-
- lib/aipp/regions/
|
351
|
-
- lib/aipp/regions/
|
352
|
-
- lib/aipp/regions/
|
353
|
-
- lib/aipp/
|
400
|
+
- lib/aipp/regions/LS/README.md
|
401
|
+
- lib/aipp/regions/LS/helpers/base.rb
|
402
|
+
- lib/aipp/regions/LS/notam/ENR.rb
|
403
|
+
- lib/aipp/runner.rb
|
354
404
|
- lib/aipp/t_hash.rb
|
355
405
|
- lib/aipp/version.rb
|
406
|
+
- lib/core_ext/array.rb
|
356
407
|
- lib/core_ext/enumerable.rb
|
357
408
|
- lib/core_ext/hash.rb
|
358
409
|
- lib/core_ext/integer.rb
|
@@ -383,14 +434,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
383
434
|
requirements:
|
384
435
|
- - ">="
|
385
436
|
- !ruby/object:Gem::Version
|
386
|
-
version: 3.
|
437
|
+
version: 3.1.0
|
387
438
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
388
439
|
requirements:
|
389
440
|
- - ">="
|
390
441
|
- !ruby/object:Gem::Version
|
391
442
|
version: '0'
|
392
443
|
requirements: []
|
393
|
-
rubygems_version: 3.3.
|
444
|
+
rubygems_version: 3.3.26
|
394
445
|
signing_key:
|
395
446
|
specification_version: 4
|
396
447
|
summary: Parser for aeronautical information publications
|
metadata.gz.sig
CHANGED
Binary file
|
data/lib/aipp/aip.rb
DELETED
@@ -1,166 +0,0 @@
|
|
1
|
-
module AIPP
|
2
|
-
|
3
|
-
# @abstract
|
4
|
-
class AIP
|
5
|
-
extend Forwardable
|
6
|
-
include AIPP::Debugger
|
7
|
-
include AIPP::Patcher
|
8
|
-
|
9
|
-
DEPENDS = []
|
10
|
-
|
11
|
-
# @return [String] AIP name (equal to the parser file name without its
|
12
|
-
# file extension such as "ENR-2.1" implemented in the file "ENR-2.1.rb")
|
13
|
-
attr_reader :aip
|
14
|
-
|
15
|
-
# @return [String] AIP file as passed and possibly updated by `url_for`
|
16
|
-
attr_reader :aip_file
|
17
|
-
|
18
|
-
# @return [Object] Fixture read from YAML file
|
19
|
-
attr_reader :fixture
|
20
|
-
|
21
|
-
# @!method close
|
22
|
-
# @see AIPP::Downloader#close
|
23
|
-
def_delegator :@downloader, :close
|
24
|
-
|
25
|
-
# @!method config
|
26
|
-
# @see AIPP::Parser#config
|
27
|
-
# @!method options
|
28
|
-
# @see AIPP::Parser#options
|
29
|
-
# @!method borders
|
30
|
-
# @see AIPP::Parser#borders
|
31
|
-
# @!method cache
|
32
|
-
# @see AIPP::Parser#cache
|
33
|
-
def_delegators :@parser, :aixm, :config, :options, :borders, :cache
|
34
|
-
private :aixm
|
35
|
-
|
36
|
-
def initialize(aip:, downloader:, fixture:, parser:)
|
37
|
-
@aip, @downloader, @fixture, @parser = aip, downloader, fixture, parser
|
38
|
-
setup if respond_to? :setup
|
39
|
-
end
|
40
|
-
|
41
|
-
# @return [String]
|
42
|
-
def inspect
|
43
|
-
"#<AIPP::AIP #{aip}>"
|
44
|
-
end
|
45
|
-
|
46
|
-
# Read an AIP source file
|
47
|
-
#
|
48
|
-
# Read the cached source file if it exists in the source archive. Otherwise,
|
49
|
-
# download it from URL and cache it.
|
50
|
-
#
|
51
|
-
# An URL builder method +url_for(aip_file)+ must be implemented by the AIP
|
52
|
-
# parser definition (e.g. +ENR-2.1.rb+).
|
53
|
-
#
|
54
|
-
# @param aip_file [String] e.g. "ENR-2.1" or "AD-2.LFMV" (default: +aip+
|
55
|
-
# with section stripped e.g. "AD-1.3-2" -> "AD-1.3")
|
56
|
-
# @return [Nokogiri::XML::Document, Nokogiri::HTML5::Document,
|
57
|
-
# Roo::Spreadsheet, String] XML/HTML as Nokogiri document, XLSX/ODS/CSV
|
58
|
-
# as Roo document, PDF and TXT as String
|
59
|
-
def read(aip_file=nil)
|
60
|
-
@aip_file = aip_file || aip.remove(/(?<![A-Z])-\d+$/)
|
61
|
-
url = url_for(@aip_file) # may update aip_file string
|
62
|
-
@downloader.read(document: @aip_file, url: url)
|
63
|
-
end
|
64
|
-
|
65
|
-
# Add feature to AIXM
|
66
|
-
#
|
67
|
-
# @param feature [AIXM::Feature] e.g. airport or airspace
|
68
|
-
# @return [AIXM::Feature] added feature
|
69
|
-
def add(feature)
|
70
|
-
verbose_info "adding #{feature.inspect}"
|
71
|
-
aixm.add_feature feature
|
72
|
-
feature
|
73
|
-
end
|
74
|
-
|
75
|
-
# @!method find_by(klass, attributes={})
|
76
|
-
# Find objects of the given class and optionally with the given attribute
|
77
|
-
# values previously written to AIXM.
|
78
|
-
#
|
79
|
-
# @note This method is delegated to +AIXM::Association::Array+.
|
80
|
-
# @see https://www.rubydoc.info/gems/aixm/AIXM/Association/Array#find_by-instance_method
|
81
|
-
#
|
82
|
-
# @!method find(object)
|
83
|
-
# Find equal objects previously written to AIXM.
|
84
|
-
#
|
85
|
-
# @note This method is delegated to +AIXM::Association::Array+.
|
86
|
-
# @see https://www.rubydoc.info/gems/aixm/AIXM/Association/Array#find-instance_method
|
87
|
-
%i(find_by find).each do |method|
|
88
|
-
define_method method do |*args|
|
89
|
-
aixm.features.send(method, *args)
|
90
|
-
end
|
91
|
-
end
|
92
|
-
|
93
|
-
# @overload given(*objects)
|
94
|
-
# Return +objects+ unless at least one of them equals nil
|
95
|
-
#
|
96
|
-
# @example
|
97
|
-
# # Instead of this:
|
98
|
-
# first, last = unless ((first = expensive_first).nil? || (last = expensive_last).nil?)
|
99
|
-
# [first, last]
|
100
|
-
# end
|
101
|
-
#
|
102
|
-
# # Use the following:
|
103
|
-
# first, last = given(expensive_first, expensive_last)
|
104
|
-
#
|
105
|
-
# @param *objects [Array<Object>] any objects really
|
106
|
-
# @return [Object] nil if at least one of the objects is nil, given
|
107
|
-
# objects otherwise
|
108
|
-
#
|
109
|
-
# @overload given(*objects)
|
110
|
-
# Yield +objects+ unless at least one of them equals nil
|
111
|
-
#
|
112
|
-
# @example
|
113
|
-
# # Instead of this:
|
114
|
-
# name = unless ((first = expensive_first.nil? || (last = expensive_last.nil?)
|
115
|
-
# "#{first} #{last}"
|
116
|
-
# end
|
117
|
-
#
|
118
|
-
# # Use any of the following:
|
119
|
-
# name = given(expensive_first, expensive_last) { |f, l| "#{f} #{l}" }
|
120
|
-
# name = given(expensive_first, expensive_last) { "#{_1} #{_2}" }
|
121
|
-
#
|
122
|
-
# @param *objects [Array<Object>] any objects really
|
123
|
-
# @yield [Array<Object>] objects passed as parameter
|
124
|
-
# @return [Object] nil if at least one of the objects is nil, return of
|
125
|
-
# block otherwise
|
126
|
-
def given(*objects)
|
127
|
-
if objects.none?(&:nil?)
|
128
|
-
block_given? ? yield(*objects) : objects
|
129
|
-
end
|
130
|
-
end
|
131
|
-
|
132
|
-
# Build and optionally check a Markdown link
|
133
|
-
#
|
134
|
-
# @example
|
135
|
-
# options[:check_links] = false
|
136
|
-
# link_to('foo', 'https://bar.com/exists') # => "[foo](https://bar.com/exists)"
|
137
|
-
# link_to('foo', 'https://bar.com/not-found') # => "[foo](https://bar.com/not-found)"
|
138
|
-
# options[:check_links] = true
|
139
|
-
# link_to('foo', 'https://bar.com/exists') # => "[foo](https://bar.com/exists)"
|
140
|
-
# link_to('foo', 'https://bar.com/not-found') # => nil
|
141
|
-
#
|
142
|
-
# @params body [String] body text of the link
|
143
|
-
# @params url [String] URL of the link
|
144
|
-
# @return [String, nil] Markdown link
|
145
|
-
def link_to(body, url)
|
146
|
-
"[#{body}](#{url})" if !options[:check_links] || url_exists?(url)
|
147
|
-
end
|
148
|
-
|
149
|
-
private
|
150
|
-
|
151
|
-
def url_exists?(url)
|
152
|
-
uri = URI.parse(url)
|
153
|
-
Net::HTTP.new(uri.host, uri.port).tap do |request|
|
154
|
-
request.use_ssl = (uri.scheme == 'https')
|
155
|
-
path = uri.path.present? ? uri.path : '/'
|
156
|
-
result = request.request_head(path)
|
157
|
-
if result.kind_of? Net::HTTPRedirection
|
158
|
-
url_exist?(result['location'])
|
159
|
-
else
|
160
|
-
result.code == '200'
|
161
|
-
end
|
162
|
-
end
|
163
|
-
end
|
164
|
-
|
165
|
-
end
|
166
|
-
end
|
@@ -1,223 +0,0 @@
|
|
1
|
-
module AIPP
|
2
|
-
module LF
|
3
|
-
|
4
|
-
class Aerodromes < AIP
|
5
|
-
|
6
|
-
include AIPP::LF::Helpers::Base
|
7
|
-
include AIPP::LF::Helpers::UsageLimitation
|
8
|
-
include AIPP::LF::Helpers::Surface
|
9
|
-
|
10
|
-
APPROACH_LIGHTING_TYPES = {
|
11
|
-
'CAT I' => :cat_1,
|
12
|
-
'CAT II' => :cat_2,
|
13
|
-
'CAT III' => :cat_3,
|
14
|
-
'CAT II-III' => :cat_2_and_3
|
15
|
-
}.freeze
|
16
|
-
|
17
|
-
LIGHTING_POSITIONS = {
|
18
|
-
threshold: 'Thr',
|
19
|
-
touch_down_zone: 'Tdz',
|
20
|
-
center_line: 'Axe',
|
21
|
-
edge: 'Bord',
|
22
|
-
runway_end: 'Fin',
|
23
|
-
stopway_center_line: 'Swy'
|
24
|
-
}.freeze
|
25
|
-
|
26
|
-
LIGHTING_COLORS = {
|
27
|
-
'W' => :white,
|
28
|
-
'R' => :red,
|
29
|
-
'G' => :green,
|
30
|
-
'B' => :blue,
|
31
|
-
'Y' => :yellow
|
32
|
-
}.freeze
|
33
|
-
|
34
|
-
ICAO_LIGHTING_COLORS = {
|
35
|
-
center_line: :white,
|
36
|
-
edge: :white
|
37
|
-
}.freeze
|
38
|
-
|
39
|
-
def parse
|
40
|
-
cache.ad.css(%Q(Ad[lk^="[LF]"])).each do |ad_node|
|
41
|
-
# Build airport
|
42
|
-
next unless limitation_type = LIMITATION_TYPES.fetch(ad_node.(:AdStatut))
|
43
|
-
airport = AIXM.airport(
|
44
|
-
source: source(section: 'AD', position: ad_node.line),
|
45
|
-
organisation: organisation_lf,
|
46
|
-
id: id_from(ad_node.(:AdCode)),
|
47
|
-
name: ad_node.(:AdNomComplet),
|
48
|
-
xy: xy_from(ad_node.(:Geometrie))
|
49
|
-
).tap do |airport|
|
50
|
-
airport.meta = ad_node.attr('pk')
|
51
|
-
airport.z = given(ad_node.(:AdRefAltFt)) { AIXM.z(_1.to_i, :qnh) }
|
52
|
-
airport.declination = ad_node.(:AdMagVar)&.to_f
|
53
|
-
airport.add_usage_limitation(type: limitation_type.fetch(:limitation)) do |limitation|
|
54
|
-
limitation.remarks = limitation_type[:remarks]
|
55
|
-
[
|
56
|
-
(:scheduled if ad_node.(:TfcRegulier?)),
|
57
|
-
(:not_scheduled if ad_node.(:TfcNonRegulier?)),
|
58
|
-
(:private if ad_node.(:TfcPrive?)),
|
59
|
-
(:other unless ad_node.(:TfcRegulier?) || ad_node.(:TfcNonRegulier?) || ad_node.(:TfcPrive?))
|
60
|
-
].compact.each do |purpose|
|
61
|
-
limitation.add_condition do |condition|
|
62
|
-
condition.realm = limitation_type.fetch(:realm)
|
63
|
-
condition.origin = case
|
64
|
-
when ad_node.(:TfcIntl?) && ad_node.(:TfcNtl?) then :any
|
65
|
-
when ad_node.(:TfcIntl?) then :international
|
66
|
-
when ad_node.(:TfcNtl?) then :national
|
67
|
-
else :other
|
68
|
-
end
|
69
|
-
condition.rule = case
|
70
|
-
when ad_node.(:TfcIfr?) && ad_node.(:TfcVfr?) then :ifr_and_vfr
|
71
|
-
when ad_node.(:TfcIfr?) then :ifr
|
72
|
-
when ad_node.(:TfcVfr?) then :vfr
|
73
|
-
else
|
74
|
-
warn("falling back to VFR rule for `#{airport.id}'", severe: false)
|
75
|
-
:vfr
|
76
|
-
end
|
77
|
-
condition.purpose = purpose
|
78
|
-
end
|
79
|
-
end
|
80
|
-
end
|
81
|
-
# TODO: link to VAC once supported downstream
|
82
|
-
# # Link to VAC
|
83
|
-
# airport.remarks = [
|
84
|
-
# airport.remarks.to_s,
|
85
|
-
# link_to('VAC-AD', url_for("VAC-#{airport.id}"))
|
86
|
-
# ].join("\n")
|
87
|
-
cache.rwy.css(%Q(Rwy:has(Ad[pk="#{ad_node.attr(:pk)}"]))).each do |rwy_node|
|
88
|
-
add_runway_to(airport, rwy_node)
|
89
|
-
end
|
90
|
-
end
|
91
|
-
add airport
|
92
|
-
end
|
93
|
-
end
|
94
|
-
|
95
|
-
private
|
96
|
-
|
97
|
-
def id_from(content)
|
98
|
-
case content
|
99
|
-
when /^\d{2}$/ then 'LF00' + content # private aerodromes without official ID
|
100
|
-
else 'LF' + content
|
101
|
-
end
|
102
|
-
end
|
103
|
-
|
104
|
-
def add_runway_to(airport, rwy_node)
|
105
|
-
AIXM.runway(
|
106
|
-
name: rwy_node.(:Rwy)
|
107
|
-
).tap do |runway|
|
108
|
-
rwylgt_nodes = cache.rwylgt.css(%Q(RwyLgt:has(Rwy[pk="#{rwy_node.attr(:pk)}"])))
|
109
|
-
airport.add_runway(runway)
|
110
|
-
runway.dimensions = AIXM.r(AIXM.d(rwy_node.(:Longueur)&.to_i, :m), AIXM.d(rwy_node.(:Largeur)&.to_i, :m))
|
111
|
-
runway.surface = surface_from(rwy_node)
|
112
|
-
runway.forth.geographic_bearing = given(rwy_node.(:OrientationGeo)) { AIXM.a(_1.to_f) }
|
113
|
-
runway.forth.xy = given(rwy_node.(:LatThr1), rwy_node.(:LongThr1)) { AIXM.xy(lat: _1.to_f, long: _2.to_f) }
|
114
|
-
runway.forth.displaced_threshold = given(rwy_node.(:LatDThr1), rwy_node.(:LongDThr1)) { AIXM.xy(lat: _1.to_f, long: _2.to_f) }
|
115
|
-
runway.forth.z = given(rwy_node.(:AltFtDThr1)) { AIXM.z(_1.to_i, :qnh) }
|
116
|
-
runway.forth.z ||= given(rwy_node.(:AltFtThr1)) { AIXM.z(_1.to_i, :qnh) }
|
117
|
-
if rwylgt_node = rwylgt_nodes[0]
|
118
|
-
runway.forth.vasis = vasis_from(rwylgt_node)
|
119
|
-
given(approach_lighting_from(rwylgt_node)) { runway.forth.add_approach_lighting(_1) }
|
120
|
-
LIGHTING_POSITIONS.each_key do |position|
|
121
|
-
given(lighting_from(rwylgt_node, position)) { runway.forth.add_lighting(_1) }
|
122
|
-
end
|
123
|
-
end
|
124
|
-
if rwy_node.(:Rwy).match? '/'
|
125
|
-
runway.back.xy = given(rwy_node.(:LatThr2), rwy_node.(:LongThr2)) { AIXM.xy(lat: _1.to_f, long: _2.to_f) }
|
126
|
-
runway.back.displaced_threshold = given(rwy_node.(:LatDThr2), rwy_node.(:LongDThr2)) { AIXM.xy(lat: _1.to_f, long: _2.to_f) }
|
127
|
-
runway.back.z = given(rwy_node.(:AltFtDThr2)) { AIXM.z(_1.to_i, :qnh) }
|
128
|
-
runway.back.z ||= given(rwy_node.(:AltFtThr2)) { AIXM.z(_1.to_i, :qnh) }
|
129
|
-
if rwylgt_node = rwylgt_nodes[1]
|
130
|
-
runway.back.vasis = vasis_from(rwylgt_node)
|
131
|
-
given(approach_lighting_from(rwylgt_node)) { runway.back.add_approach_lighting(_1) }
|
132
|
-
LIGHTING_POSITIONS.each_key do |position|
|
133
|
-
given(lighting_from(rwylgt_node, position)) { runway.back.add_lighting(_1) }
|
134
|
-
end
|
135
|
-
end
|
136
|
-
end
|
137
|
-
end
|
138
|
-
end
|
139
|
-
|
140
|
-
def vasis_from(rwylgt_node)
|
141
|
-
if rwylgt_node.(:PapiVasis)
|
142
|
-
AIXM.vasis.tap do |vasis|
|
143
|
-
vasis.type = rwylgt_node.(:PapiVasis)
|
144
|
-
vasis.slope_angle = AIXM.a(rwylgt_node.(:PapiVasisPente).to_f)
|
145
|
-
vasis.meht = AIXM.z(rwylgt_node.(:MehtFt).to_i, :qfe)
|
146
|
-
end
|
147
|
-
end
|
148
|
-
end
|
149
|
-
|
150
|
-
def approach_lighting_from(rwylgt_node)
|
151
|
-
if rwylgt_node.(:LgtApchCat)
|
152
|
-
AIXM.approach_lighting(
|
153
|
-
type: APPROACH_LIGHTING_TYPES.fetch(rwylgt_node.(:LgtApchCat) , :other)
|
154
|
-
).tap do |approach_lighting|
|
155
|
-
approach_lighting.length = AIXM.d(rwylgt_node.(:LgtApchLongueur).to_i, :m) if rwylgt_node.(:LgtApchLongueur)
|
156
|
-
approach_lighting.intensity = rwylgt_node.(:LgtApchIntensite)&.first_match(/LIH/, /LIM/, /LIL/, default: :other)
|
157
|
-
approach_lighting.remarks = {
|
158
|
-
'type' => (rwylgt_node.(:LgtApchCat) if approach_lighting.type == :other),
|
159
|
-
'intensité/intensity' => (rwylgt_node.(:LgtApchIntensite) if approach_lighting.intensity == :other)
|
160
|
-
}.to_remarks
|
161
|
-
end
|
162
|
-
end
|
163
|
-
end
|
164
|
-
|
165
|
-
def lighting_from(rwylgt_node, position)
|
166
|
-
prefix = "Lgt" + LIGHTING_POSITIONS.fetch(position)
|
167
|
-
if rwylgt_node.(:"#{prefix}Couleur") || rwylgt_node.(:"#{prefix}Longueur")
|
168
|
-
AIXM.lighting(position: position).tap do |lighting|
|
169
|
-
couleur, intensite = rwylgt_node.(:"#{prefix}Couleur"), rwylgt_node.(:"#{prefix}Intensite")
|
170
|
-
lighting.intensity = if intensite
|
171
|
-
intensite.first_match(/LIH/, /LIM/, /LIL/, default: :other)
|
172
|
-
elsif couleur
|
173
|
-
couleur.first_match(/LIH/, /LIM/, /LIL/).tap { couleur.remove!(/LIH|LIM|LIL/) }
|
174
|
-
end
|
175
|
-
lighting.color = if couleur
|
176
|
-
if couleur.match? /ICAO|EASA|OACI|AESA/
|
177
|
-
ICAO_LIGHTING_COLORS[position]
|
178
|
-
else
|
179
|
-
couleur.remove(/[^#{LIGHTING_COLORS.keys.join}]/).compact
|
180
|
-
LIGHTING_COLORS.fetch(couleur, :other)
|
181
|
-
end
|
182
|
-
end
|
183
|
-
lighting.description = {
|
184
|
-
'couleur/color' => (rwylgt_node.(:"#{prefix}Couleur") if [nil, :other].include?(lighting.color)),
|
185
|
-
'longueur/length' => rwylgt_node.(:"#{prefix}Longueur"),
|
186
|
-
'espace/spacing' => rwylgt_node.(:"#{prefix}Espace")
|
187
|
-
}.to_remarks
|
188
|
-
lighting.remarks = rwylgt_node.(:LgtRem)
|
189
|
-
end
|
190
|
-
end
|
191
|
-
end
|
192
|
-
|
193
|
-
patch AIXM::Feature::Airport, :xy do |parser, object, value|
|
194
|
-
throw(:abort) unless coordinate = parser.fixture.dig(object.id, 'xy')
|
195
|
-
lat, long = coordinate.split(/\s+/)
|
196
|
-
AIXM.xy(lat: lat, long: long)
|
197
|
-
end
|
198
|
-
|
199
|
-
patch AIXM::Feature::Airport, :z do |parser, object, value|
|
200
|
-
throw(:abort) unless value.nil?
|
201
|
-
throw(:abort, 'fixture missing') unless elevation = parser.fixture.dig(object.id, 'z')
|
202
|
-
AIXM.z(elevation, :qnh)
|
203
|
-
end
|
204
|
-
|
205
|
-
patch AIXM::Component::Runway, :dimensions do |parser, object, value|
|
206
|
-
throw(:abort) unless value.surface.zero?
|
207
|
-
throw(:abort, 'fixture missing') unless dimensions = parser.fixture.dig(object.airport.id, object.name, 'dimensions')
|
208
|
-
length, width = dimensions.split(/\D+/)
|
209
|
-
length = length&.match?(/^\d+$/) ? AIXM.d(length.to_i, :m) : value.length
|
210
|
-
width = width&.match?(/^\d+$/) ? AIXM.d(width.to_i, :m) : value.width
|
211
|
-
AIXM.r(length, width).tap { |r| throw(:abort, 'fixture incomplete') if r.surface.zero? }
|
212
|
-
end
|
213
|
-
|
214
|
-
patch AIXM::Component::Runway::Direction, :xy do |parser, object, value|
|
215
|
-
throw(:abort) unless value.nil?
|
216
|
-
throw(:abort, 'fixture missing') unless coordinate = parser.fixture.dig(object.runway.airport.id, object.name.to_s(:runway), 'xy')
|
217
|
-
lat, long = coordinate.split(/\s+/)
|
218
|
-
AIXM.xy(lat: lat, long: long)
|
219
|
-
end
|
220
|
-
|
221
|
-
end
|
222
|
-
end
|
223
|
-
end
|