Skip to content

Commit

Permalink
Version 3.0.0
Browse files Browse the repository at this point in the history
ES6 Module
  • Loading branch information
brendannee committed May 14, 2021
1 parent 3ac4a75 commit 7fcad53
Show file tree
Hide file tree
Showing 20 changed files with 854 additions and 2,313 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,10 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).

## [3.0.0] - 2021-05-13
### Breaking Changes
- Converted to ES Module

## [2.0.6] - 2021-05-06
### Updated
- Dependency updates
Expand Down
5 changes: 3 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,9 @@ If you are using this as a node module as part of an application, you can includ
## Code example

```js
const gtfsToGeoJSON = require('gtfs-to-geojson');
const config = require('config.json');
import gtfsToGeoJSON from 'gtfs-to-geojson';
import { readFile } from 'fs/promises';
const config = JSON.parse(await readFile(new URL('./config.json', import.meta.url)));

gtfsToGeoJSON(config)
.then(() => {
Expand Down
18 changes: 11 additions & 7 deletions bin/gtfs-to-geojson.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,14 @@
#!/usr/bin/env node

const { argv } = require('yargs')
import yargs from 'yargs';
/* eslint-disable-next-line node/file-extension-in-import */
import { hideBin } from 'yargs/helpers';

import gtfsToGeoJSON from '../lib/gtfs-to-geojson.js';
import { getConfig } from '../lib/file-utils.js';
import { formatError } from '../lib/log-utils.js';

const argv = yargs(hideBin(process.argv))
.usage('Usage: $0 --config ./config.json')
.help()
.option('c', {
Expand All @@ -16,19 +24,15 @@ const { argv } = require('yargs')
})
.default('skipImport', undefined);

const gtfsToGeoJSON = require('../lib/gtfs-to-geojson');
const fileUtils = require('../lib/file-utils');
const logUtils = require('../lib/log-utils');

const handleError = error => {
const text = error || 'Unknown Error';
process.stdout.write(`\n${logUtils.formatError(text)}\n`);
process.stdout.write(`\n${formatError(text)}\n`);
console.error(error);
process.exit(1);
};

const setupImport = async () => {
const config = await fileUtils.getConfig(argv);
const config = await getConfig(argv);
await gtfsToGeoJSON(config);
process.exit();
};
Expand Down
2 changes: 1 addition & 1 deletion index.js
Original file line number Diff line number Diff line change
@@ -1 +1 @@
module.exports = require('./lib/gtfs-to-geojson');
export { default } from './lib/gtfs-to-geojson.js';
70 changes: 41 additions & 29 deletions lib/file-utils.js
Original file line number Diff line number Diff line change
@@ -1,34 +1,46 @@
const path = require('path');
import path from 'node:path';
import { existsSync, createWriteStream } from 'node:fs';
import { readFile, writeFile } from 'node:fs/promises';

const archiver = require('archiver');
const fs = require('fs-extra');
const untildify = require('untildify');
const sanitize = require('sanitize-filename');
import archiver from 'archiver';
import untildify from 'untildify';
import sanitize from 'sanitize-filename';

/*
* Attempt to parse the specified config JSON file.
* Attempt to parse any config JSON file and read values from CLI.
*/
exports.getConfig = async argv => {
try {
const data = await fs.readFile(path.resolve(untildify(argv.configPath)), 'utf8').catch(error => {
console.error(new Error(`Cannot find configuration file at \`${argv.configPath}\`. Use config-sample.json as a starting point, pass --configPath option`));
export async function getConfig(argv) {
let config;

if (argv.configPath) {
// If a `configPath` is specified, try to read it and throw error if it doesn't exist
try {
const data = await readFile(path.resolve(untildify(argv.configPath)), 'utf8').catch(error => {
console.error(new Error(`Cannot find configuration file at \`${argv.configPath}\`. Use config-sample.json as a starting point, pass --configPath option`));
throw error;
});
config = Object.assign(JSON.parse(data), argv);
} catch (error) {
console.error(new Error(`Cannot parse configuration file at \`${argv.configPath}\`. Check to ensure that it is valid JSON.`));
throw error;
}
} else if (existsSync(path.resolve('./config.json'))) {
// Else if `config.json` exists, use config values read from it
try {
const data = await readFile(path.resolve('./config.json'), 'utf8');
config = Object.assign(JSON.parse(data), argv);
console.log('Using configuration from ./config.json');
} catch (error) {
console.error(new Error('Cannot parse configuration file at `./config.json`. Check to ensure that it is valid JSON.'));
throw error;
});
const config = JSON.parse(data);

if (argv.skipImport === true) {
config.skipImport = argv.skipImport;
}

return config;
} catch (error) {
console.error(new Error(`Cannot parse configuration file at \`${argv.configPath}\`. Check to ensure that it is valid JSON.`));
throw error;
}
};

exports.zipFolder = exportPath => {
const output = fs.createWriteStream(path.join(exportPath, 'geojson.zip'));
return config;
}

export function zipFolder(exportPath) {
const output = createWriteStream(path.join(exportPath, 'geojson.zip'));
const archive = archiver('zip');

return new Promise((resolve, reject) => {
Expand All @@ -38,13 +50,13 @@ exports.zipFolder = exportPath => {
archive.glob(`${exportPath}/**/*.{json}`);
archive.finalize();
});
};
}

exports.getExportPath = agencyKey => {
export function getExportPath(agencyKey) {
return path.join('geojson', sanitize(agencyKey));
};
}

exports.writeFile = (filePath, fileName, text) => {
export function writeSanitizedFile(filePath, fileName, text) {
const cleanedFileName = sanitize(fileName);
return fs.writeFile(path.join(filePath, cleanedFileName), text);
};
return writeFile(path.join(filePath, cleanedFileName), text);
}
16 changes: 9 additions & 7 deletions lib/formats/convex.js
Original file line number Diff line number Diff line change
@@ -1,23 +1,25 @@
const gtfs = require('gtfs');
const convex = require('@turf/convex').default;
const { featureEach } = require('@turf/meta');
import { getStopsAsGeoJSON } from 'gtfs';
import turfConvex from '@turf/convex';
import { featureEach } from '@turf/meta';

const { simplifyGeoJSON } = require('../geojson-utils');
import { simplifyGeoJSON } from '../geojson-utils.js';

module.exports = async (config, routeId, directionId) => {
const convex = async (config, routeId, directionId) => {
const query = {};

if (routeId !== undefined && directionId !== undefined) {
query.route_id = routeId;
query.direction_id = directionId;
}

const stops = await gtfs.getStopsAsGeoJSON(query);
const geojson = convex(stops);
const stops = await getStopsAsGeoJSON(query);
const geojson = turfConvex(stops);

featureEach(geojson, feature => {
feature.properties.agency_name = stops.features[0].properties.agency_name;
});

return simplifyGeoJSON(geojson, config);
};

export default convex;
16 changes: 9 additions & 7 deletions lib/formats/envelope.js
Original file line number Diff line number Diff line change
@@ -1,19 +1,19 @@
const gtfs = require('gtfs');
const bbox = require('@turf/bbox').default;
const bboxPoly = require('@turf/bbox-polygon').default;
const { featureEach } = require('@turf/meta');
import { getShapesAsGeoJSON } from 'gtfs';
import bbox from '@turf/bbox';
import bboxPoly from '@turf/bbox-polygon';
import { featureEach } from '@turf/meta';

const { simplifyGeoJSON } = require('../geojson-utils');
import { simplifyGeoJSON } from '../geojson-utils.js';

module.exports = async (config, routeId, directionId) => {
const envelope = async (config, routeId, directionId) => {
const query = {};

if (routeId !== undefined && directionId !== undefined) {
query.route_id = routeId;
query.direction_id = directionId;
}

const lines = await gtfs.getShapesAsGeoJSON(query);
const lines = await getShapesAsGeoJSON(query);
const geojson = bboxPoly(bbox(lines));

featureEach(geojson, feature => {
Expand All @@ -22,3 +22,5 @@ module.exports = async (config, routeId, directionId) => {

return simplifyGeoJSON(geojson, config);
};

export default envelope;
12 changes: 7 additions & 5 deletions lib/formats/lines-and-stops.js
Original file line number Diff line number Diff line change
@@ -1,18 +1,20 @@
const gtfs = require('gtfs');
import { getShapesAsGeoJSON, getStopsAsGeoJSON } from 'gtfs';

const { mergeGeojson, simplifyGeoJSON } = require('../geojson-utils');
import { mergeGeojson, simplifyGeoJSON } from '../geojson-utils.js';

module.exports = async (config, routeId, directionId) => {
const linesAndStops = async (config, routeId, directionId) => {
const query = {};

if (routeId !== undefined && directionId !== undefined) {
query.route_id = routeId;
query.direction_id = directionId;
}

const shapesGeojson = await gtfs.getShapesAsGeoJSON(query);
const stopsGeojson = await gtfs.getStopsAsGeoJSON(query);
const shapesGeojson = await getShapesAsGeoJSON(query);
const stopsGeojson = await getStopsAsGeoJSON(query);
const geojson = mergeGeojson(shapesGeojson, stopsGeojson);

return simplifyGeoJSON(geojson, config);
};

export default linesAndStops;
12 changes: 7 additions & 5 deletions lib/formats/lines-buffer.js
Original file line number Diff line number Diff line change
@@ -1,18 +1,20 @@
const gtfs = require('gtfs');
const buffer = require('@turf/buffer');
import { getShapesAsGeoJSON } from 'gtfs';
import buffer from '@turf/buffer';

const { simplifyGeoJSON } = require('../geojson-utils');
import { simplifyGeoJSON } from '../geojson-utils.js';

module.exports = async (config, routeId, directionId) => {
const linesBuffer = async (config, routeId, directionId) => {
const query = {};

if (routeId !== undefined && directionId !== undefined) {
query.route_id = routeId;
query.direction_id = directionId;
}

const lines = await gtfs.getShapesAsGeoJSON(query);
const lines = await getShapesAsGeoJSON(query);
const geojson = buffer(lines, config.bufferSizeMeters, { units: 'meters' });

return simplifyGeoJSON(geojson, config);
};

export default linesBuffer;
18 changes: 10 additions & 8 deletions lib/formats/lines-dissolved.js
Original file line number Diff line number Diff line change
@@ -1,20 +1,20 @@
const gtfs = require('gtfs');
const buffer = require('@turf/buffer');
const { geomEach } = require('@turf/meta');
const { multiPolygon } = require('@turf/helpers');
const polygonClipping = require('polygon-clipping');
import { getShapesAsGeoJSON } from 'gtfs';
import buffer from '@turf/buffer';
import { geomEach } from '@turf/meta';
import { multiPolygon } from '@turf/helpers';
import polygonClipping from 'polygon-clipping';

const { simplifyGeoJSON } = require('../geojson-utils');
import { simplifyGeoJSON } from '../geojson-utils.js';

module.exports = async (config, routeId, directionId) => {
const linesDissolved = async (config, routeId, directionId) => {
const query = {};

if (routeId !== undefined && directionId !== undefined) {
query.route_id = routeId;
query.direction_id = directionId;
}

const lines = await gtfs.getShapesAsGeoJSON(query);
const lines = await getShapesAsGeoJSON(query);
const bufferedLines = buffer(lines, config.bufferSizeMeters, { units: 'meters' });
const geometries = [];

Expand All @@ -38,3 +38,5 @@ module.exports = async (config, routeId, directionId) => {

return simplifyGeoJSON(geojson, config);
};

export default linesDissolved;
10 changes: 6 additions & 4 deletions lib/formats/lines.js
Original file line number Diff line number Diff line change
@@ -1,16 +1,18 @@
const gtfs = require('gtfs');
import { getShapesAsGeoJSON } from 'gtfs';

const { simplifyGeoJSON } = require('../geojson-utils');
import { simplifyGeoJSON } from '../geojson-utils.js';

module.exports = async (config, routeId, directionId) => {
const lines = async (config, routeId, directionId) => {
const query = {};

if (routeId !== undefined && directionId !== undefined) {
query.route_id = routeId;
query.direction_id = directionId;
}

const geojson = await gtfs.getShapesAsGeoJSON(query);
const geojson = await getShapesAsGeoJSON(query);

return simplifyGeoJSON(geojson, config);
};

export default lines;
12 changes: 7 additions & 5 deletions lib/formats/stops-buffer.js
Original file line number Diff line number Diff line change
@@ -1,19 +1,21 @@
const gtfs = require('gtfs');
const buffer = require('@turf/buffer');
import { getStopsAsGeoJSON } from 'gtfs';
import buffer from '@turf/buffer';

const { simplifyGeoJSON } = require('../geojson-utils');
import { simplifyGeoJSON } from '../geojson-utils.js';

module.exports = async (config, routeId, directionId) => {
const stopsBuffer = async (config, routeId, directionId) => {
const query = {};

if (routeId !== undefined && directionId !== undefined) {
query.route_id = routeId;
query.direction_id = directionId;
}

const stops = await gtfs.getStopsAsGeoJSON(query);
const stops = await getStopsAsGeoJSON(query);

const geojson = buffer(stops, config.bufferSizeMeters, { units: 'meters' });

return simplifyGeoJSON(geojson, config);
};

export default stopsBuffer;
18 changes: 10 additions & 8 deletions lib/formats/stops-dissolved.js
Original file line number Diff line number Diff line change
@@ -1,20 +1,20 @@
const gtfs = require('gtfs');
const buffer = require('@turf/buffer');
const { geomEach } = require('@turf/meta');
const { multiPolygon } = require('@turf/helpers');
const polygonClipping = require('polygon-clipping');
import { getStopsAsGeoJSON } from 'gtfs';
import buffer from '@turf/buffer';
import { geomEach } from '@turf/meta';
import { multiPolygon } from '@turf/helpers';
import polygonClipping from 'polygon-clipping';

const { simplifyGeoJSON } = require('../geojson-utils');
import { simplifyGeoJSON } from '../geojson-utils.js';

module.exports = async (config, routeId, directionId) => {
const stopsDissolved = async (config, routeId, directionId) => {
const query = {};

if (routeId !== undefined && directionId !== undefined) {
query.route_id = routeId;
query.direction_id = directionId;
}

const stops = await gtfs.getStopsAsGeoJSON(query);
const stops = await getStopsAsGeoJSON(query);
const bufferedStops = buffer(stops, config.bufferSizeMeters, { units: 'meters' });
const geometries = [];

Expand All @@ -39,3 +39,5 @@ module.exports = async (config, routeId, directionId) => {

return simplifyGeoJSON(geojson, config);
};

export default stopsDissolved;
Loading

0 comments on commit 7fcad53

Please sign in to comment.