{"version":3,"sources":["../lib/gpsLib.ts","../extract-gpx-data-delf01.ts"],"sourcesContent":["// Color console\r\nimport \"colors\"\r\n\r\n// Files manager\r\nimport * as fs from 'fs';\r\n\r\n// Path manager\r\nimport * as path from 'path';\r\n\r\n// Convert fs.readFile to an async function\r\nimport { promisify } from 'util';\r\nconst readFileAsync = promisify(fs.readFile);\r\n\r\n// Types\r\nimport {\r\n  RootAppPath,\r\n  MessageConcat,\r\n  ReadGpxFile,\r\n  GetStringBetweenIncludedPatterns,\r\n  GetStringBetweenIncludedPatternsData,\r\n  MergeStagesTrackData,\r\n  MergeStagesTrack,\r\n  GetString,\r\n  GetLinkTrk,\r\n  GetLinkTrkData,\r\n  GetExtensions,\r\n  GetExtensionsData,\r\n  GetTracks,\r\n  GetTracksData,\r\n  GetRoutes,\r\n  GetRoutesData,\r\n  GetWayPoints,\r\n  GetWayPointsData,\r\n  DataExtraction,\r\n  DataExtractionData,\r\n  SplitString,\r\n  SplitStringData,\r\n  GetCumulativeElevations,\r\n  GetCumulativeElevationsData,\r\n  ConvertPositionsToArr,\r\n  ConvertPositionsToArrData,\r\n  GetPositionsArr,\r\n  GetPositionsArrData,\r\n  GetElevationArr,\r\n  GetElevationArrData,\r\n  GetTagsValueArr,\r\n  GetBounds,\r\n  GetBoundsData,\r\n  GetLink,\r\n  GetLinkData,\r\n  GetMetaData,\r\n  GetMetaDataData,\r\n  CalculateDistanceBetweenPositions,\r\n  TrackDistanceCalculation,\r\n} from '../types/gpsLibType';\r\n\r\n// Concatenation of several messages\r\nconst messageConcat: MessageConcat = async ({ methodName, messagesArrObj }) => {\r\n  // Default\r\n  const maxCharacters = 1000;\r\n  const firstMessage = `Debug mode`;\r\n  let lastMessage = `... max ${maxCharacters} characters`;\r\n\r\n  // Messages conctenation\r\n  const concatenatedMessage = Array.isArray(messagesArrObj) && messagesArrObj.length > 0 ? messagesArrObj.map(({ message, color }) => `${message[color]}`).join('').substring(0, maxCharacters) : [];\r\n\r\n  // Colorized\r\n  const colorizedMethodName = methodName ? `, ${methodName} => `.magenta : \"\";\r\n\r\n  // Last message\r\n  lastMessage = concatenatedMessage.length >= maxCharacters ? lastMessage : \"\";\r\n\r\n  // Final message\r\n  const finalMessage = { message: `${firstMessage.magenta}${colorizedMethodName} ${concatenatedMessage} ${lastMessage.magenta}` };\r\n\r\n  // Display console colorized messages\r\n  console.log(finalMessage.message);\r\n\r\n  return finalMessage;\r\n};\r\n\r\n// Root app directory\r\nconst rootAppPath: RootAppPath = async () => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      let rootAppDirectory: string;\r\n\r\n      if (require.main) {\r\n        rootAppDirectory = path.dirname(require.main.filename);\r\n      } else {\r\n        rootAppDirectory = __dirname;\r\n      }\r\n      resolve({ rootAppDirectory: rootAppDirectory as string });\r\n    } catch (error) {\r\n      console.log(':( rootAppPath error'.red);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Read gpx file\r\nconst readGpxFile: ReadGpxFile = async ({ gpxFilePath, debugMode }) => {\r\n  return new Promise((resolve, reject) => {\r\n    try {\r\n      // Determine the root directory of the application\r\n      const rootAppDirectory = require.main ? path.dirname(require.main.filename) : __dirname;\r\n\r\n      // Construct the absolute path to the GPX file\r\n      const absolutePath = path.join(rootAppDirectory, gpxFilePath);\r\n\r\n      // Check if the file exists and is accessible\r\n      fs.promises.access(absolutePath, fs.constants.F_OK)\r\n        .then(() => {\r\n          // Log success message if file exists\r\n          console.log(`:) ${absolutePath} is right`.green);\r\n          // Read the file\r\n          return fs.promises.readFile(absolutePath, \"utf8\");\r\n        })\r\n        .then(async (gpxFileStr) => {\r\n          // Resolve with the contents of the file\r\n          debugMode && await messageConcat({ methodName: `readGpxFile`, messagesArrObj: [{ message: `${JSON.stringify(gpxFileStr)}`, color: \"black\" }] });\r\n          resolve({ gpxFileStr: gpxFileStr });\r\n        })\r\n        .catch((error) => {\r\n          // Log error message if file does not exist or cannot be accessed\r\n          console.error(`:( ${absolutePath} is wrong path. Check pathname or filename : ${error}`);\r\n          // Resolve with false to indicate failure\r\n          resolve({ gpxFileStr: null });\r\n        });\r\n    } catch (error) {\r\n      // Catch any synchronous errors and reject the promise\r\n      console.error(`:( readGpxFile error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n}\r\n\r\n// Get string between two included string of characters\r\nconst getStringBetweenIncludedPatterns: GetStringBetweenIncludedPatterns = async ({ str, pattern1, pattern2, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Default\r\n      let resArr = { length: 0, result: [] };\r\n\r\n      // Regex\r\n      const regex = typeof pattern1 === \"string\" ? new RegExp(pattern1, \"g\") : \"\";\r\n\r\n      // Count patterns\r\n      const matchResult = typeof str === \"string\" ? str.match(regex) : [];\r\n      const patternCount = matchResult ? matchResult.length : 0;\r\n\r\n      if (patternCount > 0) {\r\n        // Default\r\n        let resultArray = [];\r\n\r\n        for (let i = 0; i < patternCount; i++) {\r\n          const pattern1String = pattern1 instanceof RegExp ? pattern1.source : pattern1;\r\n          const patternPosition = str.indexOf(pattern1String);\r\n          const pattern2String = pattern2 instanceof RegExp ? pattern2.source : pattern2;\r\n          const pattern2Position = str.indexOf(pattern2String, patternPosition);\r\n\r\n          if (patternPosition >= 0 && pattern2Position >= 0) {\r\n            // Pattern\r\n            const patternStr = str.substring(patternPosition, pattern2Position + pattern2String.length);\r\n\r\n            // Redefine the native string\r\n            str = str.substring(pattern2Position + pattern2String.length);\r\n\r\n            // Minify file\r\n            const minifiedStr = patternStr.replace(/(\\r\\n|\\n|\\r)|>\\s+</gm, (match, newLine) => newLine ? '' : '><');\r\n\r\n            // Record\r\n            resultArray.push(minifiedStr);\r\n          }\r\n        }\r\n\r\n        const newResArr = { ...resArr, length: resultArray.length, result: resultArray.filter(Boolean) };\r\n        debugMode && await messageConcat({ methodName: `getStringBetweenIncludedPatterns`, messagesArrObj: [{ message: `${JSON.stringify(newResArr)}`, color: \"black\" }] });\r\n        resolve(newResArr);\r\n      } else {\r\n        debugMode && await messageConcat({ methodName: `getStringBetweenIncludedPatterns`, messagesArrObj: [{ message: `${JSON.stringify(resArr)}`, color: \"black\" }] });\r\n        resolve(resArr)\r\n      }\r\n    } catch (error) {\r\n      console.error(\":( getStringBetweenIncludedPatterns error => \", error);\r\n      reject(error);\r\n    }\r\n  });\r\n}\r\n\r\n// Merge all stages track\r\nconst mergeStagesTrackData: MergeStagesTrack = async ({ stagesTrackArr, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Create objects\r\n      const createNameObj = (id: number, name: string) => ({ id, name });\r\n      const createTypeObj = (id: number, type: string) => ({ id, type });\r\n      const createPositionsObj = (id: number, positions: number[]) => ({ id, positions });\r\n      const createDistanceObj = (id: number, meters: number, yards: number) => ({ id, distance: { meters, yards } });\r\n      const createElevationObj = (id: number, elevations: number[]) => ({ id, elevations });\r\n      const createCumulativeElevationObj = (id: string, cumulativePositiveElevation: number | null, cumulativeNegativeElevation: number | null) => ({ id, cumulativePositiveElevation, cumulativeNegativeElevation });\r\n\r\n      // Result object\r\n      const mergeStagesTrackData: MergeStagesTrackData = {\r\n        namesArrObj: [],\r\n        typeArrObj: [],\r\n        cmtArrObj: [],\r\n        descArrObj: [],\r\n        srcArrObj: [],\r\n        urlArrObj: [],\r\n        urlnameArrObj: [],\r\n        linkArrObj: [],\r\n        numberArrObj: [],\r\n        extensionsArrObj: [],\r\n        distances: {\r\n          full: {\r\n            meters: null,\r\n            yards: null\r\n          },\r\n          distancesArrObj: []\r\n        },\r\n        positions: {\r\n          full: [],\r\n          positionsArrObj: []\r\n        },\r\n        elevations: {\r\n          full: [],\r\n          min: null,\r\n          max: null,\r\n          minMaxArrObj: []\r\n        },\r\n        cumulativeElevations: {\r\n          cumulativePositiveElevation: null,\r\n          cumulativeNegativeElevation: null,\r\n          cumulativeElevationArrObj: []\r\n        }\r\n      }\r\n\r\n      // Settings\r\n      let positionsFullArr: any[] = [];\r\n      let elevationsFullArr: any[] = [];\r\n      let distancesFullArr: number[] = [];\r\n\r\n      // Listing each stage\r\n      for (let i = 0; i < stagesTrackArr.length; i++) {\r\n        // Default\r\n        const stage = stagesTrackArr[i];\r\n\r\n        // Create an object for each stage\r\n        const nameObj = createNameObj(i, stage.name);\r\n        const typeObj = createTypeObj(i, stage.type);\r\n        const cmtObj = createTypeObj(i, stage.cmt);\r\n        const descObj = createTypeObj(i, stage.desc);\r\n        const srcObj = createTypeObj(i, stage.src);\r\n        const urlObj = createTypeObj(i, stage.url);\r\n        const urlnameObj = createTypeObj(i, stage.urlname);\r\n        const linkObj = createTypeObj(i, stage.link);\r\n        const numberObj = createTypeObj(i, stage.number);\r\n        const extensionsObj = createTypeObj(i, stage.extensions);\r\n        const positionsObj = createPositionsObj(i, stage.positions.positionsArrObj);\r\n        const distancesObj = createDistanceObj(i, stage.distance.meters, stage.distance.yards);\r\n        const elevationsObj = createElevationObj(i, stage.elevations.full);\r\n        const cumulativeElevationsObj = createCumulativeElevationObj(stage.id, stage.elevations.cumulativePositiveElevation, stage.elevations.cumulativeNegativeElevation);\r\n\r\n        // Positions full\r\n        positionsFullArr.push(stage.positions.positionsArrObj);\r\n\r\n        // Elevations full\r\n        elevationsFullArr.push(stage.elevations.full);\r\n\r\n        // Distances full\r\n        distancesFullArr.push(stage.distance.meters);\r\n\r\n        // Record values into object\r\n        mergeStagesTrackData.namesArrObj.push(nameObj); // names\r\n        mergeStagesTrackData.typeArrObj.push(typeObj); // types\r\n        mergeStagesTrackData.cmtArrObj.push(cmtObj); // comments\r\n        mergeStagesTrackData.descArrObj.push(descObj); // descriptions\r\n        mergeStagesTrackData.srcArrObj.push(srcObj); // sources\r\n        mergeStagesTrackData.urlArrObj.push(urlObj); // url\r\n        mergeStagesTrackData.urlnameArrObj.push(urlnameObj); // urlname\r\n        mergeStagesTrackData.numberArrObj.push(numberObj); // number\r\n        mergeStagesTrackData.linkArrObj.push(linkObj); // link\r\n        mergeStagesTrackData.extensionsArrObj.push(extensionsObj); // extensions\r\n        mergeStagesTrackData.positions.positionsArrObj.push(positionsObj); // array of positions objects\r\n        mergeStagesTrackData.distances.distancesArrObj.push(distancesObj); // array of distances objects\r\n        mergeStagesTrackData.elevations.minMaxArrObj.push(elevationsObj); // array of elevations objects\r\n        mergeStagesTrackData.cumulativeElevations.cumulativeElevationArrObj.push(cumulativeElevationsObj); // array of cumulative elevations objects\r\n      };\r\n\r\n      // Positions\r\n      positionsFullArr = positionsFullArr.flat();\r\n      mergeStagesTrackData.positions = {\r\n        ...mergeStagesTrackData.positions,\r\n        full: positionsFullArr.flat()\r\n      };\r\n\r\n      // Elevations\r\n      elevationsFullArr = elevationsFullArr.flat();\r\n      mergeStagesTrackData.elevations = {\r\n        ...mergeStagesTrackData.elevations,\r\n        full: elevationsFullArr.flat(),\r\n        min: Math.min(...elevationsFullArr.flat()),\r\n        max: Math.max(...elevationsFullArr.flat())\r\n      };\r\n\r\n      // Distances\r\n      mergeStagesTrackData.distances = {\r\n        ...mergeStagesTrackData.distances,\r\n        full: {\r\n          meters: distancesFullArr.reduce((a, b) => a + b, 0),\r\n          yards: parseInt((distancesFullArr.reduce((a, b) => a + b, 0) * 1.093613).toString())\r\n        }\r\n      };\r\n\r\n      // Cumulative elevations\r\n      const cumulativeElevations = await getCumulativeElevations({ elevationsArr: elevationsFullArr.flat(), debugMode });\r\n      mergeStagesTrackData.cumulativeElevations = {\r\n        ...mergeStagesTrackData.cumulativeElevations,\r\n        cumulativePositiveElevation: cumulativeElevations.cumulativePositiveElevation,\r\n        cumulativeNegativeElevation: cumulativeElevations.cumulativeNegativeElevation\r\n      };\r\n\r\n      debugMode && await messageConcat({ methodName: `mergeStagesTrackData`, messagesArrObj: [{ message: `${JSON.stringify(mergeStagesTrackData)}`, color: \"black\" }] });\r\n      resolve(mergeStagesTrackData);\r\n    } catch (error) {\r\n      console.error(':( mergeStagesTrackData error'.red);\r\n      reject(error);\r\n    }\r\n  });\r\n}\r\n\r\n// Get string between tags\r\nconst getString: GetString = async ({ str, pattern1, pattern2 }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Regex to get string between tags\r\n      const regex1 = new RegExp(`(${pattern1}.*?${pattern2})`, 'g');\r\n\r\n      // Regex to remove tags\r\n      const regex2 = /(<([^>]+)>)/gi;\r\n\r\n      // Match strings between tags\r\n      const matches = str && str.match(regex1);\r\n\r\n      if (matches) {\r\n        // Extract and clean the strings\r\n        const result = matches.map((match) => match.replace(regex2, \"\"));\r\n\r\n        resolve(result);\r\n      } else {\r\n        resolve([]);\r\n      }\r\n    } catch (error) {\r\n      console.error(':( getString error'.red);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Get link tag\r\nconst getLinkTrk: GetLinkTrk = async ({ str, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Default\r\n      let linkTrk: GetLinkTrkData = {\r\n        href: null,\r\n        text: null,\r\n        type: null,\r\n      };\r\n\r\n      // Regex patterns\r\n      const hrefRegex = /<link\\s+href=\"([^\"]+)\"/;\r\n      const textRegex = /<text>(.*?)<\\/text>/;\r\n      const typeRegex = /<type>(.*?)<\\/type>/;\r\n\r\n      // Check if link tag exists\r\n      const check = str.includes(`<link`);\r\n\r\n      if (check) {\r\n        // Get href\r\n        const hrefMatch = str.match(hrefRegex);\r\n        const href = hrefMatch ? hrefMatch[1] : null;\r\n\r\n        // Get text\r\n        const textMatch = str.match(textRegex);\r\n        const text = textMatch ? textMatch[1] : null;\r\n\r\n        // Get type\r\n        const typeMatch = str.match(typeRegex);\r\n        const type = typeMatch ? typeMatch[1] : null;\r\n\r\n        linkTrk = {\r\n          ...linkTrk,\r\n          href,\r\n          text,\r\n          type,\r\n        };\r\n\r\n        debugMode && await messageConcat({ methodName: `getLink`, messagesArrObj: [{ message: `${JSON.stringify(linkTrk)}`, color: \"black\" }] });\r\n        resolve(linkTrk);\r\n      } else {\r\n        debugMode && await messageConcat({ methodName: `getLink`, messagesArrObj: [{ message: `${JSON.stringify(linkTrk)}`, color: \"black\" }] });\r\n        resolve(linkTrk);\r\n      }\r\n    } catch (error) {\r\n      console.error(\":( getLink error\".red);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Get extensions tag\r\nconst getExtensions: GetExtensions = async ({ str, pattern1, pattern2, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Convert pattern1 and pattern2 to strings if they are regular expressions\r\n      const regexStr = new RegExp(`${(pattern1 instanceof RegExp) ? pattern1.source : pattern1}(.*?)${(pattern2 instanceof RegExp) ? pattern2.source : pattern2}`, 'g');\r\n\r\n      // Match strings between tags\r\n      const matches = str.match(regexStr);\r\n\r\n      if (matches) {\r\n        // Extract extensions\r\n        const result: GetExtensionsData[] = matches.map((match) => {\r\n          const extension = match.substring((pattern1 instanceof RegExp) ? pattern1.source.length : pattern1.length, match.length - ((pattern2 instanceof RegExp) ? pattern2.source.length : pattern2.length));\r\n          return { extension };\r\n        });\r\n\r\n        debugMode && await messageConcat({ methodName: `getExtensions`, messagesArrObj: [{ message: `${JSON.stringify(result)}`, color: \"black\" }] });\r\n        resolve(result);\r\n      } else {\r\n        debugMode && await messageConcat({ methodName: `getExtensions`, messagesArrObj: [{ message: `${JSON.stringify([{ extension: null }])}`, color: \"black\" }] });\r\n        resolve([{ extension: null }]);\r\n      }\r\n    } catch (error) {\r\n      console.error(\":( getExtensions error\".red);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Tracks\r\nconst getTracks: GetTracks = async ({ readGpxFile, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Get track tag\r\n      const stagesTrackArray: GetStringBetweenIncludedPatternsData = await getStringBetweenIncludedPatterns({ str: readGpxFile.toString(), pattern1: \"<trk>\", pattern2: \"</trk>\", debugMode: debugMode });\r\n\r\n      if (stagesTrackArray.result) {\r\n        // Default\r\n        const resArr: GetTracksData[] = [];\r\n\r\n        // Listing stages track\r\n        for (let k = 0; k < stagesTrackArray.result.length; k++) {\r\n          // Default obj\r\n          let trackData: GetTracksData = {\r\n            id: null,\r\n            name: null,\r\n            type: null,\r\n            cmt: null,\r\n            desc: null,\r\n            src: null,\r\n            url: null,\r\n            urlname: null,\r\n            number: null,\r\n            link: null,\r\n            extensions: null,\r\n            distance: {\r\n              meters: null,\r\n              yards: null,\r\n            },\r\n            elevations: {\r\n              full: [],\r\n              min: null,\r\n              max: null,\r\n              cumulativePositiveElevation: null,\r\n              cumulativeNegativeElevation: null,\r\n            },\r\n            positions: {\r\n              positionsArrObj: [],\r\n              positionsArrArr: [],\r\n            },\r\n            times: {\r\n              full: [],\r\n            },\r\n            magvars: {\r\n              full: [],\r\n            },\r\n            geoidheights: {\r\n              full: [],\r\n            },\r\n            names: {\r\n              full: [],\r\n            },\r\n            cmts: {\r\n              full: [],\r\n            },\r\n            descs: {\r\n              full: [],\r\n            },\r\n            srcs: {\r\n              full: [],\r\n            },\r\n            urls: {\r\n              full: [],\r\n            },\r\n            urlnames: {\r\n              full: [],\r\n            },\r\n            syms: {\r\n              full: [],\r\n            },\r\n            types: {\r\n              full: [],\r\n            },\r\n            fixs: {\r\n              full: [],\r\n            },\r\n            sats: {\r\n              full: [],\r\n            },\r\n            hdops: {\r\n              full: [],\r\n            },\r\n            vdops: {\r\n              full: [],\r\n            },\r\n            pdops: {\r\n              full: [],\r\n            },\r\n            ageofdgpsdatas: {\r\n              full: [],\r\n            },\r\n            dgpsids: {\r\n              full: [],\r\n            },\r\n            extensionss: {\r\n              full: [],\r\n            },\r\n            speeds: {\r\n              full: [],\r\n            },\r\n            courses: {\r\n              full: [],\r\n            },\r\n          };\r\n\r\n          // Default\r\n          const stage = stagesTrackArray.result[k];\r\n\r\n          // Tags tracks\r\n          const trkptStr: SplitStringData = await splitString({ str: stage, pattern: \"<trkpt\" });\r\n\r\n          // Segments tracks\r\n          const trksegStr: any = await splitString({ str: stage, pattern: \"<trkseg>\" });\r\n\r\n          // Check if data exists\r\n          if (trkptStr.resArr.length > 0) {\r\n            // ID track\r\n            trackData = { ...trackData, id: k.toString() };\r\n\r\n            // Positions array of objects\r\n            const positionsArrObj = await getPositionsArr({ strArr: trkptStr.resArr, pattern: \"\\\"\", debugMode: debugMode });\r\n            trackData = { ...trackData, positions: { ...trackData.positions, positionsArrObj } };\r\n\r\n            // Positions array of arrays\r\n            const positionsArrArr = await convertPositionsToArr({ positionsArrObj: positionsArrObj, debugMode: debugMode });\r\n            if (Array.isArray(positionsArrArr)) {\r\n              trackData = { ...trackData, positions: { ...trackData.positions, positionsArrArr } };\r\n            }\r\n\r\n            // Distance calculation\r\n            const distance = await trackDistanceCalculation({ positionsArray: positionsArrArr.positions, debugMode: debugMode });\r\n\r\n            // Assign distance in meters\r\n            trackData = { ...trackData, distance: { ...trackData.distance, meters: distance } };\r\n\r\n            // Convert distance to yards if it's a number\r\n            if (typeof distance === 'number') {\r\n              trackData = { ...trackData, distance: { ...trackData.distance, yards: distance * 1.093613 } };\r\n            } else {\r\n              // Handle the case where distance is not a number\r\n              trackData = { ...trackData, distance: { ...trackData.distance, yards: null } };\r\n            }\r\n\r\n            // Elevations\r\n            const { elevationArr }: GetElevationArrData = await getElevationsArr({ strArr: trkptStr.resArr, pattern1: \"<ele>\", pattern2: \"</ele>\", debugMode: debugMode });\r\n\r\n            // Full elevations\r\n            trackData = { ...trackData, elevations: { ...trackData.elevations, full: elevationArr } };\r\n\r\n            // Min elevation\r\n            trackData = { ...trackData, elevations: { ...trackData.elevations, min: Math.min(...elevationArr) } };\r\n\r\n            // Max elevation\r\n            trackData = { ...trackData, elevations: { ...trackData.elevations, max: Math.max(...elevationArr) } };\r\n\r\n            // Cumulative elevations\r\n            const { cumulativeNegativeElevation, cumulativePositiveElevation }: GetCumulativeElevationsData = await getCumulativeElevations({ elevationsArr: elevationArr, debugMode: debugMode });\r\n            trackData = { ...trackData, elevations: { ...trackData.elevations, cumulativeNegativeElevation: cumulativeNegativeElevation } };\r\n            trackData = { ...trackData, elevations: { ...trackData.elevations, cumulativePositiveElevation: cumulativePositiveElevation } };\r\n\r\n            // Track points records\r\n            const recordsTrkptArr = [\"time\", \"magvar\", \"geoidheight\", \"name\", \"cmt\", \"desc\", \"src\", \"url\", \"urlname\", \"sym\", \"type\", \"fix\", \"sat\", \"hdop\", \"vdop\", \"pdop\", \"ageofdgpsdata\", \"dgpsid\", \"extensions\", \"speed\", \"course\"];\r\n\r\n            for (const element of recordsTrkptArr) {\r\n              const arr = [trksegStr[1]];\r\n              const elementArr = await getTagsValueArr({ strArr: arr, pattern1: `<${element}>`, pattern2: `</${element}>`, debugMode: debugMode });\r\n              trackData = { ...trackData, [`${element}s`]: { full: elementArr } };\r\n            }\r\n\r\n            // Records trk \"name\", \"type\", \"cmt\", \"desc\", \"src\", \"url\", \"urlname\", \"number\" tags\r\n            const recordsTrkArr = [\"name\", \"type\", \"cmt\", \"desc\", \"src\", \"url\", \"urlname\", \"number\"];\r\n\r\n            for (const element of recordsTrkArr) {\r\n              // Record trk elements\r\n              const elementArr = await getString({ str: stage, pattern1: `<${element}>`, pattern2: `</${element}>`, debugMode: debugMode });\r\n\r\n              trackData = { ...trackData, [element]: elementArr.length > 0 ? elementArr[0] : null };\r\n            }\r\n\r\n            // Link\r\n            // <link href=\"https://mywebsite.com\"><text>My Website</text><type>cycling</type></link>\r\n            const linkObj = await getLinkTrk({ str: stage, debugMode: debugMode });\r\n            trackData = { ...trackData, link: linkObj };\r\n\r\n            // Route extensions\r\n            // <extensions><ogr:id>17</ogr:id><ogr:longitude>10.684415</ogr:longitude><ogr:latitude>53.865650</ogr:latitude></extensions>\r\n            const extensions = await getExtensions({ str: stage, pattern1: \"<extensions>\", pattern2: \"</extensions>\", debugMode: debugMode });\r\n            trackData = { ...trackData, extensions: extensions[0] };\r\n\r\n            // Add the processed track data to the result array\r\n            resArr.push(trackData);\r\n          }\r\n        }\r\n\r\n        debugMode && await messageConcat({ methodName: `getTracks`, messagesArrObj: [{ message: `${JSON.stringify(resArr)}`, color: \"black\" }] });\r\n        resolve(resArr);\r\n      } else {\r\n        console.log(\":| No tracks in the gpx file.\");\r\n        debugMode && await messageConcat({ methodName: `getTracks`, messagesArrObj: [] });\r\n        resolve([]);\r\n      }\r\n    } catch (error) {\r\n      console.error(':( getTracks error', error);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Routes\r\nconst getRoutes: GetRoutes = async ({ readGpxFile, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Get route tag\r\n      const routesArr = await getStringBetweenIncludedPatterns({ str: readGpxFile, pattern1: \"<rte>\", pattern2: \"</rte>\", debugMode: debugMode });\r\n\r\n      if (routesArr.result) {\r\n        const resArr: GetRoutesData[] = [];\r\n\r\n        // Listing routes\r\n        for (let i = 0; i < routesArr.result.length; i++) {\r\n          // Default\r\n          const route = routesArr.result[i];\r\n\r\n          let routeData: GetRoutesData = {\r\n            id: null,\r\n            name: null,\r\n            type: null,\r\n            cmt: null,\r\n            desc: null,\r\n            src: null,\r\n            url: null,\r\n            urlname: null,\r\n            number: null,\r\n            link: null,\r\n            extensions: null,\r\n            distance: {\r\n              meters: null,\r\n              yards: null,\r\n            },\r\n            elevations: {\r\n              full: [],\r\n              min: null,\r\n              max: null,\r\n              cumulativePositiveElevation: null,\r\n              cumulativeNegativeElevation: null,\r\n            },\r\n            positions: {\r\n              positionsArrObj: [],\r\n              positionsArrArr: [],\r\n            },\r\n            times: {\r\n              full: [],\r\n            },\r\n            magvars: {\r\n              full: [],\r\n            },\r\n            geoidheights: {\r\n              full: [],\r\n            },\r\n            names: {\r\n              full: [],\r\n            },\r\n            cmts: {\r\n              full: [],\r\n            },\r\n            descs: {\r\n              full: [],\r\n            },\r\n            srcs: {\r\n              full: [],\r\n            },\r\n            urls: {\r\n              full: [],\r\n            },\r\n            urlnames: {\r\n              full: [],\r\n            },\r\n            syms: {\r\n              full: [],\r\n            },\r\n            types: {\r\n              full: [],\r\n            },\r\n            fixs: {\r\n              full: [],\r\n            },\r\n            sats: {\r\n              full: [],\r\n            },\r\n            hdops: {\r\n              full: [],\r\n            },\r\n            vdops: {\r\n              full: [],\r\n            },\r\n            pdops: {\r\n              full: [],\r\n            },\r\n            ageofdgpsdatas: {\r\n              full: [],\r\n            },\r\n            dgpsids: {\r\n              full: [],\r\n            },\r\n            extensionss: {\r\n              full: [],\r\n            },\r\n            speeds: {\r\n              full: [],\r\n            },\r\n            courses: {\r\n              full: [],\r\n            },\r\n          };\r\n\r\n          // Route ID\r\n          routeData.id = i\r\n\r\n          // Route points tags\r\n          const rteptStrArr = await splitString({ str: route, pattern: \"<rtept\" });\r\n\r\n          if (rteptStrArr.resArr.length > 0) {\r\n            // Positions array of objects\r\n            const positionsArrObj = await getPositionsArr({ strArr: rteptStrArr.resArr, pattern: \"\\\"\", debugMode: debugMode });\r\n            routeData = { ...routeData, positions: { ...routeData.positions, positionsArrObj } };\r\n\r\n            // Positions array of arrays\r\n            const positionsArrArr = (await convertPositionsToArr({ positionsArrObj: positionsArrObj, debugMode: debugMode })).positions;\r\n            routeData = { ...routeData, positions: { ...routeData.positions, positionsArrArr } };\r\n\r\n            // Distance calculation\r\n            const distance = await trackDistanceCalculation({ positionsArray: positionsArrArr, debugMode: debugMode });\r\n            routeData = { ...routeData, distance: { ...routeData.distance, meters: distance, yards: typeof distance === 'number' ? distance * 1.093613 : null } };\r\n\r\n            // Elevations\r\n            const { elevationArr } = await getElevationsArr({ strArr: rteptStrArr.resArr, pattern1: \"<ele>\", pattern2: \"</ele>\", debugMode: debugMode });\r\n            routeData = { ...routeData, elevations: { ...routeData.elevations, full: elevationArr, min: Math.min(...elevationArr), max: Math.max(...elevationArr) } };\r\n\r\n            // Cumulative elevations\r\n            const cumulativeElevations = await getCumulativeElevations({ elevationsArr: elevationArr, debugMode: debugMode });\r\n            routeData = { ...routeData, elevations: { ...routeData.elevations, cumulativeNegativeElevation: cumulativeElevations.cumulativeNegativeElevation, cumulativePositiveElevation: cumulativeElevations.cumulativePositiveElevation } };\r\n\r\n            // Record route points tags\r\n            const recordsRteptArr = [\"time\", \"magvar\", \"geoidheight\", \"name\", \"cmt\", \"desc\", \"src\", \"url\", \"urlname\", \"sym\", \"type\", \"fix\", \"sat\", \"hdop\", \"vdop\", \"pdop\", \"ageofdgpsdata\", \"dgpsid\", \"extensions\", \"speed\", \"course\"];\r\n\r\n            await Promise.all(recordsRteptArr.map(async (element) => {\r\n              if (rteptStrArr.resArr.length > 1) {\r\n                const elementArr = await getTagsValueArr({ strArr: [rteptStrArr.resArr[0]], pattern1: `<${element}>`, pattern2: `</${element}>`, debugMode: debugMode });\r\n                routeData[`${element}s`] = { full: elementArr.tagsValueArr };\r\n              } else {\r\n                console.log(`:| rteptStrArr.resArr does not contain enough elements for ${element}`.yellow);\r\n              }\r\n            }));\r\n\r\n            // Records route \"name\", \"type\", \"cmt\", \"desc\", \"src\", \"url\", \"urlname\", \"number\" tags\r\n            const recordsRteArr = [\"name\", \"type\", \"cmt\", \"desc\", \"src\", \"url\", \"urlname\", \"number\"];\r\n\r\n            await Promise.all(recordsRteArr.map(async (element) => {\r\n              const elementArr = await getString({ str: route, pattern1: `<${element}>`, pattern2: `</${element}>`, debugMode: debugMode });\r\n              routeData[element] = elementArr[0];\r\n            }));\r\n\r\n            // Route link\r\n            const linkObj = await getLinkTrk({ str: route, debugMode: debugMode });\r\n            routeData = { ...routeData, link: linkObj };\r\n\r\n            // Route extensions\r\n            const extensions = await getExtensions({ str: route, pattern1: `<extensions>`, pattern2: `</extensions>`, debugMode: debugMode });\r\n\r\n            if (extensions.length > 0 && extensions[0].extension) {\r\n              routeData = { ...routeData, extensions: extensions[0].extension };\r\n            } else {\r\n              routeData = { ...routeData, extensions: null };\r\n            }\r\n\r\n            // Record route\r\n            resArr.push(routeData);\r\n          }\r\n        }\r\n\r\n        debugMode && await messageConcat({ methodName: `getRoutes`, messagesArrObj: [{ message: `${JSON.stringify(resArr)}`, color: \"black\" }] });\r\n        resolve(resArr);\r\n      } else {\r\n        console.log(\":| No routes in the gpx file.\".yellow);\r\n        debugMode && await messageConcat({ methodName: `getRoutes`, messagesArrObj: [] });\r\n        resolve([]);\r\n      }\r\n    } catch (error) {\r\n      console.error(':( getRoutes error', error);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Waypoints\r\nconst getWayPoints: GetWayPoints = async ({ readGpxFile, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // File creator\r\n      const wayPointsArray = await getStringBetweenIncludedPatterns({ str: readGpxFile, pattern1: \"<wpt\", pattern2: \"</wpt>\", debugMode: debugMode });\r\n\r\n      if (wayPointsArray.result) {\r\n        const resArr: GetWayPointsData[] = [];\r\n\r\n        // Listing way points\r\n        for (let m = 0; m < wayPointsArray.result.length; m++) {\r\n          const point = wayPointsArray.result[m];\r\n\r\n          let wayPointsData: GetWayPointsData = {\r\n            id: m,\r\n            name: null,\r\n            position: null,\r\n            elevation: null,\r\n            time: null,\r\n            magvar: null,\r\n            geoidheight: null,\r\n            cmt: null,\r\n            desc: null,\r\n            src: null,\r\n            url: null,\r\n            urlname: null,\r\n            sym: null,\r\n            type: null,\r\n            fix: null,\r\n            sat: null,\r\n            hdop: null,\r\n            vdop: null,\r\n            pdop: null,\r\n            ageofdgpsdata: null,\r\n            dgpsid: null,\r\n            extensions: null,\r\n            speed: null,\r\n            course: null,\r\n            link: null,\r\n          };\r\n\r\n          // Tags tracks\r\n          const wptStr = await splitString({ str: point, pattern: \"<wpt\" });\r\n\r\n          // Check if data exists\r\n          if (wptStr.resArr.length > 0) {\r\n            // Position\r\n            const positionsArrObj = await getPositionsArr({ strArr: wptStr.resArr, pattern: \"\\\"\", debugMode: debugMode });\r\n            wayPointsData = { ...wayPointsData, position: `${positionsArrObj[0].lat},${positionsArrObj[0].lon}` };\r\n\r\n            // Elevation\r\n            const elevationsArr = await getElevationsArr({ strArr: wptStr.resArr, pattern1: \"<ele>\", pattern2: \"</ele>\", debugMode: debugMode });\r\n            wayPointsData = { ...wayPointsData, elevation: parseFloat(elevationsArr.elevationArr[0].toString()) };\r\n\r\n            // Link\r\n            const linkObj = await getLinkTrk({ str: wptStr.resArr[1], debugMode: debugMode });\r\n            wayPointsData = { ...wayPointsData, link: linkObj };\r\n\r\n            // Route extensions\r\n            const extensions = await getExtensions({ str: wptStr.resArr[1], pattern1: `<extensions>`, pattern2: `</extensions>`, debugMode: debugMode });\r\n            wayPointsData = { ...wayPointsData, extensions: extensions.length > 0 ? extensions[0].extension : null };\r\n\r\n            // Record wpt elements\r\n            const recordsWptArr = [\"time\", \"magvar\", \"geoidheight\", \"name\", \"cmt\", \"desc\", \"src\", \"url\", \"urlname\", \"sym\", \"type\", \"fix\", \"sat\", \"hdop\", \"vdop\", \"pdop\", \"ageofdgpsdata\", \"dgpsid\", \"speed\", \"course\"];\r\n\r\n            await Promise.all(recordsWptArr.map(async (element) => {\r\n              // Record wpt elements\r\n              const elementArr = await getTagsValueArr({ strArr: wptStr.resArr, pattern1: `<${element}>`, pattern2: `</${element}>`, debugMode: debugMode });\r\n              wayPointsData[element] = elementArr.tagsValueArr[1];\r\n            }));\r\n\r\n            // Record\r\n            resArr.push(wayPointsData);\r\n          }\r\n        }\r\n\r\n        debugMode && await messageConcat({ methodName: `getWayPoints`, messagesArrObj: [{ message: `${JSON.stringify(resArr)}`, color: \"black\" }] });\r\n        resolve(resArr);\r\n      } else {\r\n        // Console message\r\n        console.log(\":| No way points in the gpx file.\".yellow);\r\n        debugMode && await messageConcat({ methodName: `getWayPoints`, messagesArrObj: [] });\r\n        resolve([]);\r\n      }\r\n    } catch (error) {\r\n      console.log(':( getWayPoints error'.red);\r\n      reject(console.log);\r\n    }\r\n  });\r\n};\r\n\r\n// Extract gpx data\r\nconst dataExtraction: DataExtraction = async ({ readGpxFile, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Metadata extraction\r\n      const gpxFileMetadata = await getMetaData({ readGpxFile, debugMode });\r\n\r\n      // Routes\r\n      const routes = await getRoutes({ readGpxFile: readGpxFile, debugMode: debugMode });\r\n\r\n      // Tracks\r\n      const stagesTrackData: any = await getTracks({ readGpxFile, debugMode });\r\n\r\n      // Way points\r\n      const wayPoints = await getWayPoints({ readGpxFile, debugMode });\r\n\r\n      // Merge tracks\r\n      const mergedData: MergeStagesTrackData = await mergeStagesTrackData({ stagesTrackArr: stagesTrackData, debugMode });\r\n\r\n      // Result object\r\n      const resObj: DataExtractionData = {\r\n        gpxFileMetadata,\r\n        wayPoints,\r\n        routes,\r\n        stagesTrackData,\r\n        mergedData,\r\n      };\r\n\r\n      debugMode && await messageConcat({ methodName: `getWayPoints`, messagesArrObj: [{ message: `${JSON.stringify(resObj)}`, color: \"black\" }] });\r\n      resolve(resObj);\r\n    } catch (error) {\r\n      console.error(`:( dataExtraction error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Split string\r\nconst splitString: SplitString = async ({ str, pattern }) => {\r\n  return new Promise((resolve, reject) => {\r\n    try {\r\n      // Split\r\n      const resArr: string[] = str.split(pattern);\r\n      resolve({ resArr, length: resArr.length });\r\n    } catch (error) {\r\n      console.error(`:( splitString error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Get cumulative elevations\r\nconst getCumulativeElevations: GetCumulativeElevations = async ({ elevationsArr, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Default\r\n      let cumulativeNegativeElevation = 0;\r\n      let cumulativePositiveElevation = 0;\r\n\r\n      // Check existing elevations values\r\n      if (elevationsArr.length > 1) {\r\n        // Elevations calculation\r\n        for (let i = 1; i < elevationsArr.length; i++) {\r\n          // Elevations difference calculation\r\n          const elevationDifference = elevationsArr[i] - elevationsArr[i - 1];\r\n\r\n          if (elevationDifference < 0) {\r\n            cumulativeNegativeElevation += elevationDifference;\r\n          } else {\r\n            cumulativePositiveElevation += elevationDifference;\r\n          }\r\n        }\r\n      }\r\n\r\n      const cumulativeElevationsObj = {\r\n        cumulativeNegativeElevation: cumulativeNegativeElevation,\r\n        cumulativePositiveElevation: cumulativePositiveElevation\r\n      };\r\n\r\n      debugMode && await messageConcat({ methodName: `getCumulativeElevations`, messagesArrObj: [{ message: `${JSON.stringify(cumulativeElevationsObj)}`, color: \"black\" }] });\r\n      resolve(cumulativeElevationsObj);\r\n    } catch (error) {\r\n      console.error(`:( getCumulativeElevations error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Convert array of positions object to an array of positions arrays\r\nconst convertPositionsToArr: ConvertPositionsToArr = async ({ positionsArrObj }) => {\r\n  return new Promise((resolve, reject) => {\r\n    try {\r\n      // Settings\r\n      const resArr: ConvertPositionsToArrData = { id: '', positions: [] };\r\n\r\n      for (const positionsObj of positionsArrObj) {\r\n        const arr: [number, number] = [positionsObj.lat, positionsObj.lon];\r\n        resArr.positions.push(arr);\r\n      }\r\n\r\n      resolve(resArr);\r\n    } catch (error) {\r\n      console.error(`:( convertPositionsToArr error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Get selected string from string\r\nconst getPositionsArr: GetPositionsArr = async ({ strArr, pattern, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Default\r\n      const resultsObj = {\r\n        lat: 0,\r\n        lon: 0,\r\n      }\r\n\r\n      if (Array.isArray(strArr)) {\r\n        const resArr: GetPositionsArrData[] = (strArr)\r\n          .map(str => str.split(pattern))\r\n          .filter(splitStr => !isNaN(parseFloat(splitStr[1])) && !isNaN(parseFloat(splitStr[3])))\r\n          .map(splitStr => ({\r\n            lat: parseFloat(splitStr[1]),\r\n            lon: parseFloat(splitStr[3])\r\n          }));\r\n\r\n        debugMode && await messageConcat({ methodName: `getPositionsArr`, messagesArrObj: [{ message: `${JSON.stringify(resArr)}`, color: \"black\" }] });\r\n        resolve(resArr);\r\n      } else {\r\n        resolve([resultsObj]);\r\n      }\r\n    } catch (error) {\r\n      console.error(`:( getPositionsArr error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Get elevations\r\nconst getElevationsArr: GetElevationArr = async ({ strArr, pattern1, pattern2, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // If no elevations\r\n      if (Array.isArray(strArr) && strArr.length > 0) {\r\n        // Result array\r\n        const resArrPromises = strArr.map(async (str) => {\r\n          // Get each elevation\r\n          const eleStr = await getString({ str, pattern1, pattern2, debugMode: debugMode });\r\n\r\n          // Record\r\n          if (!isNaN(parseFloat(eleStr[0]))) {\r\n            // Elevation\r\n            return parseFloat(eleStr[0]);\r\n          }\r\n        });\r\n\r\n        // Wait promesses\r\n        const resolvedArr = await Promise.all(resArrPromises);\r\n\r\n        // Filter values\r\n        const resArr = resolvedArr.filter(ele => typeof ele === 'number' && !isNaN(ele)) as number[];\r\n\r\n        debugMode && await messageConcat({ methodName: `getElevationsArr`, messagesArrObj: [{ message: `${JSON.stringify({ elevationArr: resArr })}`, color: \"black\" }] });\r\n        resolve({ elevationArr: resArr });\r\n      } else {\r\n        debugMode && await messageConcat({ methodName: `getElevationsArr`, messagesArrObj: [] });\r\n        resolve({ elevationArr: [] });\r\n      }\r\n    } catch (error) {\r\n      console.error(`:( getElevationsArr error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Get tag's value\r\nconst getTagsValueArr: GetTagsValueArr = async ({ strArr, pattern1, pattern2, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      if (Array.isArray(strArr)) {\r\n        // Mapping selected string array to promises\r\n        const promises = strArr.map(async (str) => {\r\n          // Get each tag value\r\n          const tagValue = await getString({ str, pattern1, pattern2, debugMode: debugMode });\r\n\r\n          return tagValue[0] ? tagValue[0] : \"\";\r\n        });\r\n\r\n        // Resolve all promises and return the resulting array\r\n        const tagsValueArr = await Promise.all(promises);\r\n\r\n        debugMode && await messageConcat({ methodName: `getTagsValueArr`, messagesArrObj: [{ message: `${JSON.stringify({ tagsValueArr: tagsValueArr })}`, color: \"black\" }] });\r\n        resolve({ tagsValueArr: tagsValueArr });\r\n      } else {\r\n        debugMode && await messageConcat({ methodName: `getTagsValueArr`, messagesArrObj: [] });\r\n        resolve({ tagsValueArr: [] });\r\n      }\r\n    } catch (error) {\r\n      console.error(`:( getTagsValueArr error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Get bounds tag\r\nconst getBounds: GetBounds = async ({ metaData, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Default obj\r\n      const boundsDataObj: GetBoundsData = {\r\n        bounds: {\r\n          minLat: null,\r\n          minLon: null,\r\n          maxLat: null,\r\n          maxLon: null\r\n        }\r\n      };\r\n\r\n      // Split string\r\n      const bounds = metaData.str.split(`<bounds`);\r\n\r\n      // Check if bounds tag exists\r\n      if (bounds.length > 1) {\r\n        // Select values\r\n        const selectedValue = bounds[1].split(\"\\\"\");\r\n\r\n        // Result obj\r\n        const updatedBoundsDataObj: GetBoundsData = {\r\n          ...boundsDataObj,\r\n          bounds: {\r\n            minLat: parseFloat(selectedValue[1]),\r\n            minLon: parseFloat(selectedValue[3]),\r\n            maxLat: parseFloat(selectedValue[5]),\r\n            maxLon: parseFloat(selectedValue[7])\r\n          }\r\n        };\r\n\r\n        debugMode && await messageConcat({ methodName: `getBounds`, messagesArrObj: [{ message: `${JSON.stringify(updatedBoundsDataObj)}`, color: \"black\" }] });\r\n        resolve(updatedBoundsDataObj);\r\n      } else {\r\n        debugMode && await messageConcat({ methodName: `getBounds`, messagesArrObj: [{ message: `${JSON.stringify(boundsDataObj)}`, color: \"black\" }] });\r\n        resolve(boundsDataObj);\r\n      }\r\n    } catch (error) {\r\n      console.log(\":( getBounds error\".red);\r\n      reject(console.log);\r\n    }\r\n  });\r\n};\r\n\r\n// Get link tag\r\nconst getLink: GetLink = async ({ str, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Default empty object\r\n      let linkDataObj: GetLinkData = {\r\n        href: null,\r\n        text: null,\r\n        type: null\r\n      };\r\n\r\n      // Check if link tag exists\r\n      const checkedLinks = str.includes(`< link`);\r\n\r\n      // Data existing checking\r\n      if (checkedLinks) {\r\n        // Split str\r\n        const links = str.split(`< link`);\r\n\r\n        // Get href\r\n        const linksArr = links[1].split(`\"`);\r\n        linkDataObj = { ...linkDataObj, href: linksArr[1] ?? \"\" };\r\n\r\n        // Get text\r\n        const textArray: string[] = await getString({ str: links[1], pattern1: `<text>`, pattern2: `</text>`, debugMode: debugMode });\r\n        linkDataObj = { ...linkDataObj, text: textArray[0] ?? \"\" };\r\n\r\n        // Get type\r\n        const typeArray: string[] = await getString({ str: links[1], pattern1: `<type>`, pattern2: `</type>`, debugMode: debugMode });\r\n        linkDataObj = { ...linkDataObj, type: typeArray[0] ?? \"\" };\r\n\r\n        debugMode && await messageConcat({ methodName: `getLink`, messagesArrObj: [{ message: `${JSON.stringify(linkDataObj)}`, color: \"black\" }] });\r\n        resolve(linkDataObj);\r\n      } else {\r\n        debugMode && await messageConcat({ methodName: `getLink`, messagesArrObj: [{ message: `${JSON.stringify(linkDataObj)}`, color: \"black\" }] });\r\n        resolve(linkDataObj);\r\n      }\r\n    } catch (error) {\r\n      console.error(`:( getLink error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Get metadata from a GPX file\r\nconst getMetaData: GetMetaData = async ({ readGpxFile, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      let metadataObj: GetMetaDataData = {\r\n        gpxFileMetadata: {\r\n          gpxFileCreatorName: null,\r\n          gpxFileName: null,\r\n          gpxFileDescription: null,\r\n          gpxFileAuthorName: null,\r\n          gpxFileCopyright: null,\r\n          gpxFileCreationDatetime: null,\r\n          gpxFileKeywords: null,\r\n          gpxFileExtensions: null,\r\n          gpxFileBounds: null,\r\n          gpxFileLink: null\r\n        }\r\n      };\r\n\r\n      // Extract creator name from the GPX file\r\n      const resultData = await getStringBetweenIncludedPatterns({ str: readGpxFile, pattern1: \"creator=\", pattern2: \"<metadata>\", debugMode: debugMode });\r\n\r\n      // Default\r\n      let gpxFileCreatorName = \"\";\r\n\r\n      if (resultData.result && resultData.result.length > 0) {\r\n        gpxFileCreatorName = resultData.result[0].split(\"\\\"\")[1];\r\n      } else {\r\n        console.log(`:| The \"<gpx />\" tag does not contained the \"creator\" property.`.yellow);\r\n      }\r\n\r\n      // Extract metadata from the GPX file\r\n      const metaData: GetStringBetweenIncludedPatternsData = await getStringBetweenIncludedPatterns({ str: readGpxFile, pattern1: \"<metadata>\", pattern2: \"</metadata>\", debugMode: debugMode });\r\n\r\n      if (metaData.result) {\r\n        // Extract bounds from the metadata\r\n        const boundsObj: GetBoundsData = await getBounds({ metaData: { str: readGpxFile, pattern1: \"<metadata>\", pattern2: \"</metadata>\", debugMode: debugMode }, debugMode: debugMode });\r\n\r\n        // Extract links from metadata\r\n        const linkObj: GetLinkData | null = await getLink({ str: readGpxFile, pattern: \"<metadata>\", pattern2: \"</metadata>\", debugMode: debugMode });\r\n\r\n        const arr = [`name`, `desc`, `author`, `copyright`, `time`, `keywords`, `extensions`];\r\n        const resArr: string[] = [];\r\n\r\n        for (const element of arr) {\r\n          let data: string | null = metaData.result[0].substring(metaData.result[0].lastIndexOf(`<${element}>`) + `<${element}>`.length, metaData.result[0].lastIndexOf(`</${element}>`));\r\n\r\n          if (data && data.substring(0, 5) === \"<meta\") {\r\n            data = null;\r\n          }\r\n\r\n          if (data) {\r\n            resArr.push(data);\r\n          }\r\n        }\r\n\r\n        // Assign extracted metadata to metadataObj\r\n        Object.keys(metadataObj.gpxFileMetadata).forEach(async (property, f) => {\r\n          metadataObj.gpxFileMetadata[property] = resArr[f - 1];\r\n          if (Object.keys(metadataObj.gpxFileMetadata).length === f + 1) {\r\n            // Up values into object\r\n            metadataObj = {\r\n              ...metadataObj,\r\n              gpxFileMetadata: {\r\n                ...metadataObj.gpxFileMetadata,\r\n                gpxFileCreatorName: gpxFileCreatorName,\r\n                gpxFileBounds: boundsObj,\r\n                gpxFileLink: linkObj\r\n              }\r\n            };\r\n\r\n            debugMode && await messageConcat({ methodName: `getMetaData`, messagesArrObj: [{ message: `${JSON.stringify(metadataObj)}`, color: \"black\" }] });\r\n            resolve(metadataObj);\r\n          }\r\n        });\r\n      } else {\r\n        console.log(\":| No metadata tags in your gpx file.\".yellow);\r\n        debugMode && await messageConcat({ methodName: `getMetaData`, messagesArrObj: [{ message: `${JSON.stringify(metadataObj)}`, color: \"black\" }] });\r\n        resolve(metadataObj);\r\n      }\r\n    } catch (error) {\r\n      console.error(`:( getMetaData error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\n// Calculate between positions - Return the distance between (lat1,lon1) and (lat2,lon2)\r\nconst calculateDistanceBetweenPositions: CalculateDistanceBetweenPositions = async (positionsArrayObj) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // Earth radius in meters\r\n      const radius = 6378137.0;\r\n\r\n      // Degree to radian conversion\r\n      let DE2RA = 0.01745329252;\r\n\r\n      // Extracting parameters\r\n      let lat1 = positionsArrayObj[0].lat;\r\n      let lon1 = positionsArrayObj[0].lon;\r\n      let lat2 = positionsArrayObj[1].lat;\r\n      let lon2 = positionsArrayObj[1].lon;\r\n\r\n      // If the positions are different\r\n      if (lat1 && lon1 && lat2 && lon2 && lat1 !== lat2 && lon1 !== lon2) {\r\n        // Convert degrees to radians\r\n        lat1 *= DE2RA;\r\n        lon1 *= DE2RA;\r\n        lat2 *= DE2RA;\r\n        lon2 *= DE2RA;\r\n\r\n        // Calculate distance\r\n        const d = Math.sin(lat1) * Math.sin(lat2) + Math.cos(lat1) * Math.cos(lat2) * Math.cos(lon1 - lon2);\r\n\r\n        // Distance in meters\r\n        const distance = radius * Math.acos(d);\r\n\r\n        resolve(distance);\r\n      } else {\r\n        resolve(0);\r\n      }\r\n    } catch (error) {\r\n      console.log(\":( calculateDistanceBetweenPositions error\".red);\r\n      reject(console.log);\r\n    }\r\n  });\r\n};\r\n\r\n// Track distance calculation\r\nconst trackDistanceCalculation: TrackDistanceCalculation = async ({ positionsArray, debugMode }) => {\r\n  return new Promise(async (resolve, reject) => {\r\n    try {\r\n      // let positionsArray =  [[42.913941, -8.0148, 456.5],[42.926359, -8.162513, 389.7]]\r\n      // Check if track tag exists (> 1 because it need 2 arrays minimum to calculate a distance)\r\n      if (positionsArray.length > 1) {\r\n        // Default\r\n        let totalDistance: number = 0;\r\n\r\n        for (let i = 0; i < positionsArray.length; i++) {\r\n          // Stop before the last object (it need 2 arrays minimum to calculate a distance)\r\n          if (positionsArray[i + 1] && positionsArray[i][1]) {\r\n            // Positions array\r\n            const arrObj: GetPositionsArrData[] = [\r\n              { lat: positionsArray[i][0], lon: positionsArray[i][1] },\r\n              { lat: positionsArray[i + 1][0], lon: positionsArray[i + 1][1] },\r\n            ];\r\n\r\n            // Distance calculation\r\n            const distance = await calculateDistanceBetweenPositions(arrObj);\r\n\r\n            // Record the new distance\r\n            totalDistance += distance;\r\n\r\n            // End loop - Last & first item are not counted !! but i only & total length - 2\r\n            // if (positionsArr.length - 2 === i) {\r\n            //   console.log(\"i_\", i);\r\n            //   console.log(\"positionsArr.length_\", positionsArr.length - 2);\r\n            //   console.log(\"totalDistance\", totalDistance);\r\n            // }\r\n          }\r\n        }\r\n\r\n        debugMode && await messageConcat({ methodName: `trackDistanceCalculation`, messagesArrObj: [{ message: `${JSON.stringify(totalDistance)}`, color: \"black\" }] });\r\n        resolve(totalDistance)\r\n      } else {\r\n        debugMode && await messageConcat({ methodName: `trackDistanceCalculation`, messagesArrObj: [{ message: `${JSON.stringify(null)}`, color: \"black\" }] });\r\n        resolve(null);\r\n      }\r\n    } catch (error) {\r\n      console.error(`:( trackDistanceCalculation error => ${error}`);\r\n      reject(error);\r\n    }\r\n  });\r\n};\r\n\r\nexport {\r\n  messageConcat,\r\n  rootAppPath,\r\n  readGpxFile,\r\n  getStringBetweenIncludedPatterns,\r\n  mergeStagesTrackData,\r\n  getString,\r\n  getLinkTrk,\r\n  getExtensions,\r\n  getTracks,\r\n  getRoutes,\r\n  getWayPoints,\r\n  dataExtraction,\r\n  splitString,\r\n  getCumulativeElevations,\r\n  convertPositionsToArr,\r\n  getPositionsArr,\r\n  getElevationsArr,\r\n  getTagsValueArr,\r\n  getBounds,\r\n  getLink,\r\n  getMetaData,\r\n  calculateDistanceBetweenPositions,\r\n  trackDistanceCalculation\r\n}","// Libs\r\nimport { readGpxFile, dataExtraction } from './lib/gpsLib';\r\n\r\n// Types\r\nimport { DataExtractionProps } from './types/gpsLibType';\r\n\r\nconst extractGpxData = async (gpxFilePath: string, debugMode: boolean): Promise<any> => {\r\n  try {\r\n    if (typeof gpxFilePath !== \"string\") {\r\n      console.log(`:( GPX file ${gpxFilePath} is wrong`);\r\n      return;\r\n    } else {\r\n      // Read the Gpx file\r\n      const gpxContent = await readGpxFile({ gpxFilePath: gpxFilePath, debugMode: debugMode });\r\n\r\n      // Check existing file\r\n      if (!gpxContent) {\r\n        console.log(`:( Unable to read file \"${gpxFilePath}\"`);\r\n        return;\r\n      }\r\n\r\n      // Extract\r\n      const { gpxFileStr } = gpxContent;\r\n\r\n      if (typeof gpxFileStr !== \"string\") {\r\n        // Handle unexpected types here, if necessary\r\n        console.log(`:( Unexpected GPX file contents`);\r\n        return;\r\n      }\r\n\r\n      // Prepare DataExtractionProps object\r\n      const dataExtractionProps: DataExtractionProps = { readGpxFile: gpxFileStr, debugMode: debugMode };\r\n\r\n      // Data extraction\r\n      const dataExtractionObj = await dataExtraction(dataExtractionProps);\r\n\r\n      return dataExtractionObj;\r\n    }\r\n  } catch (error) {\r\n    console.log(`:( An error occurred while extracting GPX data: ${error}`);\r\n    console.error(error);\r\n    return false;\r\n  }\r\n};\r\n\r\nexport { extractGpxData };\r\n"],"mappings":"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","names":["mergeStagesTrackData","readGpxFile","promises"]}