@mailwoman/resolver-wof-sqlite 9.1.0 → 9.3.0
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/README.md +36 -20
- package/lib/address/index.ts +9 -0
- package/{address-point-interpolation.ts → lib/address/point-interpolation.ts} +40 -28
- package/{address-point-schema.ts → lib/address/point-schema.ts} +34 -8
- package/lib/address/point.ts +280 -0
- package/{ancestry-backfill.ts → lib/ancestry/backfill.ts} +14 -19
- package/{ancestry.ts → lib/ancestry/index.ts} +13 -8
- package/{build-candidate.ts → lib/build-candidate.ts} +243 -199
- package/{build-slim.ts → lib/build-slim.ts} +153 -168
- package/lib/candidate/alias-bags.ts +56 -0
- package/lib/candidate/ancestors-sidecar.ts +204 -0
- package/lib/candidate/country-display-names.ts +79 -0
- package/lib/candidate/extract-fold.ts +138 -0
- package/lib/candidate/name-roles.ts +238 -0
- package/lib/candidate/own-name.ts +146 -0
- package/lib/candidate/place-attrs.ts +44 -0
- package/lib/candidate-ancestors-schema.ts +195 -0
- package/{candidate-fts.ts → lib/candidate-fts.ts} +7 -5
- package/{candidate-importance.ts → lib/candidate-importance.ts} +54 -57
- package/lib/candidate-lookup.ts +976 -0
- package/{candidate-schema.ts → lib/candidate-schema.ts} +34 -6
- package/lib/candidate-scoring.ts +261 -0
- package/lib/capital-schema.ts +89 -0
- package/lib/capitals.ts +148 -0
- package/{coincident-roles.ts → lib/coincident-roles.ts} +75 -19
- package/{convention.ts → lib/convention/index.ts} +5 -5
- package/lib/convention/schema.ts +72 -0
- package/{coverage-manifest-schema.ts → lib/coverage-manifest-schema.ts} +15 -16
- package/lib/currency-backfill.ts +334 -0
- package/lib/env.ts +50 -0
- package/lib/exact-match.ts +113 -0
- package/{sharding.ts → lib/extracts.ts} +63 -60
- package/lib/fst/autocomplete.ts +176 -0
- package/{fst-builder.ts → lib/fst/builder.ts} +30 -27
- package/{fst-deserialize-web.ts → lib/fst/deserialize-web.ts} +27 -87
- package/lib/fst/format.ts +106 -0
- package/{fst-freshness.ts → lib/fst/freshness.ts} +42 -75
- package/lib/fst/index.ts +14 -0
- package/{fst-matcher.ts → lib/fst/matcher.ts} +1 -1
- package/{fst-serialize.ts → lib/fst/serialize.ts} +37 -115
- package/{fst-types.ts → lib/fst/types.ts} +4 -2
- package/{fts.ts → lib/fts/index.ts} +28 -23
- package/{fts-query.ts → lib/fts/query.ts} +2 -2
- package/{geonames-aliases.ts → lib/geonames/aliases.ts} +13 -13
- package/lib/geonames/index.ts +8 -0
- package/{geonames-postal.ts → lib/geonames/postal.ts} +16 -15
- package/{index.ts → lib/index.ts} +52 -48
- package/{interpolation.ts → lib/interpolation.ts} +137 -41
- package/lib/lookup.ts +861 -0
- package/{name-score.ts → lib/name-score.ts} +6 -4
- package/lib/nsul/index.ts +8 -0
- package/lib/nsul/lookup.ts +144 -0
- package/lib/nsul/schema.ts +130 -0
- package/{place-importance-schema.ts → lib/place-importance-schema.ts} +70 -22
- package/lib/poi/index.ts +8 -0
- package/{poi-lookup.ts → lib/poi/lookup.ts} +32 -39
- package/{poi-schema.ts → lib/poi/schema.ts} +10 -6
- package/lib/polygon-schema.ts +47 -0
- package/{postal-city-alias-lookup.ts → lib/postal/city-alias-lookup.ts} +15 -21
- package/{postal-city-candidate-schema.ts → lib/postal/city-candidate-schema.ts} +4 -2
- package/lib/postal/index.ts +9 -0
- package/{postcode-point-lookup.ts → lib/postcode-point-lookup.ts} +17 -15
- package/lib/primary-preference.ts +226 -0
- package/lib/proximity-rerank.ts +120 -0
- package/{ranking-weights.ts → lib/ranking-weights.ts} +30 -4
- package/lib/region-keys.ts +144 -0
- package/{reverse.ts → lib/reverse.ts} +45 -56
- package/{schema.ts → lib/schema.ts} +11 -1
- package/lib/search-fetch.ts +257 -0
- package/{sqlite-convention-source.ts → lib/sqlite-convention-source.ts} +9 -10
- package/lib/sqlite-utils.ts +83 -0
- package/{street-centroid-schema.ts → lib/street/centroid-schema.ts} +12 -6
- package/{street-centroid.ts → lib/street/centroid.ts} +26 -28
- package/lib/street/index.ts +13 -0
- package/{street-morphology-fst-builder.ts → lib/street/morphology-fst-builder.ts} +24 -14
- package/{street-morphology-fst-loader.ts → lib/street/morphology-fst-loader.ts} +14 -12
- package/{street-name-lookup.ts → lib/street/name-lookup.ts} +14 -30
- package/lib/street/normalize.ts +572 -0
- package/{street-segment-schema.ts → lib/street/segment-schema.ts} +13 -8
- package/{types.ts → lib/types.ts} +49 -9
- package/{unified-schema.ts → lib/unified-schema.ts} +21 -25
- package/lib/uprn/existence.ts +84 -0
- package/lib/uprn/index.ts +9 -0
- package/lib/uprn/lookup.ts +206 -0
- package/lib/uprn/schema.ts +124 -0
- package/lib/weights-overlay-linker.ts +878 -0
- package/out/address/index.d.ts +9 -0
- package/out/address/index.d.ts.map +1 -0
- package/out/address/index.js +9 -0
- package/out/address/index.js.map +1 -0
- package/out/{address-point-interpolation.d.ts → address/point-interpolation.d.ts} +11 -10
- package/out/address/point-interpolation.d.ts.map +1 -0
- package/out/{address-point-interpolation.js → address/point-interpolation.js} +29 -23
- package/out/address/point-interpolation.js.map +1 -0
- package/out/{address-point-schema.d.ts → address/point-schema.d.ts} +30 -10
- package/out/address/point-schema.d.ts.map +1 -0
- package/out/{address-point-schema.js → address/point-schema.js} +7 -3
- package/out/address/point-schema.js.map +1 -0
- package/out/{address-point.d.ts → address/point.d.ts} +16 -8
- package/out/address/point.d.ts.map +1 -0
- package/out/address/point.js +191 -0
- package/out/address/point.js.map +1 -0
- package/out/{ancestry-backfill.d.ts → ancestry/backfill.d.ts} +7 -5
- package/out/ancestry/backfill.d.ts.map +1 -0
- package/out/{ancestry-backfill.js → ancestry/backfill.js} +12 -16
- package/out/ancestry/backfill.js.map +1 -0
- package/out/{ancestry.d.ts → ancestry/index.d.ts} +6 -5
- package/out/ancestry/index.d.ts.map +1 -0
- package/out/{ancestry.js → ancestry/index.js} +7 -7
- package/out/ancestry/index.js.map +1 -0
- package/out/build-candidate.d.ts +88 -7
- package/out/build-candidate.d.ts.map +1 -1
- package/out/build-candidate.js +145 -149
- package/out/build-candidate.js.map +1 -1
- package/out/build-slim.d.ts +5 -5
- package/out/build-slim.d.ts.map +1 -1
- package/out/build-slim.js +127 -142
- package/out/build-slim.js.map +1 -1
- package/out/candidate/alias-bags.d.ts +19 -0
- package/out/candidate/alias-bags.d.ts.map +1 -0
- package/out/candidate/alias-bags.js +39 -0
- package/out/candidate/alias-bags.js.map +1 -0
- package/out/candidate/ancestors-sidecar.d.ts +32 -0
- package/out/candidate/ancestors-sidecar.d.ts.map +1 -0
- package/out/candidate/ancestors-sidecar.js +140 -0
- package/out/candidate/ancestors-sidecar.js.map +1 -0
- package/out/candidate/country-display-names.d.ts +35 -0
- package/out/candidate/country-display-names.d.ts.map +1 -0
- package/out/candidate/country-display-names.js +59 -0
- package/out/candidate/country-display-names.js.map +1 -0
- package/out/candidate/extract-fold.d.ts +32 -0
- package/out/candidate/extract-fold.d.ts.map +1 -0
- package/out/candidate/extract-fold.js +104 -0
- package/out/candidate/extract-fold.js.map +1 -0
- package/out/candidate/name-roles.d.ts +57 -0
- package/out/candidate/name-roles.d.ts.map +1 -0
- package/out/candidate/name-roles.js +166 -0
- package/out/candidate/name-roles.js.map +1 -0
- package/out/candidate/own-name.d.ts +50 -0
- package/out/candidate/own-name.d.ts.map +1 -0
- package/out/candidate/own-name.js +132 -0
- package/out/candidate/own-name.js.map +1 -0
- package/out/candidate/place-attrs.d.ts +43 -0
- package/out/candidate/place-attrs.d.ts.map +1 -0
- package/out/candidate/place-attrs.js +15 -0
- package/out/candidate/place-attrs.js.map +1 -0
- package/out/candidate-ancestors-schema.d.ts +150 -0
- package/out/candidate-ancestors-schema.d.ts.map +1 -0
- package/out/candidate-ancestors-schema.js +123 -0
- package/out/candidate-ancestors-schema.js.map +1 -0
- package/out/candidate-fts.d.ts +7 -5
- package/out/candidate-fts.d.ts.map +1 -1
- package/out/candidate-fts.js +5 -3
- package/out/candidate-fts.js.map +1 -1
- package/out/candidate-importance.d.ts +16 -16
- package/out/candidate-importance.d.ts.map +1 -1
- package/out/candidate-importance.js +47 -52
- package/out/candidate-importance.js.map +1 -1
- package/out/candidate-lookup.d.ts +31 -52
- package/out/candidate-lookup.d.ts.map +1 -1
- package/out/candidate-lookup.js +380 -172
- package/out/candidate-lookup.js.map +1 -1
- package/out/candidate-schema.d.ts +31 -7
- package/out/candidate-schema.d.ts.map +1 -1
- package/out/candidate-schema.js +3 -0
- package/out/candidate-schema.js.map +1 -1
- package/out/candidate-scoring.d.ts +34 -0
- package/out/candidate-scoring.d.ts.map +1 -0
- package/out/candidate-scoring.js +196 -0
- package/out/candidate-scoring.js.map +1 -0
- package/out/capital-schema.d.ts +51 -0
- package/out/capital-schema.d.ts.map +1 -0
- package/out/capital-schema.js +63 -0
- package/out/capital-schema.js.map +1 -0
- package/out/capitals.d.ts +69 -0
- package/out/capitals.d.ts.map +1 -0
- package/out/capitals.js +98 -0
- package/out/capitals.js.map +1 -0
- package/out/coincident-roles.d.ts +12 -4
- package/out/coincident-roles.d.ts.map +1 -1
- package/out/coincident-roles.js +43 -11
- package/out/coincident-roles.js.map +1 -1
- package/out/{convention.d.ts → convention/index.d.ts} +5 -5
- package/out/convention/index.d.ts.map +1 -0
- package/out/{convention.js → convention/index.js} +4 -4
- package/out/convention/index.js.map +1 -0
- package/out/convention/schema.d.ts +51 -0
- package/out/convention/schema.d.ts.map +1 -0
- package/out/convention/schema.js +34 -0
- package/out/convention/schema.js.map +1 -0
- package/out/coverage-manifest-schema.d.ts +8 -8
- package/out/coverage-manifest-schema.d.ts.map +1 -1
- package/out/coverage-manifest-schema.js +6 -10
- package/out/coverage-manifest-schema.js.map +1 -1
- package/out/currency-backfill.d.ts +90 -0
- package/out/currency-backfill.d.ts.map +1 -0
- package/out/currency-backfill.js +196 -0
- package/out/currency-backfill.js.map +1 -0
- package/out/env.d.ts +43 -0
- package/out/env.d.ts.map +1 -0
- package/out/env.js +48 -0
- package/out/env.js.map +1 -0
- package/out/exact-match.d.ts +25 -0
- package/out/exact-match.d.ts.map +1 -0
- package/out/exact-match.js +88 -0
- package/out/exact-match.js.map +1 -0
- package/out/extracts.d.ts +114 -0
- package/out/extracts.d.ts.map +1 -0
- package/out/{sharding.js → extracts.js} +38 -38
- package/out/extracts.js.map +1 -0
- package/out/{fst-autocomplete.d.ts → fst/autocomplete.d.ts} +13 -13
- package/out/fst/autocomplete.d.ts.map +1 -0
- package/out/fst/autocomplete.js +113 -0
- package/out/fst/autocomplete.js.map +1 -0
- package/out/{fst-builder.d.ts → fst/builder.d.ts} +5 -5
- package/out/fst/builder.d.ts.map +1 -0
- package/out/{fst-builder.js → fst/builder.js} +24 -24
- package/out/fst/builder.js.map +1 -0
- package/out/{fst-deserialize-web.d.ts → fst/deserialize-web.d.ts} +3 -3
- package/out/fst/deserialize-web.d.ts.map +1 -0
- package/out/{fst-deserialize-web.js → fst/deserialize-web.js} +10 -74
- package/out/fst/deserialize-web.js.map +1 -0
- package/out/fst/format.d.ts +80 -0
- package/out/fst/format.d.ts.map +1 -0
- package/out/fst/format.js +91 -0
- package/out/fst/format.js.map +1 -0
- package/out/{fst-freshness.d.ts → fst/freshness.d.ts} +11 -14
- package/out/fst/freshness.d.ts.map +1 -0
- package/out/{fst-freshness.js → fst/freshness.js} +42 -74
- package/out/fst/freshness.js.map +1 -0
- package/out/fst/index.d.ts +14 -0
- package/out/fst/index.d.ts.map +1 -0
- package/out/fst/index.js +14 -0
- package/out/fst/index.js.map +1 -0
- package/out/{fst-matcher.d.ts → fst/matcher.d.ts} +2 -2
- package/out/fst/matcher.d.ts.map +1 -0
- package/out/{fst-matcher.js → fst/matcher.js} +1 -1
- package/out/fst/matcher.js.map +1 -0
- package/out/{fst-serialize.d.ts → fst/serialize.d.ts} +5 -10
- package/out/fst/serialize.d.ts.map +1 -0
- package/out/{fst-serialize.js → fst/serialize.js} +18 -98
- package/out/fst/serialize.js.map +1 -0
- package/out/{fst-types.d.ts → fst/types.d.ts} +4 -3
- package/out/fst/types.d.ts.map +1 -0
- package/out/{fst-types.js → fst/types.js} +1 -1
- package/out/fst/types.js.map +1 -0
- package/out/{fts.d.ts → fts/index.d.ts} +20 -13
- package/out/fts/index.d.ts.map +1 -0
- package/out/{fts.js → fts/index.js} +20 -15
- package/out/fts/index.js.map +1 -0
- package/out/{fts-query.d.ts → fts/query.d.ts} +2 -2
- package/out/fts/query.d.ts.map +1 -0
- package/out/{fts-query.js → fts/query.js} +2 -2
- package/out/fts/query.js.map +1 -0
- package/out/{geonames-aliases.d.ts → geonames/aliases.d.ts} +8 -6
- package/out/geonames/aliases.d.ts.map +1 -0
- package/out/{geonames-aliases.js → geonames/aliases.js} +7 -7
- package/out/geonames/aliases.js.map +1 -0
- package/out/geonames/index.d.ts +8 -0
- package/out/geonames/index.d.ts.map +1 -0
- package/out/geonames/index.js +8 -0
- package/out/geonames/index.js.map +1 -0
- package/out/{geonames-postal.d.ts → geonames/postal.d.ts} +12 -10
- package/out/geonames/postal.d.ts.map +1 -0
- package/out/{geonames-postal.js → geonames/postal.js} +11 -11
- package/out/geonames/postal.js.map +1 -0
- package/out/index.d.ts +32 -31
- package/out/index.d.ts.map +1 -1
- package/out/index.js +24 -24
- package/out/index.js.map +1 -1
- package/out/interpolation.d.ts +18 -9
- package/out/interpolation.d.ts.map +1 -1
- package/out/interpolation.js +108 -36
- package/out/interpolation.js.map +1 -1
- package/out/lookup.d.ts +25 -25
- package/out/lookup.d.ts.map +1 -1
- package/out/lookup.js +174 -558
- package/out/lookup.js.map +1 -1
- package/out/name-score.d.ts +0 -10
- package/out/name-score.d.ts.map +1 -1
- package/out/name-score.js +6 -4
- package/out/name-score.js.map +1 -1
- package/out/nsul/index.d.ts +8 -0
- package/out/nsul/index.d.ts.map +1 -0
- package/out/nsul/index.js +8 -0
- package/out/nsul/index.js.map +1 -0
- package/out/nsul/lookup.d.ts +83 -0
- package/out/nsul/lookup.d.ts.map +1 -0
- package/out/nsul/lookup.js +80 -0
- package/out/nsul/lookup.js.map +1 -0
- package/out/nsul/schema.d.ts +100 -0
- package/out/nsul/schema.d.ts.map +1 -0
- package/out/nsul/schema.js +78 -0
- package/out/nsul/schema.js.map +1 -0
- package/out/place-importance-schema.d.ts +47 -10
- package/out/place-importance-schema.d.ts.map +1 -1
- package/out/place-importance-schema.js +56 -10
- package/out/place-importance-schema.js.map +1 -1
- package/out/poi/index.d.ts +8 -0
- package/out/poi/index.d.ts.map +1 -0
- package/out/poi/index.js +8 -0
- package/out/poi/index.js.map +1 -0
- package/out/{poi-lookup.d.ts → poi/lookup.d.ts} +8 -10
- package/out/poi/lookup.d.ts.map +1 -0
- package/out/{poi-lookup.js → poi/lookup.js} +24 -29
- package/out/poi/lookup.js.map +1 -0
- package/out/{poi-schema.d.ts → poi/schema.d.ts} +10 -6
- package/out/poi/schema.d.ts.map +1 -0
- package/out/{poi-schema.js → poi/schema.js} +1 -1
- package/out/poi/schema.js.map +1 -0
- package/out/polygon-schema.d.ts +37 -0
- package/out/polygon-schema.d.ts.map +1 -0
- package/out/polygon-schema.js +23 -0
- package/out/polygon-schema.js.map +1 -0
- package/out/{postal-city-alias-lookup.d.ts → postal/city-alias-lookup.d.ts} +7 -6
- package/out/postal/city-alias-lookup.d.ts.map +1 -0
- package/out/{postal-city-alias-lookup.js → postal/city-alias-lookup.js} +12 -16
- package/out/postal/city-alias-lookup.js.map +1 -0
- package/out/{postal-city-alias-schema.d.ts → postal/city-alias-schema.d.ts} +1 -1
- package/out/{postal-city-alias-schema.d.ts.map → postal/city-alias-schema.d.ts.map} +1 -1
- package/out/{postal-city-alias-schema.js → postal/city-alias-schema.js} +1 -1
- package/out/{postal-city-alias-schema.js.map → postal/city-alias-schema.js.map} +1 -1
- package/out/{postal-city-candidate-schema.d.ts → postal/city-candidate-schema.d.ts} +4 -3
- package/out/postal/city-candidate-schema.d.ts.map +1 -0
- package/out/{postal-city-candidate-schema.js → postal/city-candidate-schema.js} +2 -2
- package/out/{postal-city-candidate-schema.js.map → postal/city-candidate-schema.js.map} +1 -1
- package/out/postal/index.d.ts +9 -0
- package/out/postal/index.d.ts.map +1 -0
- package/out/postal/index.js +9 -0
- package/out/postal/index.js.map +1 -0
- package/out/postcode-point-lookup.d.ts +10 -10
- package/out/postcode-point-lookup.d.ts.map +1 -1
- package/out/postcode-point-lookup.js +13 -13
- package/out/postcode-point-lookup.js.map +1 -1
- package/out/primary-preference.d.ts +133 -0
- package/out/primary-preference.d.ts.map +1 -0
- package/out/primary-preference.js +146 -0
- package/out/primary-preference.js.map +1 -0
- package/out/proximity-rerank.d.ts +77 -0
- package/out/proximity-rerank.d.ts.map +1 -0
- package/out/proximity-rerank.js +86 -0
- package/out/proximity-rerank.js.map +1 -0
- package/out/ranking-weights.d.ts +15 -3
- package/out/ranking-weights.d.ts.map +1 -1
- package/out/ranking-weights.js +21 -3
- package/out/ranking-weights.js.map +1 -1
- package/out/region-keys.d.ts +47 -0
- package/out/region-keys.d.ts.map +1 -0
- package/out/region-keys.js +121 -0
- package/out/region-keys.js.map +1 -0
- package/out/reverse.d.ts +6 -6
- package/out/reverse.d.ts.map +1 -1
- package/out/reverse.js +23 -35
- package/out/reverse.js.map +1 -1
- package/out/schema.d.ts +10 -1
- package/out/schema.d.ts.map +1 -1
- package/out/schema.js.map +1 -1
- package/out/search-fetch.d.ts +59 -0
- package/out/search-fetch.d.ts.map +1 -0
- package/out/search-fetch.js +184 -0
- package/out/search-fetch.js.map +1 -0
- package/out/sqlite-convention-source.d.ts +7 -7
- package/out/sqlite-convention-source.d.ts.map +1 -1
- package/out/sqlite-convention-source.js +5 -5
- package/out/sqlite-convention-source.js.map +1 -1
- package/out/sqlite-utils.d.ts +24 -6
- package/out/sqlite-utils.d.ts.map +1 -1
- package/out/sqlite-utils.js +24 -7
- package/out/sqlite-utils.js.map +1 -1
- package/out/{street-centroid-schema.d.ts → street/centroid-schema.d.ts} +12 -7
- package/out/street/centroid-schema.d.ts.map +1 -0
- package/out/{street-centroid-schema.js → street/centroid-schema.js} +5 -5
- package/out/{street-centroid-schema.js.map → street/centroid-schema.js.map} +1 -1
- package/out/{street-centroid.d.ts → street/centroid.d.ts} +6 -6
- package/out/street/centroid.d.ts.map +1 -0
- package/out/{street-centroid.js → street/centroid.js} +18 -24
- package/out/street/centroid.js.map +1 -0
- package/out/street/index.d.ts +13 -0
- package/out/street/index.d.ts.map +1 -0
- package/out/street/index.js +13 -0
- package/out/street/index.js.map +1 -0
- package/out/{street-morphology-fst-builder.d.ts → street/morphology-fst-builder.d.ts} +4 -4
- package/out/street/morphology-fst-builder.d.ts.map +1 -0
- package/out/{street-morphology-fst-builder.js → street/morphology-fst-builder.js} +18 -13
- package/out/street/morphology-fst-builder.js.map +1 -0
- package/out/{street-morphology-fst-loader.d.ts → street/morphology-fst-loader.d.ts} +5 -5
- package/out/street/morphology-fst-loader.d.ts.map +1 -0
- package/out/{street-morphology-fst-loader.js → street/morphology-fst-loader.js} +11 -10
- package/out/street/morphology-fst-loader.js.map +1 -0
- package/out/{street-name-lookup.d.ts → street/name-lookup.d.ts} +4 -7
- package/out/street/name-lookup.d.ts.map +1 -0
- package/out/{street-name-lookup.js → street/name-lookup.js} +9 -23
- package/out/street/name-lookup.js.map +1 -0
- package/out/street/normalize.d.ts +179 -0
- package/out/street/normalize.d.ts.map +1 -0
- package/out/street/normalize.js +457 -0
- package/out/street/normalize.js.map +1 -0
- package/out/{street-segment-schema.d.ts → street/segment-schema.d.ts} +13 -9
- package/out/street/segment-schema.d.ts.map +1 -0
- package/out/{street-segment-schema.js → street/segment-schema.js} +4 -4
- package/out/{street-segment-schema.js.map → street/segment-schema.js.map} +1 -1
- package/out/types.d.ts +49 -9
- package/out/types.d.ts.map +1 -1
- package/out/types.js.map +1 -1
- package/out/unified-schema.d.ts +6 -5
- package/out/unified-schema.d.ts.map +1 -1
- package/out/unified-schema.js +16 -19
- package/out/unified-schema.js.map +1 -1
- package/out/uprn/existence.d.ts +53 -0
- package/out/uprn/existence.d.ts.map +1 -0
- package/out/uprn/existence.js +61 -0
- package/out/uprn/existence.js.map +1 -0
- package/out/uprn/index.d.ts +9 -0
- package/out/uprn/index.d.ts.map +1 -0
- package/out/uprn/index.js +9 -0
- package/out/uprn/index.js.map +1 -0
- package/out/uprn/lookup.d.ts +85 -0
- package/out/uprn/lookup.d.ts.map +1 -0
- package/out/uprn/lookup.js +149 -0
- package/out/uprn/lookup.js.map +1 -0
- package/out/uprn/schema.d.ts +93 -0
- package/out/uprn/schema.d.ts.map +1 -0
- package/out/uprn/schema.js +78 -0
- package/out/uprn/schema.js.map +1 -0
- package/out/weights-overlay-linker.d.ts +299 -0
- package/out/weights-overlay-linker.d.ts.map +1 -0
- package/out/weights-overlay-linker.js +511 -0
- package/out/weights-overlay-linker.js.map +1 -0
- package/package.json +622 -154
- package/address-point.ts +0 -125
- package/candidate-lookup.ts +0 -720
- package/fst-autocomplete.ts +0 -204
- package/geo.ts +0 -121
- package/lookup.ts +0 -1354
- package/out/address-point-interpolation.d.ts.map +0 -1
- package/out/address-point-interpolation.js.map +0 -1
- package/out/address-point-schema.d.ts.map +0 -1
- package/out/address-point-schema.js.map +0 -1
- package/out/address-point.d.ts.map +0 -1
- package/out/address-point.js +0 -84
- package/out/address-point.js.map +0 -1
- package/out/ancestry-backfill.d.ts.map +0 -1
- package/out/ancestry-backfill.js.map +0 -1
- package/out/ancestry.d.ts.map +0 -1
- package/out/ancestry.js.map +0 -1
- package/out/convention.d.ts.map +0 -1
- package/out/convention.js.map +0 -1
- package/out/fst-autocomplete.d.ts.map +0 -1
- package/out/fst-autocomplete.js +0 -130
- package/out/fst-autocomplete.js.map +0 -1
- package/out/fst-builder.d.ts.map +0 -1
- package/out/fst-builder.js.map +0 -1
- package/out/fst-deserialize-web.d.ts.map +0 -1
- package/out/fst-deserialize-web.js.map +0 -1
- package/out/fst-freshness.d.ts.map +0 -1
- package/out/fst-freshness.js.map +0 -1
- package/out/fst-matcher.d.ts.map +0 -1
- package/out/fst-matcher.js.map +0 -1
- package/out/fst-serialize.d.ts.map +0 -1
- package/out/fst-serialize.js.map +0 -1
- package/out/fst-types.d.ts.map +0 -1
- package/out/fst-types.js.map +0 -1
- package/out/fts-query.d.ts.map +0 -1
- package/out/fts-query.js.map +0 -1
- package/out/fts.d.ts.map +0 -1
- package/out/fts.js.map +0 -1
- package/out/geo.d.ts +0 -74
- package/out/geo.d.ts.map +0 -1
- package/out/geo.js +0 -71
- package/out/geo.js.map +0 -1
- package/out/geonames-aliases.d.ts.map +0 -1
- package/out/geonames-aliases.js.map +0 -1
- package/out/geonames-postal.d.ts.map +0 -1
- package/out/geonames-postal.js.map +0 -1
- package/out/poi-lookup.d.ts.map +0 -1
- package/out/poi-lookup.js.map +0 -1
- package/out/poi-schema.d.ts.map +0 -1
- package/out/poi-schema.js.map +0 -1
- package/out/postal-city-alias-lookup.d.ts.map +0 -1
- package/out/postal-city-alias-lookup.js.map +0 -1
- package/out/postal-city-candidate-schema.d.ts.map +0 -1
- package/out/sharding.d.ts +0 -114
- package/out/sharding.d.ts.map +0 -1
- package/out/sharding.js.map +0 -1
- package/out/street-centroid-schema.d.ts.map +0 -1
- package/out/street-centroid.d.ts.map +0 -1
- package/out/street-centroid.js.map +0 -1
- package/out/street-morphology-fst-builder.d.ts.map +0 -1
- package/out/street-morphology-fst-builder.js.map +0 -1
- package/out/street-morphology-fst-loader.d.ts.map +0 -1
- package/out/street-morphology-fst-loader.js.map +0 -1
- package/out/street-name-lookup.d.ts.map +0 -1
- package/out/street-name-lookup.js.map +0 -1
- package/out/street-normalize.d.ts +0 -95
- package/out/street-normalize.d.ts.map +0 -1
- package/out/street-normalize.js +0 -272
- package/out/street-normalize.js.map +0 -1
- package/out/street-segment-schema.d.ts.map +0 -1
- package/sqlite-utils.ts +0 -46
- package/street-normalize.ts +0 -318
- /package/{postal-city-alias-schema.ts → lib/postal/city-alias-schema.ts} +0 -0
package/README.md
CHANGED
|
@@ -15,11 +15,11 @@ Requires Node 22+ for built-in `node:sqlite`.
|
|
|
15
15
|
## Quick start
|
|
16
16
|
|
|
17
17
|
```ts
|
|
18
|
-
import {
|
|
18
|
+
import { WOFSQLitePlaceLookup } from "@mailwoman/resolver-wof-sqlite"
|
|
19
19
|
|
|
20
|
-
|
|
20
|
+
using lookup = new WOFSQLitePlaceLookup({
|
|
21
21
|
databasePath: "/path/to/whosonfirst-data-admin-us-latest.db",
|
|
22
|
-
|
|
22
|
+
buildFTS: true, // build the FTS5 index on first open (one-time cost)
|
|
23
23
|
})
|
|
24
24
|
|
|
25
25
|
const candidates = await lookup.findPlace({
|
|
@@ -31,42 +31,59 @@ const candidates = await lookup.findPlace({
|
|
|
31
31
|
for (const c of candidates) {
|
|
32
32
|
console.log(c.id, c.name, c.country, c.lat, c.lon, "score:", c.score)
|
|
33
33
|
}
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
## A database that cannot answer says so on construction
|
|
37
|
+
|
|
38
|
+
Databases are `ATTACH`ed by a schema name **derived from the filename**, and queries route to them by matching that name against the requested placetype — `postalcode_us` serves `postalcode`. Two ways that used to fail without logging, and both now throw when you build the lookup:
|
|
39
|
+
|
|
40
|
+
- The name does not route. `postcode-ca-overture.db` derives `postcode_ca_overture`, and the router tests `startsWith("postalcode_")` — **"postcode" is not "postalcode"**. It held 843,739 Canadian codes and answered every query with zero hits, which is indistinguishable from "this country has no places".
|
|
41
|
+
- The database carries `spr` but no `place_search`. It routes, then dies mid-`SELECT`.
|
|
34
42
|
|
|
35
|
-
lookup.
|
|
43
|
+
The predicate is the **table, not the filename**: a database carrying `spr` is claiming to be a place database, and every lookup path here reaches the FTS index. A relation-table database like `postcode-locality-<cc>.db` carries no `spr`, never makes that claim, and is exempt — which is what keeps the documented default database list working.
|
|
44
|
+
|
|
45
|
+
```
|
|
46
|
+
WOFSQLitePlaceLookup: …/postcode-ca-overture.db carries "spr" but no "place_search" table, so it
|
|
47
|
+
cannot serve a lookup. Build it with the FTS index, or leave it out — it is usable as a BUILD input
|
|
48
|
+
either way. Its schema name "postcode_ca_overture" also matches no routed placetype (postalcode,
|
|
49
|
+
locality, region, county, country, venue), so it would never have been queried even with the table
|
|
50
|
+
— check the filename's spelling.
|
|
36
51
|
```
|
|
37
52
|
|
|
38
|
-
|
|
53
|
+
The second sentence appears only when the name routes nowhere. It is the half that turns zero hits into a diagnosis.
|
|
54
|
+
|
|
55
|
+
## Multiple databases (admin + postcode in one connection)
|
|
39
56
|
|
|
40
|
-
Pass an array of paths to open multiple WOF
|
|
57
|
+
Pass an array of paths to open multiple WOF databases on a single connection — each is opened as a
|
|
41
58
|
separate SQLite schema via `ATTACH DATABASE`. Schema names auto-derive from filenames
|
|
42
59
|
(`whosonfirst-data-admin-us-latest.db` → `admin_us`, `whosonfirst-data-postalcode-us-latest.db` →
|
|
43
60
|
`postalcode_us`). Queries route by `placetype` — a `postalcode` query goes to the
|
|
44
|
-
`postalcode_us`
|
|
61
|
+
`postalcode_us` database automatically, everything else hits main.
|
|
45
62
|
|
|
46
63
|
```ts
|
|
47
|
-
const lookup = new
|
|
64
|
+
const lookup = new WOFSQLitePlaceLookup({
|
|
48
65
|
databasePath: ["/data/wof/whosonfirst-data-admin-us-latest.db", "/data/wof/whosonfirst-data-postalcode-us-latest.db"],
|
|
49
66
|
})
|
|
50
67
|
|
|
51
|
-
await lookup.findPlace({ text: "Springfield", placetype: "locality" }) // → admin
|
|
52
|
-
await lookup.findPlace({ text: "62701", placetype: "postalcode" }) // → postcode
|
|
68
|
+
await lookup.findPlace({ text: "Springfield", placetype: "locality" }) // → admin extract
|
|
69
|
+
await lookup.findPlace({ text: "62701", placetype: "postalcode" }) // → postcode extract
|
|
53
70
|
```
|
|
54
71
|
|
|
55
72
|
Override schema names or routing explicitly when needed:
|
|
56
73
|
|
|
57
74
|
```ts
|
|
58
|
-
new
|
|
75
|
+
new WOFSQLitePlaceLookup({
|
|
59
76
|
databasePath: ["/data/wof/admin.db", { path: "/data/oddly-named.db", schemaName: "pc", placetypes: ["postalcode"] }],
|
|
60
77
|
})
|
|
61
78
|
```
|
|
62
79
|
|
|
63
|
-
Cross-
|
|
80
|
+
Cross-database `UNION` queries are not supported in one `findPlace` call — BM25 scores aren't
|
|
64
81
|
comparable across separately-indexed corpora. Issue two `findPlace` calls and merge in your
|
|
65
82
|
caller if you need that.
|
|
66
83
|
|
|
67
84
|
## Getting the WOF SQLite distribution
|
|
68
85
|
|
|
69
|
-
The Geocode Earth team mirrors WOF SQLite distributions at <https://data.geocode.earth/wof/dist/sqlite/>. The two relevant
|
|
86
|
+
The Geocode Earth team mirrors WOF SQLite distributions at <https://data.geocode.earth/wof/dist/sqlite/>. The two relevant distributions for v1:
|
|
70
87
|
|
|
71
88
|
| Distribution | Size (bz2) | Use |
|
|
72
89
|
| ---------------------------------------------- | ---------- | ----------------------------------------------------------------- |
|
|
@@ -83,7 +100,7 @@ bunzip2 whosonfirst-data-admin-us-latest.db.bz2
|
|
|
83
100
|
|
|
84
101
|
Upstream WOF SQLite distributions ship a `places` table but **not** an FTS5 index. The resolver needs FTS5 to do fast prefix + token-bag matching. Two options:
|
|
85
102
|
|
|
86
|
-
1. **`
|
|
103
|
+
1. **`buildFTS: true` on construction** — builds the index lazily on first open. Cost is one-time but expensive (~minutes on the full US admin database). Use for prototyping.
|
|
87
104
|
2. **Pre-build the index with `mailwoman gazetteer build fts`** — ship the DB with the index included so first-open is fast. Recommended for production.
|
|
88
105
|
|
|
89
106
|
### `mailwoman gazetteer build fts`
|
|
@@ -143,7 +160,7 @@ What survives in the slim DB:
|
|
|
143
160
|
|
|
144
161
|
What gets dropped: the `geojson` table, which is build-time only — `lookup.ts` never reads it at query time, and it accounts for ~95% of the on-disk size. The `place_population` aux table consumes `wof:population` from geojson before we drop it.
|
|
145
162
|
|
|
146
|
-
`
|
|
163
|
+
`WOFSQLitePlaceLookup` opens the slim DB without any code change. Out-of-set queries (a locality not in the top-K) correctly return zero hits.
|
|
147
164
|
|
|
148
165
|
You can also build the index programmatically via the package's `./fts` subpath:
|
|
149
166
|
|
|
@@ -151,12 +168,11 @@ You can also build the index programmatically via the package's `./fts` subpath:
|
|
|
151
168
|
import { DatabaseSync } from "node:sqlite"
|
|
152
169
|
import { buildPlaceSearchFts } from "@mailwoman/resolver-wof-sqlite/fts"
|
|
153
170
|
|
|
154
|
-
|
|
171
|
+
using db = new DatabaseSync("/path/to/wof.db")
|
|
155
172
|
const { created, indexedRows, durationMs } = buildPlaceSearchFts(db, {
|
|
156
173
|
drop: false,
|
|
157
174
|
onProgress: (phase, detail) => console.log(phase, detail),
|
|
158
175
|
})
|
|
159
|
-
db.close()
|
|
160
176
|
```
|
|
161
177
|
|
|
162
178
|
## Ranking
|
|
@@ -209,7 +225,7 @@ R*Tree because it computes haversine distance against the centroid columns direc
|
|
|
209
225
|
All weights are configurable via the second ctor argument:
|
|
210
226
|
|
|
211
227
|
```ts
|
|
212
|
-
new
|
|
228
|
+
new WOFSQLitePlaceLookup({ databasePath }, { countryMatchBoost: 0.5 })
|
|
213
229
|
```
|
|
214
230
|
|
|
215
231
|
Defaults are in `lookup.ts::DEFAULT_WEIGHTS`.
|
|
@@ -242,11 +258,11 @@ This package itself is AGPL-3.0; the WOF data it indexes is CC-BY 4.0. The two l
|
|
|
242
258
|
|
|
243
259
|
`resolver-wof-sqlite/integration.test.ts` exercises the resolver against a real WOF SQLite distribution. The suite is **skipped** when no DB is present — set `MAILWOMAN_WOF_DB` to override the lookup path, otherwise it defaults to `/mnt/playpen/mailwoman-data/wof/whosonfirst-data-admin-us-latest.db` (the canonical lab location). CI runs against the fixture-only suites; operators with real WOF data locally get an extra layer of validation.
|
|
244
260
|
|
|
245
|
-
Coverage includes: placetype filtering, country filtering, the empty-result case, FTS5 special-character sanitization, Japanese alt-name resolution, parent-constrained lookup, and a performance budget (`findPlace` < 250 ms against the 142 k-row US admin
|
|
261
|
+
Coverage includes: placetype filtering, country filtering, the empty-result case, FTS5 special-character sanitization, Japanese alt-name resolution, parent-constrained lookup, and a performance budget (`findPlace` < 250 ms against the 142 k-row US admin database).
|
|
246
262
|
|
|
247
263
|
## Concurrency model
|
|
248
264
|
|
|
249
|
-
This package opens a single `node:sqlite` connection per `
|
|
265
|
+
This package opens a single `node:sqlite` connection per `WOFSQLitePlaceLookup` instance. SQLite is single-writer / multiple-reader; the Kysely wrapper around the connection serializes all queries through a mutex. For high-concurrency HTTP servers, instantiate one resolver per request handler or per pool slot — sharing a single instance across concurrent requests is safe (queries queue) but won't parallelize across cores.
|
|
250
266
|
|
|
251
267
|
## License
|
|
252
268
|
|
|
@@ -6,13 +6,13 @@
|
|
|
6
6
|
* Address-point interpolation — "Method 2" of the resolution ladder (#483, Phase 1 of
|
|
7
7
|
* `docs/articles/plan/2026-06-11-resolution-ladder.md`): when the exact address-point tier (#476)
|
|
8
8
|
* misses a house number, bracket the number with REAL neighbor points on the same street from the
|
|
9
|
-
* same #476
|
|
10
|
-
* replaces TIGER's uniform-spacing assumption — the dominant error term of the TIGER pilot's
|
|
9
|
+
* same #476 extract and interpolate linearly in house-number space between them. Real occupancy
|
|
10
|
+
* replaces TIGER's uniform-spacing assumption — the dominant error term of the TIGER pilot's check
|
|
11
11
|
* miss; TIGER range interpolation (`StreetInterpolator`) demotes to the fallback for streets too
|
|
12
12
|
* sparse to bracket.
|
|
13
13
|
*
|
|
14
14
|
* Matching key is `street_key` — THE shared normalizer plus the route fold
|
|
15
|
-
* (`canonicalizeRouteKey`), identical at build time (`scripts/build-address-point-
|
|
15
|
+
* (`canonicalizeRouteKey`), identical at build time (`scripts/build-address-point-extract.ts`) and
|
|
16
16
|
* query time, by construction. Scope is postcode-first like the segment tier; a query without a
|
|
17
17
|
* postcode goes straight to the fallback (which carries its own statewide-ambiguity abstention).
|
|
18
18
|
*
|
|
@@ -20,7 +20,7 @@
|
|
|
20
20
|
*
|
|
21
21
|
* - Neighbor candidates NEVER include the queried number itself (any unit/duplicate row of it) — in
|
|
22
22
|
* production the exact tier would already have answered an on-file number, and in the eval
|
|
23
|
-
* this is what makes grading against the same
|
|
23
|
+
* this is what makes grading against the same extract non-circular by construction.
|
|
24
24
|
* - Both-sided bracket (`bracket: "both"`): linear interpolation between the nearest known number
|
|
25
25
|
* below and above; `uncertaintyM` = half the distance between them.
|
|
26
26
|
* - Single-sided (`bracket: "single"`): linear extrapolation along the two nearest known numbers on
|
|
@@ -33,14 +33,14 @@
|
|
|
33
33
|
* Standalone like the segment tier — core wiring rides the Phase 2 ordered `spatialTiers` list.
|
|
34
34
|
*/
|
|
35
35
|
|
|
36
|
-
import { DatabaseSync } from "node:sqlite"
|
|
37
|
-
|
|
38
36
|
import type { InterpolationLookup } from "@mailwoman/resolver"
|
|
37
|
+
import { haversineKm } from "@mailwoman/spatial"
|
|
38
|
+
import { DatabaseClient } from "@mailwoman/sqlite/client"
|
|
39
39
|
|
|
40
|
-
import {
|
|
41
|
-
import type { InterpolatedHit, InterpolationQuery, StreetInterpolator } from "
|
|
42
|
-
import { hasTable } from "
|
|
43
|
-
import { canonicalizeRouteKey,
|
|
40
|
+
import type { AddressPointDatabase } from "#address/point-schema"
|
|
41
|
+
import type { InterpolatedHit, InterpolationQuery, StreetInterpolator } from "#interpolation"
|
|
42
|
+
import { hasTable, prepareAll, type PreparedAll } from "#sqlite-utils"
|
|
43
|
+
import { canonicalizeRouteKey, type RouteKey, streetKeyVariants } from "#street/normalize"
|
|
44
44
|
|
|
45
45
|
/**
|
|
46
46
|
* Extrapolation cap for a single-sided bracket: at most one pair-span beyond the nearest known point (`t = 2`). Past
|
|
@@ -67,31 +67,36 @@ interface NumberAnchor {
|
|
|
67
67
|
release: string
|
|
68
68
|
}
|
|
69
69
|
|
|
70
|
-
export class AddressPointInterpolator
|
|
71
|
-
|
|
72
|
-
|
|
70
|
+
export class AddressPointInterpolator<
|
|
71
|
+
DB extends AddressPointDatabase = AddressPointDatabase,
|
|
72
|
+
> implements InterpolationLookup {
|
|
73
|
+
readonly #db: DatabaseClient<DB>
|
|
74
|
+
/**
|
|
75
|
+
* Resources this instance opened. A connection handed in by a caller is NOT in here, so disposal cannot reach it —
|
|
76
|
+
* ownership is membership rather than a flag a later branch has to check.
|
|
77
|
+
*/
|
|
78
|
+
readonly #resources = new DisposableStack()
|
|
73
79
|
readonly #fallback: StreetInterpolator | undefined
|
|
74
|
-
readonly #byPostcode:
|
|
80
|
+
readonly #byPostcode: PreparedAll<[postcode: string, street: RouteKey, number: number], PointRow> | undefined
|
|
75
81
|
|
|
76
|
-
constructor(opts: { dbPath?: string; database?:
|
|
82
|
+
constructor(opts: { dbPath?: string; database?: DatabaseClient<DB>; fallback?: StreetInterpolator }) {
|
|
77
83
|
if (opts.database) {
|
|
78
84
|
this.#db = opts.database
|
|
79
|
-
this.#ownsDB = false
|
|
80
85
|
} else if (opts.dbPath) {
|
|
81
|
-
this.#db = new
|
|
82
|
-
this.#ownsDB = true
|
|
86
|
+
this.#db = this.#resources.use(new DatabaseClient<DB>(opts.dbPath, { readOnly: true }))
|
|
83
87
|
} else {
|
|
84
88
|
throw new Error("AddressPointInterpolator: one of dbPath or database is required")
|
|
85
89
|
}
|
|
86
90
|
|
|
87
91
|
this.#fallback = opts.fallback
|
|
88
92
|
|
|
89
|
-
// Degrade gracefully on an empty/tableless
|
|
93
|
+
// Degrade gracefully on an empty/tableless extract (#568): with no `address_point` table this tier
|
|
90
94
|
// is skipped, deferring to the segment fallback rather than crashing at construction.
|
|
91
95
|
if (hasTable(this.#db, "address_point")) {
|
|
92
96
|
// Strictly-numeric neighbor numbers on the route-folded street key within the ZIP. The
|
|
93
97
|
// queried number itself is excluded HERE (see module doc: non-circular by construction).
|
|
94
|
-
this.#byPostcode =
|
|
98
|
+
this.#byPostcode = prepareAll(
|
|
99
|
+
this.#db,
|
|
95
100
|
`SELECT CAST(number AS INTEGER) AS n, lat, lon, source, release
|
|
96
101
|
FROM address_point
|
|
97
102
|
WHERE postcode = ? AND street_key = ?
|
|
@@ -102,25 +107,32 @@ export class AddressPointInterpolator implements InterpolationLookup {
|
|
|
102
107
|
}
|
|
103
108
|
|
|
104
109
|
find(query: InterpolationQuery): InterpolatedHit | null {
|
|
105
|
-
const streetKey = canonicalizeRouteKey(normalizeStreetForKey(query.street))
|
|
106
110
|
const numberRaw = query.number.trim()
|
|
107
111
|
|
|
108
|
-
if (
|
|
112
|
+
if (!/^\d+$/.test(numberRaw)) return null
|
|
109
113
|
const n = Number(numberRaw)
|
|
110
114
|
|
|
111
|
-
// No own table (empty
|
|
115
|
+
// No own table (empty extract) or no postcode → defer to the segment fallback rather than query.
|
|
112
116
|
if (!this.#byPostcode || !query.postcode) return this.#fallback?.find(query) ?? null
|
|
113
117
|
|
|
114
|
-
|
|
118
|
+
// Key-variant ladder (see `streetKeyVariants`) — same probe order as the exact-point reader.
|
|
119
|
+
let rows: PointRow[] = []
|
|
120
|
+
|
|
121
|
+
for (const variant of streetKeyVariants(query.street)) {
|
|
122
|
+
const streetKey = canonicalizeRouteKey(variant)
|
|
123
|
+
|
|
124
|
+
rows = this.#byPostcode(query.postcode.trim(), streetKey, n)
|
|
125
|
+
|
|
126
|
+
if (rows.length) break
|
|
127
|
+
}
|
|
128
|
+
|
|
115
129
|
const hit = rows.length >= 2 ? interpolateFromNeighbors(rows, n) : null
|
|
116
130
|
|
|
117
131
|
return hit ?? this.#fallback?.find(query) ?? null
|
|
118
132
|
}
|
|
119
133
|
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
this.#db.close()
|
|
123
|
-
}
|
|
134
|
+
[Symbol.dispose](): void {
|
|
135
|
+
this.#resources[Symbol.dispose]()
|
|
124
136
|
}
|
|
125
137
|
}
|
|
126
138
|
|
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
* @license AGPL-3.0
|
|
4
4
|
* @author Teffen Ellis, et al.
|
|
5
5
|
*
|
|
6
|
-
* Typed schema for the SITUS / rooftop ADDRESS-POINT
|
|
7
|
-
* by `scripts/build-address-point-
|
|
6
|
+
* Typed schema for the SITUS / rooftop ADDRESS-POINT extracts (`address-points-<cc>-<slug>.db`, built
|
|
7
|
+
* by `scripts/build-address-point-extract.ts` — the #476/#567 national rooftop tier behind the
|
|
8
8
|
* demo's "type any US address, get the building"). Single source of truth for the columns shared
|
|
9
9
|
* by the BUILDER and the READER ({@link AddressPointSqliteLookup}), so a column rename in one is a
|
|
10
10
|
* compile error in the other.
|
|
@@ -18,6 +18,8 @@
|
|
|
18
18
|
|
|
19
19
|
import type { Kysely } from "kysely"
|
|
20
20
|
|
|
21
|
+
import type { NameKey, RouteKey, StreetKey } from "#street/normalize"
|
|
22
|
+
|
|
21
23
|
/**
|
|
22
24
|
* One rooftop address point. `(street_norm, number)` within a `postcode` (preferred) or `locality_norm` scope is the
|
|
23
25
|
* lookup; `street_key` is the #483 route-fold key for interpolation. Coordinates are non-null (the builder drops
|
|
@@ -27,11 +29,12 @@ export interface AddressPointTable {
|
|
|
27
29
|
/**
|
|
28
30
|
* Shared {@link normalizeStreetForKey} of the street — the build/query-consistent probe key.
|
|
29
31
|
*/
|
|
30
|
-
street_norm:
|
|
32
|
+
street_norm: StreetKey
|
|
31
33
|
/**
|
|
32
|
-
* `canonicalizeRouteKey(street_norm)` — the route-fold key (#483 Method 2).
|
|
34
|
+
* `canonicalizeRouteKey(street_norm)` — the route-fold key (#483 Method 2). Its own brand, so it cannot be
|
|
35
|
+
* interchanged with the plain `street_norm` above.
|
|
33
36
|
*/
|
|
34
|
-
street_key:
|
|
37
|
+
street_key: RouteKey
|
|
35
38
|
/**
|
|
36
39
|
* House number, normalized lower-case (kept TEXT — "123-A", "12 1/2" must survive).
|
|
37
40
|
*/
|
|
@@ -41,7 +44,7 @@ export interface AddressPointTable {
|
|
|
41
44
|
/**
|
|
42
45
|
* Shared {@link normalizeLocalityForKey} of the locality — the fallback scope.
|
|
43
46
|
*/
|
|
44
|
-
locality_norm:
|
|
47
|
+
locality_norm: NameKey | null
|
|
45
48
|
/**
|
|
46
49
|
* The street as it appeared in the source (kept for display / debugging).
|
|
47
50
|
*/
|
|
@@ -56,6 +59,16 @@ export interface AddressPointTable {
|
|
|
56
59
|
* The pinned data release the point was ingested from.
|
|
57
60
|
*/
|
|
58
61
|
release: string
|
|
62
|
+
/**
|
|
63
|
+
* The source register's stable administrative key for the point's commune or municipality — BAN's `code_insee`. A
|
|
64
|
+
* display name (`locality_norm`) is not a key; the coverage basis is computed per THIS.
|
|
65
|
+
*/
|
|
66
|
+
admin_code: string | null
|
|
67
|
+
/**
|
|
68
|
+
* The register's own certification flag for the point (BAN `certification_commune`: 1 certified by the commune, 0
|
|
69
|
+
* not), or null for a source that states none. A basis is never inferred from a share of these.
|
|
70
|
+
*/
|
|
71
|
+
certified: number | null
|
|
59
72
|
}
|
|
60
73
|
|
|
61
74
|
/**
|
|
@@ -65,6 +78,15 @@ export interface AddressPointDatabase {
|
|
|
65
78
|
address_point: AddressPointTable
|
|
66
79
|
}
|
|
67
80
|
|
|
81
|
+
/**
|
|
82
|
+
* The slice of a Kysely handle the `address_point` DDL touches — the parameter type its builders take.
|
|
83
|
+
*
|
|
84
|
+
* Kysely is invariant in its schema parameter (the incompatibility is in `transaction()`), so a extract that EXTENDS
|
|
85
|
+
* `AddressPointTable` — OSM adds `h3_cell` — cannot pass its own handle to a `Kysely<AddressPointDatabase>` parameter.
|
|
86
|
+
* Naming only `schema` lets it, and the DDL below needs nothing else.
|
|
87
|
+
*/
|
|
88
|
+
export type AddressPointSchemaHandle = Pick<Kysely<AddressPointDatabase>, "schema">
|
|
89
|
+
|
|
68
90
|
/**
|
|
69
91
|
* The `address_point` columns in INSERT order. The builder's positional prepared statement derives its placeholder list
|
|
70
92
|
* from this, so the positional order can't drift from the DDL / the reader.
|
|
@@ -81,12 +103,14 @@ export const ADDRESS_POINT_COLUMNS = [
|
|
|
81
103
|
"lon",
|
|
82
104
|
"source",
|
|
83
105
|
"release",
|
|
106
|
+
"admin_code",
|
|
107
|
+
"certified",
|
|
84
108
|
] as const
|
|
85
109
|
|
|
86
110
|
/**
|
|
87
111
|
* Create the `address_point` table — called before the streaming bulk load.
|
|
88
112
|
*/
|
|
89
|
-
export async function createAddressPointTable(db:
|
|
113
|
+
export async function createAddressPointTable(db: AddressPointSchemaHandle): Promise<void> {
|
|
90
114
|
await db.schema
|
|
91
115
|
.createTable("address_point")
|
|
92
116
|
.addColumn("street_norm", "text", (c) => c.notNull())
|
|
@@ -101,13 +125,15 @@ export async function createAddressPointTable(db: Kysely<AddressPointDatabase>):
|
|
|
101
125
|
.addColumn("lon", "real", (c) => c.notNull())
|
|
102
126
|
.addColumn("source", "text", (c) => c.notNull())
|
|
103
127
|
.addColumn("release", "text", (c) => c.notNull())
|
|
128
|
+
.addColumn("admin_code", "text")
|
|
129
|
+
.addColumn("certified", "integer")
|
|
104
130
|
.execute()
|
|
105
131
|
}
|
|
106
132
|
|
|
107
133
|
/**
|
|
108
134
|
* Create the three probe indexes the reader relies on (postcode-scope, locality-scope, route-key).
|
|
109
135
|
*/
|
|
110
|
-
export async function createAddressPointIndexes(db:
|
|
136
|
+
export async function createAddressPointIndexes(db: AddressPointSchemaHandle): Promise<void> {
|
|
111
137
|
await db.schema
|
|
112
138
|
.createIndex("idx_ap_postcode")
|
|
113
139
|
.on("address_point")
|