gtfs-to-html 2.6.8 → 2.6.10
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.
- package/CHANGELOG.md +17 -0
- package/lib/formatters.js +9 -15
- package/lib/log-utils.js +1 -1
- package/package.json +6 -6
- package/public/css/timetable_styles.css +1 -1
- package/public/js/system-map.js +14 -1
- package/public/js/timetable-map.js +14 -1
- package/views/default/formatting_functions.pug +2 -8
- package/views/default/overview.pug +11 -11
- package/views/default/overview_full.pug +2 -2
- package/views/default/timetablepage.pug +1 -1
- package/views/default/timetablepage_full.pug +2 -2
- package/www/docs/previewing-html-output.md +4 -0
- package/www/docs/processing-large-gtfs.md +2 -0
- package/www/docs/related-libraries.md +32 -18
- package/www/docs/reviewing-changes.md +4 -0
- package/www/static/img/favicon.ico +0 -0
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,23 @@ All notable changes to this project will be documented in this file.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [2.6.10] - 2024-07-15
|
|
9
|
+
|
|
10
|
+
### Updated
|
|
11
|
+
- Better date format in timetable comment
|
|
12
|
+
- favicon
|
|
13
|
+
- Improved timetable_page_name fallback
|
|
14
|
+
- Overview template formatting
|
|
15
|
+
- Update mapbox version
|
|
16
|
+
|
|
17
|
+
## [2.6.9] - 2024-07-11
|
|
18
|
+
|
|
19
|
+
### Added
|
|
20
|
+
- Stop popup window on map link to streetview
|
|
21
|
+
|
|
22
|
+
### Updated
|
|
23
|
+
- Dependency updates
|
|
24
|
+
|
|
8
25
|
## [2.6.8] - 2024-06-21
|
|
9
26
|
|
|
10
27
|
### Updated
|
package/lib/formatters.js
CHANGED
|
@@ -512,22 +512,16 @@ export function formatTimetablePageLabel(timetablePage) {
|
|
|
512
512
|
timetablePage.consolidatedTimetables &&
|
|
513
513
|
timetablePage.consolidatedTimetables.length > 0
|
|
514
514
|
) {
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
(timetable) => timetable.routes,
|
|
524
|
-
),
|
|
525
|
-
'route_id',
|
|
526
|
-
);
|
|
527
|
-
const timetablePageLabel = routes.map((route) => formatRouteName(route));
|
|
515
|
+
// Use route names from all timetables
|
|
516
|
+
const routes = uniqBy(
|
|
517
|
+
flatMap(
|
|
518
|
+
timetablePage.consolidatedTimetables,
|
|
519
|
+
(timetable) => timetable.routes,
|
|
520
|
+
),
|
|
521
|
+
'route_id',
|
|
522
|
+
);
|
|
528
523
|
|
|
529
|
-
|
|
530
|
-
}
|
|
524
|
+
return routes.map((route) => formatRouteName(route)).join(' and ');
|
|
531
525
|
}
|
|
532
526
|
|
|
533
527
|
return 'Unknown';
|
package/lib/log-utils.js
CHANGED
|
@@ -17,7 +17,7 @@ export function generateLogText(outputStats, config) {
|
|
|
17
17
|
const logText = [
|
|
18
18
|
`Feed Version: ${feedVersion}`,
|
|
19
19
|
`GTFS-to-HTML Version: ${config.gtfsToHtmlVersion}`,
|
|
20
|
-
`Date Generated: ${new Date()}`,
|
|
20
|
+
`Date Generated: ${new Date().toISOString()}`,
|
|
21
21
|
`Timetable Page Count: ${outputStats.timetablePages}`,
|
|
22
22
|
`Timetable Count: ${outputStats.timetables}`,
|
|
23
23
|
`Calendar Service ID Count: ${outputStats.calendars}`,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "gtfs-to-html",
|
|
3
|
-
"version": "2.6.
|
|
3
|
+
"version": "2.6.10",
|
|
4
4
|
"private": false,
|
|
5
5
|
"description": "Build human readable transit timetables as HTML, PDF or CSV from GTFS",
|
|
6
6
|
"keywords": [
|
|
@@ -42,23 +42,23 @@
|
|
|
42
42
|
"copy-dir": "^1.3.0",
|
|
43
43
|
"csv-stringify": "^6.5.0",
|
|
44
44
|
"express": "^4.19.2",
|
|
45
|
-
"gtfs": "^4.
|
|
45
|
+
"gtfs": "^4.13.0",
|
|
46
46
|
"insane": "^2.6.2",
|
|
47
47
|
"js-beautify": "^1.15.1",
|
|
48
48
|
"lodash-es": "^4.17.21",
|
|
49
|
-
"marked": "^13.0.
|
|
49
|
+
"marked": "^13.0.2",
|
|
50
50
|
"moment": "^2.30.1",
|
|
51
51
|
"morgan": "^1.10.0",
|
|
52
52
|
"pretty-error": "^4.0.0",
|
|
53
53
|
"pug": "^3.0.3",
|
|
54
|
-
"puppeteer": "^22.
|
|
54
|
+
"puppeteer": "^22.13.0",
|
|
55
55
|
"sanitize-filename": "^1.6.3",
|
|
56
56
|
"sqlstring": "^2.3.3",
|
|
57
57
|
"timer-machine": "^1.1.0",
|
|
58
58
|
"toposort": "^2.0.2",
|
|
59
59
|
"untildify": "^5.0.0",
|
|
60
60
|
"yargs": "^17.7.2",
|
|
61
|
-
"yoctocolors": "^2.
|
|
61
|
+
"yoctocolors": "^2.1.1"
|
|
62
62
|
},
|
|
63
63
|
"devDependencies": {
|
|
64
64
|
"husky": "^9.0.11",
|
|
@@ -66,7 +66,7 @@
|
|
|
66
66
|
"prettier": "^3.3.2"
|
|
67
67
|
},
|
|
68
68
|
"engines": {
|
|
69
|
-
"node": ">=
|
|
69
|
+
"node": ">= 20.11.0"
|
|
70
70
|
},
|
|
71
71
|
"release-it": {
|
|
72
72
|
"github": {
|
package/public/js/system-map.js
CHANGED
|
@@ -60,10 +60,23 @@ function formatStopPopup(feature) {
|
|
|
60
60
|
$('<strong>').text(feature.properties.stop_code).appendTo(html);
|
|
61
61
|
}
|
|
62
62
|
|
|
63
|
-
$('<
|
|
63
|
+
$('<label>').addClass('block').text('Routes Served:').appendTo(html);
|
|
64
64
|
|
|
65
65
|
$(html).append(routes.map((route) => formatRoute(route)));
|
|
66
66
|
|
|
67
|
+
$('<a>')
|
|
68
|
+
.addClass(
|
|
69
|
+
'bg-blue-500 hover:bg-blue-700 text-white font-bold py-1.5 px-3 rounded inline-block hover:no-underline mt-2',
|
|
70
|
+
)
|
|
71
|
+
.prop(
|
|
72
|
+
'href',
|
|
73
|
+
`https://www.google.com/maps/@?api=1&map_action=pano&viewpoint=${feature.geometry.coordinates[1]},${feature.geometry.coordinates[0]}&heading=0&pitch=0&fov=90`,
|
|
74
|
+
)
|
|
75
|
+
.prop('target', '_blank')
|
|
76
|
+
.prop('rel', 'noopener noreferrer')
|
|
77
|
+
.html('View on Streetview')
|
|
78
|
+
.appendTo(html);
|
|
79
|
+
|
|
67
80
|
return html.prop('outerHTML');
|
|
68
81
|
}
|
|
69
82
|
|
|
@@ -53,10 +53,23 @@ function formatStopPopup(feature, routes) {
|
|
|
53
53
|
$('<strong>').text(feature.properties.stop_code).appendTo(html);
|
|
54
54
|
}
|
|
55
55
|
|
|
56
|
-
$('<
|
|
56
|
+
$('<label>').addClass('block').text('Routes Served:').appendTo(html);
|
|
57
57
|
|
|
58
58
|
$(html).append(routeIds.map((routeId) => formatRoute(routes[routeId])));
|
|
59
59
|
|
|
60
|
+
$('<a>')
|
|
61
|
+
.addClass(
|
|
62
|
+
'bg-blue-500 hover:bg-blue-700 text-white font-bold py-1.5 px-3 rounded inline-block hover:no-underline mt-2',
|
|
63
|
+
)
|
|
64
|
+
.prop(
|
|
65
|
+
'href',
|
|
66
|
+
`https://www.google.com/maps/@?api=1&map_action=pano&viewpoint=${feature.geometry.coordinates[1]},${feature.geometry.coordinates[0]}&heading=0&pitch=0&fov=90`,
|
|
67
|
+
)
|
|
68
|
+
.prop('target', '_blank')
|
|
69
|
+
.prop('rel', 'noopener noreferrer')
|
|
70
|
+
.html('View on Streetview')
|
|
71
|
+
.appendTo(html);
|
|
72
|
+
|
|
60
73
|
return html.prop('outerHTML');
|
|
61
74
|
}
|
|
62
75
|
|
|
@@ -11,14 +11,8 @@
|
|
|
11
11
|
return summary;
|
|
12
12
|
}
|
|
13
13
|
|
|
14
|
-
function
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
if (hasLongName) {
|
|
18
|
-
return route.route_long_name;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
return route.route_short_name;
|
|
14
|
+
function isNullOrEmpty(value) {
|
|
15
|
+
return value === null || value === '';
|
|
22
16
|
}
|
|
23
17
|
|
|
24
18
|
function formatFrequencyWarning(frequencies) {
|
|
@@ -1,28 +1,28 @@
|
|
|
1
1
|
include formatting_functions.pug
|
|
2
2
|
|
|
3
|
-
.
|
|
3
|
+
.h-screen.items-stretch(class="md:flex")
|
|
4
4
|
if !timetablePages || !timetablePages.length
|
|
5
5
|
.flex.justify-center
|
|
6
6
|
.bg-blue-700.text-white.font-bold.rounded-lg.border.shadow-lg.text-lg.p-8(class="w-1/2") No timetables found
|
|
7
7
|
else
|
|
8
|
-
.overview-list.flex-none(class="md:overflow-y-scroll")
|
|
8
|
+
.overview-list.flex-none(class="md:overflow-y-scroll md:max-w-96")
|
|
9
9
|
each timetablePageGroup in getAgencyTimetableGroups(timetablePages, agencies)
|
|
10
|
-
h1.text-2xl.
|
|
10
|
+
h1.text-2xl.mx-4.py-3= `${formatAgencyName(timetablePageGroup.agency)} Routes`
|
|
11
|
+
|
|
11
12
|
each timetablePage in timetablePageGroup.timetablePages
|
|
12
13
|
if config.allowEmptyTimetables || timetablePage.consolidatedTimetables.length > 0
|
|
13
|
-
a.block.p-2.border-b.border-slate-200(class="hover:bg-slate-100 hover:no-underline" href=`${timetablePage.relativePath}` data-route-ids=`${timetablePage.route_ids ? timetablePage.route_ids.join(',') : ''}`)
|
|
14
|
-
.text-lg.text-gray-800.leading-none= timetablePage.timetable_page_label
|
|
14
|
+
a.timetable-overview-label.flex.items-center.gap-2.block.p-2.border-b.border-slate-200(class="hover:bg-slate-100 hover:no-underline" href=`${timetablePage.relativePath}` data-route-ids=`${timetablePage.route_ids ? timetablePage.route_ids.join(',') : ''}`)
|
|
15
15
|
each route in _.uniqBy(_.flatMap(timetablePage.consolidatedTimetables, timetable => timetable.routes), 'route_id')
|
|
16
|
-
.
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
16
|
+
.route-color-swatch-large.flex-none(style=`background-color: ${formatRouteColor(route)}; color: ${formatRouteTextColor(route)};`)= route.route_short_name || ''
|
|
17
|
+
div
|
|
18
|
+
.text-xl.leading-none.text-slate-800= timetablePage.timetable_page_label
|
|
19
|
+
.inline-flex.items-center.justify-center.px-2.py-1.text-xs.font-bold.leading-none.text-slate-800.bg-slate-200.rounded-full= timetablePage.dayList
|
|
20
20
|
if config.showMap
|
|
21
|
-
.map.
|
|
21
|
+
.map.h-full.w-full(id="system_map")
|
|
22
22
|
|
|
23
23
|
//- Use #{variable} format to inject values from pug to client side js
|
|
24
24
|
script.
|
|
25
25
|
(function() {
|
|
26
|
-
|
|
26
|
+
const geojson = !{JSON.stringify(geojson) || '\'\''};
|
|
27
27
|
createSystemMap('system_map', geojson);
|
|
28
28
|
})();
|
|
@@ -6,9 +6,9 @@ block extraHeader
|
|
|
6
6
|
if config.showMap
|
|
7
7
|
script(src="https://unpkg.com/jquery@3.7.1/dist/jquery.min.js" crossorigin="anonymous")
|
|
8
8
|
script(src="https://unpkg.com/lodash@4.17.21/lodash.min.js" crossorigin="anonymous")
|
|
9
|
-
script(src="https://api.mapbox.com/mapbox-gl-js/v3.
|
|
9
|
+
script(src="https://api.mapbox.com/mapbox-gl-js/v3.5.1/mapbox-gl.js")
|
|
10
10
|
script.
|
|
11
11
|
mapboxgl.accessToken = '#{config.mapboxAccessToken}';
|
|
12
12
|
script(src=`${config.assetPath}js/system-map.js`)
|
|
13
13
|
|
|
14
|
-
link(href="https://api.mapbox.com/mapbox-gl-js/v3.
|
|
14
|
+
link(href="https://api.mapbox.com/mapbox-gl-js/v3.5.1/mapbox-gl.css" rel="stylesheet")
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
include formatting_functions.pug
|
|
2
2
|
|
|
3
|
-
<!-- Timetable generated on #{Date()} using GTFS-to-HTML version #{config.gtfsToHtmlVersion} -->
|
|
3
|
+
<!-- Timetable generated on #{new Date().toISOString()} using GTFS-to-HTML version #{config.gtfsToHtmlVersion} -->
|
|
4
4
|
.timetable-page(class=`menu-type-${config.menuType}`)
|
|
5
5
|
.container.mx-4(class="md:mx-auto")
|
|
6
6
|
if config.showRouteTitle
|
|
@@ -9,10 +9,10 @@ block extraHeader
|
|
|
9
9
|
script(src=`${config.assetPath}js/timetable-menu.js`)
|
|
10
10
|
|
|
11
11
|
if config.showMap
|
|
12
|
-
script(src="https://api.mapbox.com/mapbox-gl-js/v3.
|
|
12
|
+
script(src="https://api.mapbox.com/mapbox-gl-js/v3.5.1/mapbox-gl.js")
|
|
13
13
|
script.
|
|
14
14
|
mapboxgl.accessToken = '#{config.mapboxAccessToken}';
|
|
15
15
|
script(src=`${config.assetPath}js/timetable-map.js`)
|
|
16
16
|
|
|
17
|
-
link(href="https://api.mapbox.com/mapbox-gl-js/v3.
|
|
17
|
+
link(href="https://api.mapbox.com/mapbox-gl-js/v3.5.1/mapbox-gl.css" rel="stylesheet")
|
|
18
18
|
|
|
@@ -11,10 +11,14 @@ After an initial run of `gtfs-to-html`, the GTFS data will be downloaded and loa
|
|
|
11
11
|
|
|
12
12
|
You can view an individual route HTML on demand by running the included Express app:
|
|
13
13
|
|
|
14
|
+
```bash
|
|
14
15
|
node app
|
|
16
|
+
```
|
|
15
17
|
|
|
16
18
|
By default, `gtfs-to-html` will look for a `config.json` file in the project root. To specify a different path for the configuration file:
|
|
17
19
|
|
|
20
|
+
```bash
|
|
18
21
|
node app --configPath /path/to/your/custom-config.json
|
|
22
|
+
```
|
|
19
23
|
|
|
20
24
|
Once running, you can view the HTML in your browser at [localhost:3000](http://localhost:3000)
|
|
@@ -5,4 +5,6 @@ title: Processing very large GTFS files
|
|
|
5
5
|
|
|
6
6
|
By default, node has a memory limit of 512 MB or 1 GB. If you have a very large GTFS file and want to use the option `showOnlyTimepoint` = `false` you may need to allocate more memory. Use the `max-old-space-size` option. For example to allocate 4 GB:
|
|
7
7
|
|
|
8
|
+
```
|
|
8
9
|
NODE_OPTIONS=--max_old_space_size=4096 gtfs-to-html
|
|
10
|
+
```
|
|
@@ -4,37 +4,51 @@ title: Related Libraries
|
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
## `node-gtfs`
|
|
7
|
-
|
|
8
|
-
`gtfs-to-html` uses the [`node-gtfs`](https://github.com/blinktaginc/node-gtfs) library to handle importing and querying GTFS data. It provides methods for loading transit data in GTFS format into a SQLite database and methods to query for agencies, routes, stops, times, fares, calendars and other GTFS data. It also offers spatial queries to find nearby stops, routes and agencies and can convert stops and shapes to geoJSON format.
|
|
9
|
-
|
|
10
7
|
[`https://github.com/blinktaginc/node-gtfs`](https://github.com/blinktaginc/node-gtfs)
|
|
8
|
+
<div style={{ display: 'flex', gap: 20 }}>
|
|
9
|
+
<div style={{ width: 100, flexShrink: 0 }}><img src="https://github.com/BlinkTagInc/node-gtfs/raw/master/docs/images/node-gtfs-logo.svg" alt="node-gtfs" width="100" /></div>
|
|
10
|
+
<div><code>gtfs-to-html</code> uses the <a href="https://github.com/blinktaginc/node-gtfs">node-gtfs</a> library to handle importing and querying GTFS data. It provides methods for loading transit data in GTFS format into a SQLite database and methods to query for agencies, routes, stops, times, fares, calendars and other GTFS data. It also offers spatial queries to find nearby stops, routes and agencies and can convert stops and shapes to geoJSON format.</div>
|
|
11
|
+
</div>
|
|
11
12
|
|
|
12
13
|
## `gtfs-to-geojson`
|
|
13
|
-
|
|
14
|
-
[`gtfs-to-geojson`](https://github.com/blinktaginc/gtfs-to-geojson) converts transit data in GTFS format into geoJSON. This includes both shapes and stops. It can be configured to generate one geoJSON file per route or a single file which contains all routes for an agency. This is useful for creating maps of transit routes.
|
|
15
|
-
|
|
16
14
|
[`https://github.com/blinktaginc/gtfs-to-geojson`](https://github.com/blinktaginc/gtfs-to-geojson)
|
|
15
|
+
<div style={{ display: 'flex', gap: 20 }}>
|
|
16
|
+
<div style={{ width: 100, flexShrink: 0 }}><img src="https://github.com/BlinkTagInc/gtfs-to-geojson/raw/master/docs/images/gtfs-to-geojson-logo.svg" alt="gtfs-to-geojson" width="100" /></div>
|
|
17
|
+
<div><a href="https://github.com/blinktaginc/gtfs-to-geojson"><code>gtfs-to-geojson</code></a> converts transit data in GTFS format into geoJSON. This includes both shapes and stops. It can be configured to generate one geoJSON file per route or a single file which contains all routes for an agency. This is useful for creating maps of transit routes.</div>
|
|
18
|
+
</div>
|
|
17
19
|
|
|
18
20
|
## `gtfs-to-chart`
|
|
19
|
-
|
|
20
|
-
[`gtfs-to-chart`](https://github.com/blinktaginc/gtfs-to-chart) generates a stringline chart in D3 using data from an agency's GTFS. This chart shows all trips for a specific route as they travel through space over a single day.
|
|
21
|
-
|
|
22
21
|
[`https://github.com/blinktaginc/gtfs-to-chart`](https://github.com/blinktaginc/gtfs-to-chart)
|
|
22
|
+
<div style={{ display: 'flex', gap: 20 }}>
|
|
23
|
+
<div style={{ width: 100, flexShrink: 0 }}><img src="https://github.com/BlinkTagInc/gtfs-to-chart/raw/master/docs/images/gtfs-to-chart-logo.svg" alt="gtfs-to-chart" width="100" /></div>
|
|
24
|
+
<div><a href="https://github.com/blinktaginc/gtfs-to-chart"><code>gtfs-to-chart</code></a> generates a stringline chart in D3 using data from an agency's GTFS. This chart shows all trips for a specific route as they travel through space over a single day.</div>
|
|
25
|
+
</div>
|
|
23
26
|
|
|
24
27
|
## Transit Departures Widget
|
|
25
|
-
|
|
26
|
-
The [Transit Departures Widget](https://github.com/BlinkTagInc/transit-departures-widget) generates a user-friendly transit realtime departures widget in HTML format directly from GTFS and GTFS-RT transit data. Most transit agencies have schedule data in GTFS format and many publish realtime departure information using GTFS-RT. This project generates HTML, JS and CSS for use on a transit agency website to allow users to see when the next vehicle is departing from a specific stop and includes features like caching, auto-refresh, url parameters and custom templates.
|
|
27
|
-
|
|
28
28
|
[`https://github.com/BlinkTagInc/transit-departures-widget`](https://github.com/BlinkTagInc/transit-departures-widget)
|
|
29
|
+
<div style={{ display: 'flex', gap: 20 }}>
|
|
30
|
+
<div style={{ width: 100, flexShrink: 0 }}><img src="https://github.com/BlinkTagInc/transit-departures-widget/raw/main/docs/images/transit-departures-widget-logo.svg" alt="Transit Departures Widget" width="100" /></div>
|
|
31
|
+
<div>The <a href="https://github.com/BlinkTagInc/transit-departures-widget">Transit Departures Widget</a> generates a user-friendly transit realtime departures widget in HTML format directly from GTFS and GTFS-RT transit data. Most transit agencies have schedule data in GTFS format and many publish realtime departure information using GTFS-RT. This project generates HTML, JS and CSS for use on a transit agency website to allow users to see when the next vehicle is departing from a specific stop and includes features like caching, auto-refresh, url parameters and custom templates.</div>
|
|
32
|
+
</div>
|
|
33
|
+
|
|
34
|
+
## GTFS Accessibility Validator
|
|
35
|
+
[`https://github.com/BlinkTagInc/gtfs-accessibility-validator`](https://github.com/BlinkTagInc/gtfs-accessibility-validator)
|
|
36
|
+
<div style={{ display: 'flex', gap: 20 }}>
|
|
37
|
+
<div style={{ width: 100, flexShrink: 0 }}><img src="https://github.com/BlinkTagInc/gtfs-accessibility-validator/raw/main/docs/images/gtfs-accessibility-validator-logo.svg" alt="Transit Departures Widget" width="100" /></div>
|
|
38
|
+
<div>The <a href="https://github.com/BlinkTagInc/gtfs-accessibility-validator">GTFS Accessibility Validator</a> checks transit data in GTFS format for fields and files related to accessibility. The accessibility guidelines are taken from the <a href="https://dot.ca.gov/cal-itp/california-transit-data-guidelines-v3_0#section-checklist">California Transit Data Guidelines</a> published by Caltrans.</div>
|
|
39
|
+
</div>
|
|
29
40
|
|
|
30
41
|
## GTFS Text-to-Speech Tester
|
|
31
|
-
|
|
32
|
-
The [GTFS Text-to-Speech Tester](https://github.com/BlinkTagInc/node-gtfs-tts) is a command-line tool that will read all GTFS stop names using Text-to-Speech and allow flagging which names need Text-to-Speech values for tts_stop_name in stops.txt. Using this tool is the quickest way to determine which stops need phoenetic spellings, abbreviations written out, large digits written as words, ordinals written out or other changes so that they can be read.
|
|
33
|
-
|
|
34
42
|
[`https://github.com/BlinkTagInc/node-gtfs-tts`](https://github.com/BlinkTagInc/node-gtfs-tts)
|
|
43
|
+
<div style={{ display: 'flex', gap: 20 }}>
|
|
44
|
+
<div style={{ width: 100, flexShrink: 0 }}><img src="https://github.com/BlinkTagInc/node-gtfs-tts/raw/main/docs/images/gtfs-tts-logo.svg" alt="Transit Departures Widget" width="100" /></div>
|
|
45
|
+
<div>The <a href="https://github.com/BlinkTagInc/node-gtfs-tts">GTFS Text-to-Speech Tester</a> is a command-line tool that will read all GTFS stop names using Text-to-Speech and allow flagging which names need Text-to-Speech values for tts_stop_name in stops.txt. Using this tool is the quickest way to determine which stops need phonetic spellings, abbreviations written out, large digits written as words, ordinals written out or other changes so that they can be read.</div>
|
|
46
|
+
</div>
|
|
35
47
|
|
|
36
48
|
## `node-gtfs-realtime`
|
|
37
|
-
|
|
38
|
-
[GTFS-realtime](https://developers.google.com/transit/gtfs-realtime) transit data is in [protobuf format](https://developers.google.com/protocol-buffers) which means its not human-readable by default. `node-GTFS-Realtime` aims to make it fast and easy to inspect GTFS-realtime data by providing a one-line command for downloading [GTFS-realtime format](https://developers.google.com/transit/gtfs-realtime) data and converting to JSON. Try it by running `npx gtfs-realtime http://api.bart.gov/gtfsrt/tripupdate.aspx` in your terminal.
|
|
39
|
-
|
|
40
49
|
[`https://github.com/BlinkTagInc/node-gtfs-realtime`](https://github.com/BlinkTagInc/node-gtfs-realtime)
|
|
50
|
+
<div style={{ display: 'flex', gap: 20 }}>
|
|
51
|
+
<div style={{ width: 100, flexShrink: 0 }}><img src="https://github.com/BlinkTagInc/node-gtfs-realtime/raw/main/docs/images/node-gtfs-realtime-logo.svg
|
|
52
|
+
" alt="Transit Departures Widget" width="100" /></div>
|
|
53
|
+
<div>GTFS-realtime transit data is in <a href="https://developers.google.com/protocol-buffers">protobuf format</a> which means its not human-readable by default. <code>node-GTFS-Realtime</code> aims to make it fast and easy to inspect GTFS-realtime data by providing a one-line command for downloading GTFS-realtime format data and converting to JSON. Try it out by running <code>npx gtfs-realtime http://api.bart.gov/gtfsrt/tripupdate.aspx</code> in your terminal.</div>
|
|
54
|
+
</div>
|
|
@@ -18,8 +18,12 @@ First generate two folders of GTFS-to-HTML output to compare. To make it easy to
|
|
|
18
18
|
|
|
19
19
|
Then, install diff2html:
|
|
20
20
|
|
|
21
|
+
```bash
|
|
21
22
|
npm install -g diff2html-cli
|
|
23
|
+
```
|
|
22
24
|
|
|
23
25
|
Use the `diff` command and pipe the output to `diff2html` to get a nicely formatted list of the differences between two folders of html files.
|
|
24
26
|
|
|
27
|
+
```bash
|
|
25
28
|
diff -bur html/folder1 html/folder2 | diff2html -i stdin
|
|
29
|
+
```
|
|
Binary file
|