text-to-map 1.1.13 → 1.1.16
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/dist/bin/cities.d.ts +1 -0
- package/dist/bin/cities.js +9 -0
- package/dist/bin/parse-ordinance.js +0 -1
- package/dist/db/address-points.js +5 -6
- package/dist/db/cities.d.ts +2 -0
- package/dist/db/cities.js +48 -0
- package/dist/db/db.d.ts +1 -0
- package/dist/db/db.js +8 -1
- package/dist/db/migrations/20230731232915_city_positions.js +25 -0
- package/dist/db/types.d.ts +2 -1
- package/dist/db/types.js +1 -0
- package/dist/index.d.ts +3 -2
- package/dist/index.js +5 -3
- package/dist/open-data-sync/cities.d.ts +2 -0
- package/dist/open-data-sync/cities.js +40 -0
- package/dist/souradnice.csv +6260 -0
- package/package.json +3 -2
- package/dist/address_points_init.db +0 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -36,7 +36,6 @@ function main() {
|
|
|
36
36
|
};
|
|
37
37
|
console.time("downloadAndImportAllLatestAddressPoints");
|
|
38
38
|
const { municipality } = yield getNewMunicipality("Česká Lípa");
|
|
39
|
-
console.log(municipality.founder.schools[0].locations);
|
|
40
39
|
const addressPoints = yield parseOrdinanceToAddressPoints(lines, {
|
|
41
40
|
// currentMunicipality: municipality,
|
|
42
41
|
}, reportErrors, reportWarnings);
|
|
@@ -11,7 +11,7 @@ import { AddressPointType, createSingleLineAddress } from "czech-address";
|
|
|
11
11
|
import { SeriesType, isNegativeSeriesSpec, isRange, isSeriesSpecArray, } from "../street-markdown/types";
|
|
12
12
|
import { findClosestString } from "../utils/helpers";
|
|
13
13
|
import jtsk2wgs84 from "../utils/jtsk2wgs84";
|
|
14
|
-
import { extractKeyValuesPairs, generate2DPlaceholders, getKnexDb, insertMultipleRows, isMysql, isSqlite, nonEmptyOrNull, } from "./db";
|
|
14
|
+
import { extractKeyValuesPairs, generate2DPlaceholders, getKnexDb, insertMultipleRows, isMysql, isSqlite, nonEmptyOrNull, rawQuery, } from "./db";
|
|
15
15
|
import { getFounderCityCode } from "./founders";
|
|
16
16
|
import { MunicipalityType } from "./types";
|
|
17
17
|
const DescriptiveType = "č.p.";
|
|
@@ -80,7 +80,7 @@ export const commitAddressPoints = (buffer) => __awaiter(void 0, void 0, void 0,
|
|
|
80
80
|
});
|
|
81
81
|
const placeHolders = generate2DPlaceholders(columnNames.length, buffer.length);
|
|
82
82
|
const knex = getKnexDb();
|
|
83
|
-
yield
|
|
83
|
+
yield rawQuery(`INSERT ${isMysql(knex) ? "IGNORE" : ""} INTO address_point (${columnNames.join(",")}) VALUES ${placeHolders} ${!isMysql(knex) ? "ON CONFLICT (id) DO NOTHING" : ""}`, params);
|
|
84
84
|
return buffer.length;
|
|
85
85
|
});
|
|
86
86
|
export const insertCities = (buffer) => __awaiter(void 0, void 0, void 0, function* () {
|
|
@@ -129,8 +129,7 @@ const addressPointSelect = `
|
|
|
129
129
|
LEFT JOIN prague_district p ON a.prague_district_code = p.code
|
|
130
130
|
LEFT JOIN municipality_part m ON a.municipality_part_code = m.code`;
|
|
131
131
|
export const getAddressPointById = (addressPointId) => __awaiter(void 0, void 0, void 0, function* () {
|
|
132
|
-
const
|
|
133
|
-
const row = yield knex.raw(`${addressPointSelect}
|
|
132
|
+
const row = yield rawQuery(`${addressPointSelect}
|
|
134
133
|
WHERE a.id = ?`, [addressPointId]);
|
|
135
134
|
if (row.length === 0) {
|
|
136
135
|
return null;
|
|
@@ -144,7 +143,7 @@ export const checkStreetExists = (streetName, founder) => __awaiter(void 0, void
|
|
|
144
143
|
const errors = [];
|
|
145
144
|
// we check the whole city
|
|
146
145
|
const cityCode = yield getFounderCityCode(founder);
|
|
147
|
-
const rowList = yield
|
|
146
|
+
const rowList = yield rawQuery(`SELECT name AS street_name
|
|
148
147
|
FROM street
|
|
149
148
|
WHERE city_code = ? AND name = ? ${isSqlite(knex) ? "COLLATE NOCASE" : ""}`, [cityCode, streetName]);
|
|
150
149
|
if (rowList.length > 0) {
|
|
@@ -207,7 +206,7 @@ export const findAddressPoints = (params) => __awaiter(void 0, void 0, void 0, f
|
|
|
207
206
|
(params.type === FindAddressPointsType.WholeMunicipalityNoStreetName
|
|
208
207
|
? " AND a.street_code IS NULL"
|
|
209
208
|
: "");
|
|
210
|
-
const queryResult = yield
|
|
209
|
+
const queryResult = yield rawQuery(`SELECT a.id, s.name AS street_name, o.name AS object_type_name, a.descriptive_number,
|
|
211
210
|
a.orientational_number, a.orientational_number_letter, c.name AS city_name,
|
|
212
211
|
d.name AS district_name, m.name AS municipality_part_name, p.name AS prague_district_name,
|
|
213
212
|
a.postal_code, a.wgs84_latitude, a.wgs84_longitude
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
2
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
3
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
4
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
5
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
6
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
7
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
|
+
});
|
|
9
|
+
};
|
|
10
|
+
import chunk from "lodash/chunk";
|
|
11
|
+
import { extractKeyValuesPairs, insertMultipleRows, rawQuery } from "./db";
|
|
12
|
+
const citiesColumn = {
|
|
13
|
+
cityName: 0,
|
|
14
|
+
cityCode: 1,
|
|
15
|
+
countyName: 2,
|
|
16
|
+
countyCode: 3,
|
|
17
|
+
regionName: 4,
|
|
18
|
+
regionCode: 5,
|
|
19
|
+
postalCode: 6,
|
|
20
|
+
latitude: 7,
|
|
21
|
+
longitude: 8,
|
|
22
|
+
};
|
|
23
|
+
export const insertCityPositions = (data) => __awaiter(void 0, void 0, void 0, function* () {
|
|
24
|
+
let changes = 0;
|
|
25
|
+
// cities are most likely already inserted, but in case they're not,
|
|
26
|
+
// we need to insert them before updating them with region data
|
|
27
|
+
changes += yield insertCities(data);
|
|
28
|
+
const prev = changes;
|
|
29
|
+
for (const arrayChunk of chunk(data, 1000)) {
|
|
30
|
+
const queries = [];
|
|
31
|
+
for (const row of arrayChunk) {
|
|
32
|
+
queries.push(rawQuery(`UPDATE city SET wgs84_latitude = ?, wgs84_longitude = ? WHERE code = ?`, [
|
|
33
|
+
row[citiesColumn.latitude],
|
|
34
|
+
row[citiesColumn.longitude],
|
|
35
|
+
row[citiesColumn.cityCode],
|
|
36
|
+
]));
|
|
37
|
+
}
|
|
38
|
+
yield Promise.all(queries);
|
|
39
|
+
changes += queries.length;
|
|
40
|
+
console.log(`Done ${changes - prev} / ${data.length} rows...`);
|
|
41
|
+
}
|
|
42
|
+
return changes;
|
|
43
|
+
});
|
|
44
|
+
export const insertCities = (buffer) => __awaiter(void 0, void 0, void 0, function* () {
|
|
45
|
+
return yield insertMultipleRows(extractKeyValuesPairs(buffer, citiesColumn.cityCode, [
|
|
46
|
+
citiesColumn.cityName,
|
|
47
|
+
]), "city", ["code", "name"]);
|
|
48
|
+
});
|
package/dist/db/db.d.ts
CHANGED
|
@@ -20,6 +20,7 @@ export declare const initDb: (config?: Partial<DbConfig>) => Promise<Knex>;
|
|
|
20
20
|
export declare const clearDb: (config?: Partial<DbConfig>) => Promise<Knex>;
|
|
21
21
|
export declare const disconnectKnex: () => Promise<void>;
|
|
22
22
|
export declare const nonEmptyOrNull: (value: string) => string | null;
|
|
23
|
+
export declare const rawQuery: (query: string, ...bindings: readonly Knex.RawBinding[]) => Promise<any[]>;
|
|
23
24
|
/**
|
|
24
25
|
* Efficiently insert multiple rows. If preventDuplicatesByFirstColumn is true, the first
|
|
25
26
|
* column should be unique (PK or UNIQUE).
|
package/dist/db/db.js
CHANGED
|
@@ -57,6 +57,7 @@ export const getKnexDb = (config = {}) => {
|
|
|
57
57
|
client: DbClient[SupportedDbType.postgres],
|
|
58
58
|
connection: _knexDbConfig.pgConnectionString,
|
|
59
59
|
useNullAsDefault: true,
|
|
60
|
+
debug: _knexDbConfig.verbose,
|
|
60
61
|
});
|
|
61
62
|
}
|
|
62
63
|
else if (_knexDbConfig.dbType === SupportedDbType.mysql) {
|
|
@@ -71,6 +72,7 @@ export const getKnexDb = (config = {}) => {
|
|
|
71
72
|
database,
|
|
72
73
|
},
|
|
73
74
|
useNullAsDefault: true,
|
|
75
|
+
debug: _knexDbConfig.verbose,
|
|
74
76
|
});
|
|
75
77
|
}
|
|
76
78
|
else {
|
|
@@ -141,6 +143,11 @@ const getEnvConfig = () => {
|
|
|
141
143
|
export const nonEmptyOrNull = (value) => {
|
|
142
144
|
return value ? value : null;
|
|
143
145
|
};
|
|
146
|
+
export const rawQuery = (query, ...bindings) => __awaiter(void 0, void 0, void 0, function* () {
|
|
147
|
+
const knex = getKnexDb();
|
|
148
|
+
const result = yield knex.raw(query, ...bindings);
|
|
149
|
+
return isMysql(knex) ? result[0] : result;
|
|
150
|
+
});
|
|
144
151
|
/**
|
|
145
152
|
* Efficiently insert multiple rows. If preventDuplicatesByFirstColumn is true, the first
|
|
146
153
|
* column should be unique (PK or UNIQUE).
|
|
@@ -152,7 +159,7 @@ export const insertMultipleRows = (rows, table, columnNames, preventDuplicates =
|
|
|
152
159
|
const insertPlaceholders = generate2DPlaceholders(columnNames.length, rows.length);
|
|
153
160
|
const knex = getKnexDb();
|
|
154
161
|
const onConfict = preventDuplicates && !isMysql(knex) ? `ON CONFLICT DO NOTHING` : "";
|
|
155
|
-
yield
|
|
162
|
+
yield rawQuery(`INSERT ${isMysql(knex) ? "IGNORE" : ""} INTO ${table} (${columnNames.join(",")}) VALUES ${insertPlaceholders} ${onConfict}`, rows.flat());
|
|
156
163
|
return rows.length;
|
|
157
164
|
});
|
|
158
165
|
/**
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
2
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
3
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
4
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
5
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
6
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
7
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
|
+
});
|
|
9
|
+
};
|
|
10
|
+
export function up(knex) {
|
|
11
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
12
|
+
yield knex.schema.alterTable("city", (t) => {
|
|
13
|
+
t.double("wgs84_latitude").nullable();
|
|
14
|
+
t.double("wgs84_longitude").nullable();
|
|
15
|
+
});
|
|
16
|
+
});
|
|
17
|
+
}
|
|
18
|
+
export function down(knex) {
|
|
19
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
20
|
+
yield knex.schema.alterTable("city", (t) => {
|
|
21
|
+
t.dropColumn("wgs84_latitude");
|
|
22
|
+
t.dropColumn("wgs84_longitude");
|
|
23
|
+
});
|
|
24
|
+
});
|
|
25
|
+
}
|
package/dist/db/types.d.ts
CHANGED
package/dist/db/types.js
CHANGED
package/dist/index.d.ts
CHANGED
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
import { clearDb, initDb } from "./db/db";
|
|
2
2
|
import { downloadAndImportAddressPoints } from "./open-data-sync/address-points";
|
|
3
|
+
import { importCities } from "./open-data-sync/cities";
|
|
3
4
|
import { downloadAndImportRegions } from "./open-data-sync/regions";
|
|
4
5
|
import { downloadAndImportSchools } from "./open-data-sync/schools";
|
|
5
6
|
import { downloadAndImportStreets } from "./open-data-sync/streets";
|
|
6
7
|
import { OpenDataSyncOptionsPartial } from "./utils/helpers";
|
|
7
|
-
export * from "./street-markdown/types";
|
|
8
8
|
export * from "./street-markdown/smd";
|
|
9
|
+
export * from "./street-markdown/types";
|
|
9
10
|
/**
|
|
10
11
|
* Download and import all open data to SQLite DB. The DB file will be located
|
|
11
12
|
* in the `dataDir` folder.
|
|
@@ -18,4 +19,4 @@ export * from "./street-markdown/smd";
|
|
|
18
19
|
* ```
|
|
19
20
|
*/
|
|
20
21
|
export declare function downloadAndImportEverything(options?: OpenDataSyncOptionsPartial, syncStreets?: boolean): Promise<void>;
|
|
21
|
-
export {
|
|
22
|
+
export { clearDb, downloadAndImportAddressPoints, downloadAndImportRegions, downloadAndImportSchools, downloadAndImportStreets, importCities, initDb, };
|
package/dist/index.js
CHANGED
|
@@ -8,12 +8,13 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
|
|
8
8
|
});
|
|
9
9
|
};
|
|
10
10
|
import { clearDb, initDb } from "./db/db";
|
|
11
|
-
import { downloadAndImportAddressPoints
|
|
11
|
+
import { downloadAndImportAddressPoints } from "./open-data-sync/address-points";
|
|
12
|
+
import { importCities } from "./open-data-sync/cities";
|
|
12
13
|
import { downloadAndImportRegions } from "./open-data-sync/regions";
|
|
13
14
|
import { downloadAndImportSchools } from "./open-data-sync/schools";
|
|
14
15
|
import { downloadAndImportStreets } from "./open-data-sync/streets";
|
|
15
|
-
export * from "./street-markdown/types";
|
|
16
16
|
export * from "./street-markdown/smd";
|
|
17
|
+
export * from "./street-markdown/types";
|
|
17
18
|
/**
|
|
18
19
|
* Download and import all open data to SQLite DB. The DB file will be located
|
|
19
20
|
* in the `dataDir` folder.
|
|
@@ -31,9 +32,10 @@ export function downloadAndImportEverything(options = {}, syncStreets = true) {
|
|
|
31
32
|
yield downloadAndImportAddressPoints(options);
|
|
32
33
|
yield downloadAndImportSchools(options);
|
|
33
34
|
yield downloadAndImportRegions(options);
|
|
35
|
+
yield importCities(options);
|
|
34
36
|
if (syncStreets) {
|
|
35
37
|
yield downloadAndImportStreets(options);
|
|
36
38
|
}
|
|
37
39
|
});
|
|
38
40
|
}
|
|
39
|
-
export {
|
|
41
|
+
export { clearDb, downloadAndImportAddressPoints, downloadAndImportRegions, downloadAndImportSchools, downloadAndImportStreets, importCities, initDb, };
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
2
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
3
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
4
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
5
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
6
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
7
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
|
+
});
|
|
9
|
+
};
|
|
10
|
+
import { parse } from "csv-parse";
|
|
11
|
+
import iconv from "iconv-lite";
|
|
12
|
+
import { pipeline } from "stream/promises";
|
|
13
|
+
import { SyncPart } from "../db/types";
|
|
14
|
+
import { prepareOptions, } from "../utils/helpers";
|
|
15
|
+
import { runSyncPart } from "./common";
|
|
16
|
+
import { createReadStream } from "fs";
|
|
17
|
+
import { insertCityPositions } from "../db/cities";
|
|
18
|
+
import { fileURLToPath } from "url";
|
|
19
|
+
import { dirname, join } from "path";
|
|
20
|
+
const importDataToDb = (options) => __awaiter(void 0, void 0, void 0, function* () {
|
|
21
|
+
console.log("Starting to parse CSV file...");
|
|
22
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
23
|
+
const __dirname = dirname(__filename);
|
|
24
|
+
// source: https://github.com/33bcdd/souradnice-mest/blob/master/souradnice.csv
|
|
25
|
+
const csvStream = createReadStream(join(__dirname, "..", "souradnice.csv"));
|
|
26
|
+
const rows = [];
|
|
27
|
+
const parseStream = parse({ delimiter: ",", fromLine: 2 }).on("data", (data) => {
|
|
28
|
+
rows.push(data);
|
|
29
|
+
});
|
|
30
|
+
yield pipeline(csvStream, iconv.decodeStream("utf-8"), parseStream);
|
|
31
|
+
console.log("Parsing completed. Starting to import data to DB...");
|
|
32
|
+
yield insertCityPositions(rows);
|
|
33
|
+
console.log(`Import completed. Total imported rows: ${rows.length}`);
|
|
34
|
+
});
|
|
35
|
+
export const importCities = (options = {}) => __awaiter(void 0, void 0, void 0, function* () {
|
|
36
|
+
yield runSyncPart(SyncPart.Regions, [], () => __awaiter(void 0, void 0, void 0, function* () {
|
|
37
|
+
const completeOptions = prepareOptions(options);
|
|
38
|
+
yield importDataToDb(completeOptions);
|
|
39
|
+
}));
|
|
40
|
+
});
|