From e9b6da4581b01272f8b48fabb1f3bad4da3a0743 Mon Sep 17 00:00:00 2001 From: Alex kiwijos Lindqvist Date: Sun, 22 Oct 2023 21:59:37 +0200 Subject: [PATCH 1/3] Add function for retrieving satations data --- src/db/repository/trainRepository.ts | 91 +++++++++++++++++++++++----- 1 file changed, 76 insertions(+), 15 deletions(-) diff --git a/src/db/repository/trainRepository.ts b/src/db/repository/trainRepository.ts index 361c791..cb629ee 100644 --- a/src/db/repository/trainRepository.ts +++ b/src/db/repository/trainRepository.ts @@ -1,13 +1,73 @@ import fetch from "node-fetch"; const API_URL = "https://api.trafikinfo.trafikverket.se/v2/data.json"; + // Cache announcements to prevent over-fetching -const cache = new Map(); +const delayedCache = new Map(); let changeid = "0"; +const stationCache = new Map(); + const codeCache = new Map(); const trainRepository = { + getTrainStations: async () => { + if (stationCache.has("stations")) { + return { + ok: true, + data: stationCache.get("stations"), + error: null + }; + } + + const query = ` + + + + AdvertisedLocationName + Geometry + LocationSignature + + `; + + try { + const response = await fetch(API_URL, { + method: "POST", + body: query, + headers: { "Content-Type": "text/xml" } + }); + const result = await response.json(); + + // Replace the Geometry object with longitude and latitude + const stations = result.RESPONSE.RESULT[0].TrainStation.map((station) => { + const [longitude, latitude] = station.Geometry.WGS84.split("POINT ")[1] + .split("(")[1] + .split(")")[0] + .split(" "); + + return { + AdvertisedLocationName: station.AdvertisedLocationName, + Longitude: longitude, + Latitude: latitude, + LocationSignature: station.LocationSignature + }; + }); + + stationCache.set("stations", stations); + + return { + ok: true, + data: stations, + error: null + }; + } catch (err) { + return { + ok: false, + data: null, + error: err.message + }; + } + }, getTrainDelays: async () => { const query = ` @@ -45,37 +105,40 @@ const trainRepository = { body: query, headers: { "Content-Type": "text/xml" } }); + const result = await response.json(); + // Update id to only fetch newer entries changeid = result.RESPONSE.RESULT[0].INFO.LASTCHANGEID; - if (cache.size === 0) { - // Initially populate cache with all announcements + + if (delayedCache.size === 0) { + // Initially populate delayedCache with all announcements result.RESPONSE.RESULT[0].TrainAnnouncement.forEach((delay) => { - cache.set(delay.ActivityId, delay); + delayedCache.set(delay.ActivityId, delay); }); } else if (result.RESPONSE.RESULT[0].TrainAnnouncement.length > 0) { // Add only new announcements and remove those that have been deleted (if any) result.RESPONSE.RESULT[0].TrainAnnouncement.forEach((delay) => { - if (cache.has(delay.ActivityId)) { + if (delayedCache.has(delay.ActivityId)) { if (delay?.Deleted === true) { - cache.delete(delay.ActivityId); + delayedCache.delete(delay.ActivityId); } } else { - cache.set(delay.ActivityId, delay); + delayedCache.set(delay.ActivityId, delay); } }); } - const data = Array.from(cache.values()); + return { ok: true, - data: data, + data: Array.from(delayedCache.values()), error: null }; } catch (err) { return { ok: false, data: null, - error: err + error: err.message }; } }, @@ -119,11 +182,9 @@ const trainRepository = { console.error(`Error fetching codes: ${err}`); return { - errors: { - ok: false, - data: null, - error: err.Message - } + ok: false, + data: null, + error: err.Message }; } } From c5de9e34d08d71479beb5965641498f3c9fffac5 Mon Sep 17 00:00:00 2001 From: Alex kiwijos Lindqvist Date: Sun, 22 Oct 2023 22:37:42 +0200 Subject: [PATCH 2/3] Add query for retrieving stations data --- src/config/schema/query.ts | 3 +++ src/config/schema/schema.ts | 15 ++++++++++++--- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/src/config/schema/query.ts b/src/config/schema/query.ts index 0705ee7..14e9c13 100644 --- a/src/config/schema/query.ts +++ b/src/config/schema/query.ts @@ -13,6 +13,9 @@ const query = { }, ticketCodes: async () => { return await trainRepository.getTrainCodes(); + }, + trainStations: async () => { + return await trainRepository.getTrainStations(); } }; diff --git a/src/config/schema/schema.ts b/src/config/schema/schema.ts index a562fbf..f9e2b31 100644 --- a/src/config/schema/schema.ts +++ b/src/config/schema/schema.ts @@ -6,6 +6,7 @@ const schema = buildSchema(` ticket(id: ID!): Ticket trainDelays: TrainDelayResponse ticketCodes: TicketCodeResponse + trainStations: TrainStationResponse } type Mutation { createTicket(code: String!, trainnumber: String!, traindate: String!): TicketResponse @@ -22,6 +23,11 @@ const schema = buildSchema(` error: String data: [TicketCode] } + type TrainStationResponse { + ok: Boolean + error: String + data: [TrainStation] + } type TicketCode { Code: String Level1Description: String @@ -41,6 +47,12 @@ const schema = buildSchema(` ToLocation: [TrainLocation] TrainOwner: String } + type TrainStation { + AdvertisedLocationName: String! + LocationSignature: String! + Longitude: String! + Latitude: String! + } type TrainLocation { LocationName: String! Order: Int! @@ -52,9 +64,6 @@ const schema = buildSchema(` trainnumber: String! traindate: String! } - type Tickets { - tickets: [Ticket] - } type TicketResponse { data: Ticket error: String From ef56f2f7ca18bb0cd91b4f17aed3c3a8f76665b7 Mon Sep 17 00:00:00 2001 From: Alex kiwijos Lindqvist Date: Mon, 23 Oct 2023 09:31:37 +0200 Subject: [PATCH 3/3] Disable graphql graphical interface --- src/config/app.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/config/app.ts b/src/config/app.ts index cc26fd6..f5867d3 100644 --- a/src/config/app.ts +++ b/src/config/app.ts @@ -25,14 +25,14 @@ app.use("/tickets", jwtAuth.checkToken, tickets); app.use("/codes", jwtAuth.checkToken, codes); // Make handler a graphql handler -app.use("/auth", graphqlHTTP({ schema: authSchema, rootValue: authResolver, graphiql: true })); +app.use("/auth", graphqlHTTP({ schema: authSchema, rootValue: authResolver, graphiql: false })); app.use( "/graphql", graphqlHTTP({ schema, rootValue: resolver, - graphiql: true + graphiql: false }) );