From 3227c7bc6bd233c92b1cf54bec689f0582dca547 Mon Sep 17 00:00:00 2001 From: Ariel Costas Guerrero Date: Mon, 1 Dec 2025 22:25:56 +0100 Subject: refactor: replace StopSheet with StopSummarySheet and update related components - Deleted StopSheet and StopSheetSkeleton components. - Introduced StopSummarySheet and StopSummarySheetSkeleton components. - Updated ConsolidatedCirculationCard to support a reduced view. - Modified ConsolidatedCirculationList to accept a reduced prop. - Adjusted map route to use StopSummarySheet. - Cleaned up CSS styles related to the stop sheet components. - Enhanced error handling and loading states in the new summary sheet. - Updated stop report logic to filter out empty next streets. --- src/frontend/app/components/StopSheet.tsx | 213 ------------------------------ 1 file changed, 213 deletions(-) delete mode 100644 src/frontend/app/components/StopSheet.tsx (limited to 'src/frontend/app/components/StopSheet.tsx') diff --git a/src/frontend/app/components/StopSheet.tsx b/src/frontend/app/components/StopSheet.tsx deleted file mode 100644 index 77bb5f1..0000000 --- a/src/frontend/app/components/StopSheet.tsx +++ /dev/null @@ -1,213 +0,0 @@ -import { RefreshCw } from "lucide-react"; -import React, { useEffect, useState } from "react"; -import { useTranslation } from "react-i18next"; -import { Sheet } from "react-modal-sheet"; -import { Link } from "react-router"; -import { REGION_DATA } from "~/config/RegionConfig"; -import type { Stop } from "~/data/StopDataProvider"; -import { type ConsolidatedCirculation } from "../routes/stops-$id"; -import { ErrorDisplay } from "./ErrorDisplay"; -import LineIcon from "./LineIcon"; -import { StopAlert } from "./StopAlert"; -import { ConsolidatedCirculationCard } from "./Stops/ConsolidatedCirculationCard"; -import "./StopSheet.css"; -import { StopSheetSkeleton } from "./StopSheetSkeleton"; - -interface StopSheetProps { - isOpen: boolean; - onClose: () => void; - stop: Stop; -} - -interface ErrorInfo { - type: "network" | "server" | "unknown"; - status?: number; - message?: string; -} - -const loadConsolidatedData = async ( - stopId: number -): Promise => { - const resp = await fetch( - `${REGION_DATA.consolidatedCirculationsEndpoint}?stopId=${stopId}`, - { - headers: { - Accept: "application/json", - }, - } - ); - - if (!resp.ok) { - throw new Error(`HTTP ${resp.status}: ${resp.statusText}`); - } - - return await resp.json(); -}; - -export const StopSheet: React.FC = ({ - isOpen, - onClose, - stop, -}) => { - const { t } = useTranslation(); - const [data, setData] = useState(null); - const [loading, setLoading] = useState(false); - const [error, setError] = useState(null); - const [lastUpdated, setLastUpdated] = useState(null); - - const parseError = (error: any): ErrorInfo => { - if (!navigator.onLine) { - return { type: "network", message: "No internet connection" }; - } - - if ( - error.message?.includes("Failed to fetch") || - error.message?.includes("NetworkError") - ) { - return { type: "network" }; - } - - if (error.message?.includes("HTTP")) { - const statusMatch = error.message.match(/HTTP (\d+):/); - const status = statusMatch ? parseInt(statusMatch[1]) : undefined; - return { type: "server", status }; - } - - return { type: "unknown", message: error.message }; - }; - - const loadData = async () => { - try { - setLoading(true); - setError(null); - setData(null); - - const stopData = await loadConsolidatedData(stop.stopId); - setData(stopData); - setLastUpdated(new Date()); - } catch (err) { - console.error("Failed to load stop data:", err); - setError(parseError(err)); - } finally { - setLoading(false); - } - }; - - useEffect(() => { - if (isOpen && stop.stopId) { - loadData(); - } - }, [isOpen, stop.stopId]); - - // Show only the next 4 arrivals - const sortedData = data - ? [...data].sort( - (a, b) => - (a.realTime?.minutes ?? a.schedule?.minutes ?? 999) - - (b.realTime?.minutes ?? b.schedule?.minutes ?? 999) - ) - : []; - const limitedEstimates = sortedData.slice(0, 4); - - return ( - - - - -
-
-

{stop.name.original}

- ({stop.stopId}) -
- -
= 10 ? "scrollable" : ""}`} - > - {stop.lines.map((line) => ( -
- -
- ))} -
- - - - {loading ? ( - - ) : error ? ( - - ) : data ? ( - <> -
-

- {t("estimates.next_arrivals", "Next arrivals")} -

- - {limitedEstimates.length === 0 ? ( -
- {t("estimates.none", "No hay estimaciones disponibles")} -
- ) : ( -
- {limitedEstimates.map((estimate, idx) => ( - - ))} -
- )} -
- - ) : null} -
-
- -
- {lastUpdated && ( -
- {t("estimates.last_updated", "Actualizado a las")}{" "} - {lastUpdated.toLocaleTimeString(undefined, { - hour: "2-digit", - minute: "2-digit", - second: "2-digit", - })} -
- )} - -
- - - - {t("map.view_all_estimates", "Ver todas las estimaciones")} - -
-
-
- -
- ); -}; -- cgit v1.3