Skip to content

Instantly share code, notes, and snippets.

@vesse
Last active August 11, 2020 04:50
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save vesse/80a9022cb5eef194700cc389cf8259f3 to your computer and use it in GitHub Desktop.
Save vesse/80a9022cb5eef194700cc389cf8259f3 to your computer and use it in GitHub Desktop.
Finnish postal number geometries download (postinumeroalueet)
/**
* Convert postal number geometries to WGS84 coordinates for geocoding
*/
import axios from 'axios';
import * as proj4 from 'proj4';
import * as turf from '@turf/turf';
import { promisify } from 'util';
import * as fs from 'fs';
const writeFile = promisify(fs.writeFile);
// Paavo geometry properties
interface Properties {
readonly objectid: number;
readonly posti_alue: string;
readonly vuosi: string;
readonly nimi: string;
readonly namn: string;
readonly kunta: string;
readonly kuntanro: number;
readonly pinta_ala: number;
readonly bbox: [number, number, number, number];
}
// Coordinate definition for EPSG:3067 / TM35FIN. As proj4 does not understand
// urn:ogc:def:crs:EPSG:3067 which would be available in the response crs the
// implementation here is fixed to work with this SRID only, but it is the official
// one in Finland and thus unlikely to change
proj4.defs(
'TM35FIN',
'+proj=utm +zone=35 +ellps=GRS80 +towgs84=0,0,0,-0,-0,-0,0 +units=m +no_defs'
);
const endpoint = 'http://geo.stat.fi/geoserver/postialue/wfs';
const params = new URLSearchParams({
service: 'wfs',
version: '1.1.0',
request: 'GetFeature',
outputFormat: 'json',
typeName: 'postialue:pno',
// If need to debug, limit to single postal code
// featureID: 'pno.1',
});
// Get geometries from Tilastokeskus WFS endpoint
const getGeometries = () => {
console.log('Download geometries');
return axios.get(endpoint, { params }).then((result) => result.data);
};
// Process the GeoJSON response and create map to WGS84 centroid coordinate
const calculateCentroids = (
features: turf.FeatureCollection<turf.Polygon, Properties>
) => {
console.log('Calculate centroids');
return features.features
.map((feature) => ({
postalCode: feature.properties?.posti_alue,
// Coordinates from the API are using ETRS-TM35FIN coordinate reference
// system, and for HubSpot we need WGS84 which is the one used by
// eg. Google Maps and GPS
coordinate: proj4(
'TM35FIN',
'WGS84',
turf.centroid(feature).geometry?.coordinates!
),
}));
};
if (!module.parent) {
getGeometries()
.then(calculateCentroids)
.then(() => console.log('Done'))
.catch((err) => console.error('Failed to execute', err));
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment