import json, tables, options, sequtils, strutils, algorithm, math import nimhafas import ../cache_types, formaters template getPlannedOrPrognosedTime(obj: untyped): int64 = if not obj.prognosedTime.isNone: obj.prognosedTime.get else: obj.plannedTime proc renderJourneys*(data: CacheObject): JsonNode = var data = data; result = newJObject() result["REQ_ID"] = %data.reqId result["FROM"] = %formatPoint(data.params.fromPoint) result["TO"] = %formatPoint(data.params.toPoint) result["JOURNEYS"] = newJArray() var journeys = toSeq(data.journeys.pairs).map(proc (i: (string, Journey)): (int, Journey) = (parseInt(i[0]), i[1])).sorted(proc (b, a: (int, Journey)): int = b[0] - a[0]) for id, journey in items(journeys): let departureLeg = journey.legs[0] let arrivalLeg = journey.legs[journey.legs.len-1] let departureTime = getPlannedOrPrognosedTime(departureLeg.departure) let arrivalTime = getPlannedOrPrognosedTime(arrivalLeg.arrival) var products = initTable[string, seq[string]]() var productsCombined: seq[string] var changes: int var changesDuration: int var cancelled: bool var departureDelay: string var arrivalDelay: string var departureHasDelay: bool var arrivalHasDelay: bool if departureLeg.departure.prognosedTime.isSome: let delay = floorDiv((departureLeg.departure.prognosedTime.get - departureLeg.departure.plannedTime), 60) if delay != 0: departureHasDelay = true if delay > 0: departureDelay = "+" departureDelay &= $delay if arrivalLeg.arrival.prognosedTime.isSome: let delay = floorDiv((arrivalLeg.arrival.prognosedTime.get - arrivalLeg.arrival.plannedTime), 60) if delay != 0: arrivalHasDelay = true if delay > 0: arrivalDelay = "+" arrivalDelay &= $delay for leg in journey.legs: if leg.cancelled != false: cancelled = true if leg.isWalking: products["Fußweg"] = newSeq[string]() continue if leg.isTransfer: continue inc(changes) if not products.contains(leg.line.get.productName): products[leg.line.get.productName] = newSeq[string]() if leg.line.get.trainTypeShort.isSome(): products[leg.line.get.productName].add(leg.line.get.trainTypeShort.get) for product, types in pairs(products): let typesLen = types.len if typesLen > 1: productsCombined.add(product & " (" & types.join(", ") & ")") elif typesLen == 1: productsCombined.add(product & " " & types[0]) else: productsCombined.add(product) let productsString = productsCombined.join(", ") result["JOURNEYS"].add(%* { "ID": id, "ARRIVAL": formatTime(arrivalTime, ""), "ARRIVAL_HAS_DELAY": arrivalHasDelay, "ARRIVAL_DELAY": arrivalDelay, "DEPARTURE": formatTime(departureTime, ""), "DURATION": formatDuration(arrivalTime - departureTime), "DEPARTURE_HAS_DELAY": departureHasDelay, "DEPARTURE_DELAY": departureDelay, "CHANGES_DUR": changesDuration, "CHANGES": changes-1, "PRODUCTS": productsString, "IS_CANCELLED": cancelled })