@gooin/fit2spatial
Version:
Convert Garmin FIT files to GeoJSON, SHP, KML, GPX
91 lines (90 loc) • 3.56 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.extractZipFile = exports.checkFitFilesIncludsGPS = exports.parseFitFile = exports.writeToFile = exports.listFitFiles = exports.getFitFileName = exports.createDirectory = exports.checkIsDirectory = exports.checkIsFitFile = void 0;
const fs = require("node:fs");
const path = require("node:path");
const decompress = require("decompress");
const sports_lib_1 = require("@sports-alliance/sports-lib");
const _ = require("lodash");
const checkIsFitFile = (filePath) => {
return fs.existsSync(filePath) && fs.lstatSync(filePath).isFile() && filePath.endsWith('.fit');
};
exports.checkIsFitFile = checkIsFitFile;
const checkIsDirectory = (filePath) => {
return fs.existsSync(filePath) && fs.lstatSync(filePath).isDirectory();
};
exports.checkIsDirectory = checkIsDirectory;
const createDirectory = (directoryPath) => {
fs.mkdirSync(directoryPath);
};
exports.createDirectory = createDirectory;
const getFitFileName = (filePath) => {
return path.basename(filePath, '.fit');
};
exports.getFitFileName = getFitFileName;
const listFitFiles = (directoryPath) => {
const files = fs.readdirSync(directoryPath);
return files.filter(file => file.endsWith('.fit'));
};
exports.listFitFiles = listFitFiles;
// eslint-disable-next-line @typescript-eslint/explicit-module-boundary-types
const writeToFile = (filePath, data) => {
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
fs.writeFileSync(filePath, data, error => {
if (error)
throw error;
});
};
exports.writeToFile = writeToFile;
const parseFitFile = async (filePath) => {
const file = fs.readFileSync(filePath);
const buffer = file.buffer;
try {
const event = await sports_lib_1.SportsLib.importFromFit(buffer);
// 如果不包含GPS数据,返回undefined
if (!checkFitFilesIncludsGPS(event)) {
return;
}
return event;
}
catch (error) {
console.error(`[${filePath}] parse error: ${error}`);
}
};
exports.parseFitFile = parseFitFile;
function checkFitFilesIncludsGPS(event) {
const activity = event.getActivities()[0];
const streams = activity.getAllStreams();
const lonData = _.find(streams, stream => stream.type === 'Longitude');
const latData = _.find(streams, stream => stream.type === 'Latitude');
if (lonData && latData) {
return true;
}
return false;
}
exports.checkFitFilesIncludsGPS = checkFitFilesIncludsGPS;
async function extractZipFile(zipFilePath) {
const zipFileName = path.basename(zipFilePath, path.extname(zipFilePath));
const outputDir = path.dirname(zipFilePath);
const extractDir = path.join(outputDir, zipFileName);
if (!fs.existsSync(extractDir)) {
fs.mkdirSync(extractDir);
}
// unzip
await decompress(zipFilePath, extractDir);
// rename files
const files = fs.readdirSync(extractDir);
for (const file of files) {
const ext = path.extname(file);
if (ext === '.dbf' || ext === '.prj' || ext === '.shp' || ext === '.shx') {
const oldPath = path.join(extractDir, file);
const newPath = path.join(outputDir, `${zipFileName}${ext}`);
fs.renameSync(oldPath, newPath);
}
}
// remove temp dir and zip file
fs.rmdirSync(extractDir);
fs.rmSync(zipFilePath);
}
exports.extractZipFile = extractZipFile;