A JavaScript/TypeScript parser for Norwegian KOF files. Usable as an ES module or via script injection. Includes demo scripts and sample KOF files.
- Parse Norwegian KOF files
- Use as ES module or via
<script src=...> - TypeScript and JavaScript support
- Demo scripts and sample files included
Additional features added during development
- Export parsed geometries (Point / LineString / Polygon) to GeoJSON.
- Optionally produce reprojections to EPSG:4326 (lat/lon) for demo files that contain an EPSG hint (currently supports EPSG:25832 and a best-effort EPSG:5110 definition) using proj4.
- Geometry properties include
name(PPPPPPPPPP) andfcode(KKKKKKKK). Lines/polygons inherit these from their first point when not explicitly set. - Tests generate human-readable
.logoutput per demo file (undertest/mocha/logs/) and atest/geojson/folder containing produced GeoJSON files (both are gitignored by default). - Parser emits structured warnings with line numbers and diagnostic strategies to aid debugging.
Example KOF files for testing parsing functionality are located in:
demo/kof_files
The positioning of the data content in a KOF file is given by the following header description string (which tells us in which column ranges the data is located):
-05 PPPPPPPPPP KKKKKKKK XXXXXXXX.XXX YYYYYYY.YYY ZZZZ.ZZZ
Where:
05is the row code (required)PPPPPPPPPPis the observation/point name (optional) (the parser will use an ID system per object and per observation, so the point name can be optional)KKKKKKKKis the code of the observation/point (optional) (defaults to empty string if blank)XXXXXXXX.XXXis northing or latitude (required if the row contains an observation; not required for start/close codes like 91, 99, 96, etc.)YYYYYYY.YYYis easting or longitude (required if the row contains an observation; not required for start/close codes like 91, 99, 96, etc.)ZZZZ.ZZZis elevation (optional; set to -500 if not found)- Other optional parameters after
ZZZZ.ZZZare allowed and will be parsed if present.
KOF files use special codes to indicate the start and end of geometries:
- Points: Each point is a single row with code
05. - Lines:
- Start with a row code
91(e.g.09_91), followed by one or more05rows for the line's vertices. - End with a row code
99(e.g.09_99).
- Start with a row code
- Polygons:
- Start with a row code
91(e.g.09_91), followed by one or more05rows for the polygon's vertices. - Closed with a row code
96(e.g.09_96). - Multiple polygons may be present in a file, each with their own start/close codes.
- Start with a row code
From an actual KOF file with header and data:
-05 PPPPPPPPPP KKKKKKKK XXXXXXXX.XXX YYYYYYY.YYY ZZZZ.ZZZ
05 LYKT-04 8751 6540290.081 314103.268 7.934
import { kof } from 'kof-parser';
const result = kof.parse(kofString);<script src="dist/kof-parser.umd.js"></script>
<script>
const result = kof.parse(kofString);
</script>Node / CommonJS (parsing and GeoJSON export):
const { KOF } = require('kof-parser');
const fs = require('fs');
const content = fs.readFileSync('demo/kof_files/example.kof', 'utf8');
const k = new KOF('example.kof', content, { sourceCrs: 'EPSG:25832' });
k.parse();
// Export GeoJSON (no reprojection)
const gj = k.toGeoJSON();
console.log(gj.type, gj.features.length);
// Reproject to EPSG:4326 (if proj4 available)
const gj4326 = k.reproject('EPSG:4326');
console.log('Reprojected:', gj4326.features.length);ES module example:
import { KOF } from 'kof-parser';
const content = await fetch('/demo/kof_files/example.kof').then(r => r.text());
const k = new KOF('example.kof', content, { sourceCrs: 'EPSG:25832' });
k.parse();
const geojson = k.toGeoJSON({ crs: { from: 'EPSG:25832', to: 'EPSG:4326' } });
console.log(geojson);- The parser prefers fixed-column parsing when a header line (
-05 PPPPPPPPPP KKKKKKKK ...) is present; for files without a header it falls back to heuristic token parsing. - The project includes a comprehensive Mocha test-suite under
test/mocha/that covers attributes, encodings, grouping, KOF codes and demo GeoJSON exports. Runningnpm testwill clean old logs, run tests, and (for demo files) produce GeoJSON and reprojection outputs undertest/geojson/. - Reprojection:
proj4is used during testing to convert demo files containingepsg25832orepsg5110in their filenames to EPSG:4326; the converted files are written withepsg4326in their filenames. - EPSG:5110: the repo registers a reasonable NTM10-like proj4 definition as a best-effort. Replace this definition with an authoritative proj4 string if you have one.
To ensure clean, reproducible builds and to avoid TypeScript write-errors when a dist/ folder is present in a working tree, the project now performs an explicit clean before building:
- Locally: run
npm run clean(this removes thedist/directory) ornpm run buildwhich will run the clean step automatically. - CI: the GitHub Actions workflow runs a
git clean -fdxstep before building so the runner has a fresh workspace andtsccan write output intodist/without conflicts.
This keeps local and CI builds consistent and prevents "TS5055: Cannot write file ... because it would overwrite input file" errors when dist/ is present in the repo.
This project is released under the MIT License; see the LICENSE file in the repository for full terms.
- Added explicit
LICENSE(MIT). - Cleaned package metadata (removed accidental core-module devDependencies).
- Tests and demo exports generate
.logandtest/geojson/artifacts (gitignored).
Publishing notes
- The package is configured to publish
dist/andtypes/via thefilesfield inpackage.json. Before publishing, run a fresh build (npm run build) and validate the bundle withnpm pack.
MIT