github的node-gtfs项目学习

项目链接:https://github.com/BlinkTagInc/node-gtfs

一句话概括

Import and Export GTFS transit data into SQLite. Query or change routes, stops, times, fares and more.
导入和导出GTFS交通数据到SQLite;查询或改变路线、站点、时间、票价等。

node-gtfs简介

  • node-gtfs将GTFS格式的交通数据加载到一个SQLite数据库中,并提供一些方法来查询机构、路线、站点、时间、票价、日历和其他GTFS数据。
  • node-gtfs提供空间查询功能,以寻找附近的站点、路线和机构,并可以将站点和形状转换为geoJSON格式。此外,该库可以将数据从SQLite数据库导出为GTFS(csv)格式。
  • node-gtfs还支持将GTFS-Realtime数据导入同一数据库。为了保持实时数据库的新鲜度,它使用非常有效的SQLITE REPLACE操作。
  • 可以把node-gtfs作为一个命令行工具或作为一个node.js模块使用。

四个组成部分

GTFS import script

gtfs-import脚本从JSON配置文件中读取,并将指定的GTFS文件导入到一个SQLite数据库。

GTFS export script

gtfs-export脚本从一个JSON配置文件中读取配置信息,然后从一个SQLite数据库中导出GTFS格式的数据。
这可以用来在手动修改数据库中的数据后从SQLite导出一个GTFS文件。

GTFS-Realtime update script

gtfsrealtime-update脚本要求提供GTFS实时数据并将其导入SQLite数据库。GTFS-Realtime数据可以补充GTFS静态数据。

以上这三种操作都需要有配置文件config.json,具体参数将在文章末尾进行介绍

query methods

noded-gtfs库包括许多方法,可以在项目中使用这些方法来查询GTFS数据。除了标准的静态GTFS数据之外,node-gtfs还支持以下GTFS的扩展:

  • GTFS-Realtime - 实时警报、车辆位置和预测
  • GTFS-Ride - 乘客计数
  • Operational Data Standard (ODS) - 空驶和人员信息
  • GTFS-TImetables - 创建可供人类阅读的时间表的信息

大多数查询方法接受三个可选参数:queryfieldssortByoptions(其他可选参数)

打开数据库

要使用任何一种查询方法,首先要在进行任何查询之前打开数据库。

import { openDb } from 'gtfs';
const db = openDb(config);

另外还需要读取配置文件:

import { readFile } from 'fs/promises';
const config = JSON.parse(
  await readFile(new URL('./config.json', import.meta.url))
);

这两段代码都是进行查询操作的前置操作,以下的代码省略了这两段必要代码。自己在写代码时要注意这两部分代码都要写上。

静态GTFS文件的查询操作

  • getAgencies(query, fields, sortBy, options)
    返回一个机构数组。
    agency_id标识了一个交通品牌,它通常是一个交通机构的同义词。请注意,在某些情况下,例如当一个机构经营多个独立的服务时,机构和品牌是不同的。本文件使用 "机构 "一词来代替 “品牌”。一个数据集可能包含多个机构的数据。
import { getAgencies } from 'gtfs';

// Get all agencies
const agencies = getAgencies();

// Get a specific agency
const agencies = getAgencies({
  agency_id: 'caltrain',
});
  • getAreas(query, fields, sortBy, options)
    返回一个区域数组。
    帮助文档没有说清楚area是什么,不放代码了。

  • getRoutes(query, fields, sortBy, options)
    返回一个路线数组。
    routes.txt有一项属性是routes_type,表示在一条路线上使用的交通工具的类型,包括地铁、轻轨、公共汽车等。

import { getRoutes } from 'gtfs';

// Get all routes, sorted by route_short_name
const routes = getRoutes({}, [], [['route_short_name', 'ASC']]);

// Get a specific route
const routes = getRoutes({
  route_id: 'Lo-16APR',
});

/*
 * `getRoutes` allows passing a `stop_id` as part of the query. This will
 * query stoptimes and trips to find all routes that serve that `stop_id`.
 */
const routes = getRoutes(
  {
    stop_id: '70011',
  },
  [],
  [['stop_name', 'ASC']]
);
  • getStops(query, fields, sortBy, options)
    返回一个站点数组。
import { getStops } from 'gtfs';

// Get all stops
const stops = getStops();

// Get a specific stop by stop_id
const stops = getStops({
  stop_id: '70011',
});

/*
 * `getStops` allows passing a `route_id` in the query and it will
 * query trips and stoptimes to find all stops served by that `route_id`.
 */
const stops = getStops({
  route_id: 'Lo-16APR',
});

/*
 * `getStops` allows passing a `trip_id` in the query and it will query
 * stoptimes to find all stops on that `trip_id`.
 */
const stops = getStops({
  trip_id: '37a',
});

/*
 * `getStops` allows passing a `shape_id` in the query and it will query
 * trips and stoptimes to find all stops that use that `shape_id`.
 */
const stops = getStops({
  shape_id: 'cal_sf_tam',
});
  • getStoptimes(query, fields, sortBy, options)
    返回一个stop_times数组
    主键:(trip_id, stop_sequence)
    trip_id就是这一趟的id,stop_sequence就是一个特定行程的停靠顺序/站点停靠顺序。这些数值必须沿行程增加,但不需要是连续的。
    例如,行程中的第一个地点可以有一个stop_sequence=1,行程中的第二个地点可以有一个stop_sequence=23,第三个地点可以有一个stop_sequence=40,以此类推。
    如果在一个站点没有单独的到达和离开时间,那么到达时间和离开时间应该是相同的。
import { getStoptimes } from 'gtfs';

// Get all stoptimes
const stoptimes = getStoptimes();

// Get all stoptimes for a specific stop
const stoptimes = getStoptimes({
  stop_id: '70011',
});

// Get all stoptimes for a specific trip, sorted by stop_sequence
const stoptimes = getStoptimes(
  {
    trip_id: '37a',
  },
  [],
  [['stop_sequence', 'ASC']]
);

// Get all stoptimes for a specific stop and service_id
const stoptimes = getStoptimes({
  stop_id: '70011',
  service_id: 'CT-16APR-Caltrain-Weekday-01',
});
  • getTrips(query, fields, sortBy, options)
    返回一个行程数组。
import { getTrips } from 'gtfs';

// Get all trips
const trips = getTrips();

// Get trips for a specific route and direction
const trips = getTrips({
  route_id: 'Lo-16APR',
  direction_id: 0
});

// Get trips for direction '' or null
const trips = getTrips({
  route_id: 'Lo-16APR',
  direction_id: null
});

// Get trips for a specific route and direction limited by a service_id
const trips = getTrips({
  route_id: 'Lo-16APR',
  direction_id: 0,
  service_id: ''
});
  • getShapes(query, fields, sortBy, options)
    shapes描述了车辆沿着路线行驶的路径,并在shapes.txt文件中定义。形状与行程相关,由车辆依次经过的一系列点组成。形状不需要准确地截取站点的位置,但一个行程中的所有站点应该位于该行程形状的一小段距离内,即形状点连接起来接近于直线段。
    shapes.txt 文件包含交通系统中交通车辆所采用地理路径的制图表达。
    一个链接帮助更好理解shapes.txt:How to make a shapes.txt file for your GTFS dataset with ArcGIS
import { getShapes } from 'gtfs';

// Get all shapes for an agency
const shapes = getShapes();

/*
 * `getShapes` allows passing a `route_id` in the query and it will query
 * trips to find all shapes served by that `route_id`.
 */
const shapes = getShapes({
  route_id: 'Lo-16APR',
});

/*
 * `getShapes` allows passing a `trip_id` in the query and it will query
 * trips to find all shapes served by that `trip_id`.
 */
const shapes = getShapes({
  trip_id: '37a',
});

/*
 * `getShapes` allows passing a `service_id` in the query and it will query
 * trips to find all shapes served by that `service_id`.
 */
const shapes = getShapes({
  service_id: 'CT-16APR-Caltrain-Sunday-02',
});
  • getCalendars(query, fields, sortBy, options)
    返回一个日历数组。
    表示该服务是否在start_date和end_date字段指定的日期范围内的所有周一/周二./…/周日运行。
import { getCalendars } from 'gtfs';

// Get all calendars for an agency
const calendars = getCalendars();

// Get calendars for a specific `service_id`
const calendars = getCalendars({
  service_id: 'CT-16APR-Caltrain-Sunday-02',
});

GTFS时刻表文件的查询操作

这是一个可选的、非标准的文件,名为timetables.txt,可以包含在一个机构的GTFS中。这个文件向GTFS-to-HTML指定了应该建立哪些HTML时间表。通常,这是使用GTFS-to-HTML唯一需要创建的额外文件。
GTFS-to-HTML链接:https://gtfstohtml.com/
GTFS-to-HTML简介:GTFS-to-HTML可以直接从GTFS交通数据中创建HTML、PDF或CSV格式的人类可读的、用户友好的交通时刻表。大多数交通机构拥有GTFS格式的时间表数据,但需要在网站上向用户显示每条线路的时间表。这个项目使创建格式良好的HTML时间表的过程自动化,以便将其纳入交通机构的网站。这样,当时间表发生变化时,就可以很容易地保持时间表的最新和准确,并减少错误的可能性。

我们不需要这个功能,所以不在这里介绍了。

GTFS实时数据查询

为了使用GTFS-Realtime查询方法,必须首先在node-gtfs中配置GTFS-Realtime update相关的url等,见上文介绍。

  • getServiceAlerts(query, fields, sortBy, options)
    返回一个GTFS实时服务警报的数组。
    服务警报允许在网络中断时提供更新。个别行程的延误和取消通常应使用行程更新进行沟通。
import { getServiceAlerts } from 'gtfs';

// Get service alerts
const serviceAlerts = getServiceAlerts();
  • getTripUpdates(query, fields, sortBy, options)
    返回一个GTFS实时行程更新数组。
    行程更新代表时间表的波动。这些更新将给出沿途各站的预测到达或出发时间。行程更新还可以提供更复杂的情况,即行程被取消或被添加到时间表中,甚至被重新安排路线。
    在GTFS中,一个行程是在一个特定时间发生的两个或更多站点的序列。
    每个计划的行程最多应该有一次行程更新。如果一个预定的行程没有行程更新,该行程将被断定为没有实时数据可用。数据使用者不应该假设该行程是准时运行的。
    【好,其实我没有太明白这个方法是干嘛用的】
import { getTripUpdates } from 'gtfs';

// Get all trip updates
const tripUpdates = getTripUpdates();
  • getStopTimesUpdates(query, fields, sortBy, options)
    返回一个GTFS实时站点时间更新的数组。
    一个行程的更新包括一个或多个对车辆站点时间的更新,这被称为StopTimeUpdates。这些可以为过去和未来的站点时间提供。你可以直接抛弃过去的停车时间,但是没有必要。如果过去的StopTimeUpdate指的是在未来的行程中预定到达的站点(即车辆已经提前通过了该站点),生产者不应该放弃过去的StopTimeUpdate,否则将被认为没有对该站点的更新。
    举个例子:
    第4站 - 预测在上午10:18到达(计划在上午10:20 - 提前2分钟)。
    第5站 - 预测在上午10:30到达(计划在上午10:30 - 准时)。

    4号站的预测直到上午10:21才会从反馈中删除,即使公交车在上午10:18实际经过该站。 如果4号站的StopTimeUpdate在上午10:18或10:19从反馈中删除,而预定到达时间是上午10:20,那么消费者应该假设4号站在那个时间不存在实时信息,所以应该使用GTFS的时间表数据。
import { getStopTimesUpdates } from 'gtfs';

// Get all stop times updates
const stopTimesUpdates = getStopTimesUpdates();
  • getVehiclePositions(query, fields, sortBy, options)
    返回一个GTFS实时车辆位置的数组。
    车辆位置(Vehicle Position)用于提供自动生成的车辆位置信息,该信息可以来自车上的GPS设备。每个能够提供位置的车辆提都应当提供一个单一的车辆位置。
    车辆位置包括以下几个属性:
    • Position
      Position包含车辆位置内的位置数据。纬度和经度是必须的,其他字段是可选的。这些类型的数据是:
      ·Latitude - 纬度
      ·Longitude - 经度
      ·Bearing - 车辆方向
      ·Odometer - 车辆已经行驶的距离
      ·Speed - 车辆测量的瞬间速度,单位为米/秒
    • CongestionLevel
      车辆位置还允许机构指定车辆目前所经历的拥堵程度。拥堵可以分为以下几类:
      ·Unknown congestion level
      ·Running smoothly
      ·Stop and go
      ·Congestion
      ·Severe congestion
    • OccupancyStatus
      还允许该机构指定车辆的乘客占用程度。乘坐状态可分为以下几类:
      ·Empty
      ·Many seats available
      ·Few seats available
      ·Standing room only
      ·Crushed standing room only
      ·Full
      ·Not accepting passengers
    • VehicleStopStatus
      车辆停车状态对车辆的状态有更多的意义,它与当前接近或处于的停车点有关。它可以被设置为这些值中的任何一个:
      ·Incoming at – 车辆即将到达参考的站点
      ·Stopped at – 车辆停在参考站。
      ·In transit to – 参考站是车辆的下一站 – default
    • VehicleDescriptor
      VehicleDescriptor描述了一个精确的物理车辆,可以包含以下任何属性:
      ·ID - 车辆的内部识别系统。对车辆来说应该是唯一的。
      ·Label - 用户可见的标签 - 例如火车的名称
      ·License plate - 车辆的实际车牌
import { getVehiclePositions } from 'gtfs';

// Get all vehicle position data
const vehiclePositions = getVehiclePositions();

config.json文件

以上的import、export和update三种操作都需要用到配置文件。注意,配置文件的命名是随意的,同时我们可以指定一个配置json文件的路径。在默认情况下,node-gtfs会在其运行的目录中寻找一个名为config.json的配置文件。使用config.json文件允许你指定比单独的CLI参数更多的选项,见下文的参数说明。

agencies

GTFS文件可以通过URL或本地路径的zipped/unzipped包(URL和包这两种都被称为agencies,机构)导入。具体例子如下:

  1. 指定一个下载的URL
{
  "agencies": [
    {
      "url": "http://countyconnection.com/GTFS/google_transit.zip"
    }
  ]
}
  1. 指定一个GTFS文件压缩包的路径
{
  "agencies": [
    {
      "path": "/path/to/the/gtfs.zip"
    }
  ]
}
  1. 指定一个已经解压缩的GTFS文件的路径
{
  "agencies": [
    {
      "path": "/path/to/the/unzipped/gtfs/"
    }
  ]
}
  1. 如果你不希望所有的GTFS文件被导入,你可以指定一个不想将其导入的文件阵列。
{
  "agencies": [
    {
      "path": "/path/to/the/unzipped/gtfs/",
      "exclude": ["shapes", "stops"]
    }
  ]
}
  1. 指定GTFS-实时更新的URL。realtimeUrls允许一个GTFS-实时的URL阵列。例如,一个用于行程更新(trip updates)的URL,一个用于车辆更新(vehicle updates)的URL和一个用于服务警告(service alerts)的URL。此外,realtimeHeaders参数允许在请求中添加额外的HTTP头信息。
{
  "agencies": [
    {
      "url": "http://countyconnection.com/GTFS/google_transit.zip",
      "realtimeUrls": [
        "https://opendata.somewhere.com/gtfs-rt/VehicleUpdates.pb",
        "https://opendata.somewhere.com/gtfs-rt/TripUpdates.pb"
      ]
    }
  ]
}
  1. 指定多个机构被导入同一个数据库中
{
  "agencies": [
    {
      "path": "/path/to/the/gtfs.zip"
    },
    {
      "path": "/path/to/the/othergtfs.zip"
    }
  ]
}

csvOptions

这是一个可选的参数。如果你想跳过导入GTFS文件中的无效行,就可以用这个参数。

    "csvOptions": {
      "skip_lines_with_error": true
    }

exportPath

一个放置导出的GTFS文件的目录的路径。如果该目录不存在,它将被创建。在运行gtfs-export脚本或exportGtfs()时使用。

{
  "agencies": [
    {
      "path": "/path/to/the/unzipped/gtfs/"
    }
  ],
  "exportPath": "~/path/to/export/gtfs"
}

ignoreDuplicates

如果你不希望node-GTFS在导入GTFS时遇到重复的id时抛出一个错误,可以使用该参数。如果为真,它不会导入违反了唯一约束的重复记录,如asrip_id, stop_id, calendar_id等。如果将GTFS从多个来源导入到一个共享路线或站点的SQlite数据库中, 那么这个参数会非常有用。默认下该参数值为false。

{
  "agencies": [
    {
      "path": "/path/to/the/unzipped/gtfs/"
    }
  ],
  "ignoreDuplicates": false
}

sqlitePath

表示数据库的路径。默认是使用内存数据库,值为:memory:。

     // "sqlitePath": ":memory:";内存数据库
    "sqlitePath": "/dev/sqlite/gtfs"

SQLite 内存中数据库是完全存储在内存中(而不是磁盘上)的数据库。 使用特殊数据源文件名 :memory: 可创建内存中数据库。 连接关闭后,数据库会被删除。 使用 :memory: 时,每个连接都会创建自己的数据库。

verbose

如果不希望import script打印任何输出到控制台,可以把verbose设置为false。默认值是true。

{
  "agencies": [
    {
      "path": "/path/to/the/unzipped/gtfs/"
    }
  ],
  "verbose": false
}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值