From 4753ee401c00ff3e98dee25c01df64d219727e9c Mon Sep 17 00:00:00 2001 From: Gurudas Bhardwaj Date: Sat, 14 Feb 2026 12:20:06 +0530 Subject: [PATCH 1/2] feat: integrate Mapbox for enhanced mapping functionality - Added HomeMap component to display a Mapbox map with geolocation features. - Updated Home page to render the HomeMap component. - Introduced PrivateLayout component for consistent layout structure. - Updated TypeScript configuration to include additional type definitions. - Added Mapbox GL and related dependencies to package.json and package-lock.json. - Created global.d.ts for Mapbox CSS module declaration. --- client/app/(private)/home/page.tsx | 21 +- client/app/(private)/layout.tsx | 7 + client/components/home/HomeMap.tsx | 310 ++++++++++++++++++++++ client/components/landing/Footer.tsx | 2 +- client/components/profile/ProfileCard.tsx | 4 +- client/package-lock.json | 254 ++++++++++++++++++ client/package.json | 1 + client/tsconfig.json | 3 +- client/types/global.d.ts | 1 + server/src/middleware/tokenVerify.ts | 4 +- 10 files changed, 583 insertions(+), 24 deletions(-) create mode 100644 client/app/(private)/layout.tsx create mode 100644 client/components/home/HomeMap.tsx create mode 100644 client/types/global.d.ts diff --git a/client/app/(private)/home/page.tsx b/client/app/(private)/home/page.tsx index 1c5c7b8..68a2e36 100644 --- a/client/app/(private)/home/page.tsx +++ b/client/app/(private)/home/page.tsx @@ -1,22 +1,5 @@ -"use client"; +import HomeMap from "@/components/home/HomeMap"; export default function Home() { - const handleLogout = () => { - window.location.href = `${process.env.NEXT_PUBLIC_BACKEND_URL}/api/v1/auth/google/logout`; - }; - - return ( -
-
-

Home

-

You are logged in!

- -
-
- ); + return ; } diff --git a/client/app/(private)/layout.tsx b/client/app/(private)/layout.tsx new file mode 100644 index 0000000..d40dfb1 --- /dev/null +++ b/client/app/(private)/layout.tsx @@ -0,0 +1,7 @@ +export default function PrivateLayout({ + children, +}: { + children: React.ReactNode; +}) { + return <>{children}; +} diff --git a/client/components/home/HomeMap.tsx b/client/components/home/HomeMap.tsx new file mode 100644 index 0000000..df8f65d --- /dev/null +++ b/client/components/home/HomeMap.tsx @@ -0,0 +1,310 @@ +"use client"; + +import { useEffect, useMemo, useRef, useState } from "react"; + +import { ArrowRight, Info, MapPin, ShieldCheck } from "lucide-react"; +import mapboxgl from "mapbox-gl"; +import "mapbox-gl/dist/mapbox-gl.css"; + +type HomeMapProps = { + className?: string; +}; + +export default function HomeMap({ className }: HomeMapProps) { + const mapContainerRef = useRef(null); + const mapRef = useRef(null); + const [showRightModal, setShowRightModal] = useState(true); + const revealTimeoutRef = useRef | null>(null); + const mapboxToken = process.env.NEXT_PUBLIC_MAPBOX_TOKEN || ""; + const [mapStatus, setMapStatus] = useState< + "loading" | "ready" | "error" | "no-token" + >(mapboxToken ? "loading" : "no-token"); + const [mapError, setMapError] = useState(null); + const [geoError, setGeoError] = useState(null); + + const mapStatusLabel = useMemo(() => { + if (mapStatus === "no-token") return "Mapbox token missing"; + if (mapStatus === "error") return mapError || "Map failed to load"; + if (mapStatus === "loading") return "Loading map..."; + return ""; + }, [mapStatus, mapError]); + + useEffect(() => { + const container = mapContainerRef.current; + if (!container) return; + if (mapRef.current) return; + + if (!mapboxToken) return; + mapboxgl.accessToken = mapboxToken; + + const map = new mapboxgl.Map({ + container, + style: "mapbox://styles/mapbox/light-v11", + center: [0, 0], + zoom: 2, + attributionControl: false, + }); + + mapRef.current = map; + map.addControl( + new mapboxgl.NavigationControl({ showCompass: false }), + "bottom-right" + ); + + const handleMapLoad = () => setMapStatus("ready"); + const handleMapError = () => { + setMapStatus("error"); + setMapError("Map failed to load. Check your token or network."); + }; + + map.on("load", handleMapLoad); + map.on("error", handleMapError); + + const hideRightModal = () => { + if (revealTimeoutRef.current) clearTimeout(revealTimeoutRef.current); + setShowRightModal(false); + }; + + const scheduleShowRightModal = () => { + if (revealTimeoutRef.current) clearTimeout(revealTimeoutRef.current); + revealTimeoutRef.current = setTimeout(() => { + setShowRightModal(true); + }, 1000); + }; + + map.on("movestart", hideRightModal); + map.on("moveend", scheduleShowRightModal); + + let marker: mapboxgl.Marker | null = null; + + if (navigator.geolocation) { + navigator.geolocation.getCurrentPosition( + (position) => { + const { longitude, latitude } = position.coords; + map.flyTo({ + center: [longitude, latitude], + zoom: 13, + essential: true, + }); + + marker = new mapboxgl.Marker({ color: "#2bee6c" }) + .setLngLat([longitude, latitude]) + .addTo(map); + }, + (error) => { + setGeoError(error.message || "Location permission was denied."); + map.flyTo({ center: [0, 0], zoom: 2 }); + }, + { enableHighAccuracy: true, timeout: 8000 } + ); + } else { + setTimeout(() => { + setGeoError("Geolocation is not supported in this browser."); + }, 0); + } + + const resize = () => map.resize(); + const raf = requestAnimationFrame(resize); + window.addEventListener("resize", resize); + + let resizeObserver: ResizeObserver | null = null; + if (typeof ResizeObserver !== "undefined") { + resizeObserver = new ResizeObserver(resize); + resizeObserver.observe(container); + } + + return () => { + map.off("movestart", hideRightModal); + map.off("moveend", scheduleShowRightModal); + map.off("load", handleMapLoad); + map.off("error", handleMapError); + if (revealTimeoutRef.current) clearTimeout(revealTimeoutRef.current); + if (marker) marker.remove(); + window.removeEventListener("resize", resize); + if (resizeObserver) resizeObserver.disconnect(); + cancelAnimationFrame(raf); + map.remove(); + mapRef.current = null; + }; + }, [mapboxToken]); + + return ( +
+ {/* Map Background */} +
+
+
+ + {/* Subtle Air Quality Blobs */} +
+
+ + {mapStatus !== "ready" && ( +
+
+ {mapStatusLabel} +
+
+ )} + + {/* Floating Overlays */} +
+ {/* Left Section: Search Card — compact */} +
+
+

+ Start your healthy journey +

+

+ Enter your route to find the cleanest path. +

+
+
+ +
+
+ +
+ +
+
+ +
+ +
+
+ +
+ +
+ + {geoError && ( +
+ {geoError} +
+ )} + +
+
+
+
+ + Clean + +
+
+
+ + Fair + +
+
+
+ + Poor + +
+
+ + Live Air Quality Data + +
+
+
+ + {/* Right Section: Onboarding — prominent emphasis */} + +
+
+
+ ); +} diff --git a/client/components/landing/Footer.tsx b/client/components/landing/Footer.tsx index 48b3689..b8ee9c2 100644 --- a/client/components/landing/Footer.tsx +++ b/client/components/landing/Footer.tsx @@ -1,6 +1,6 @@ import Link from "next/link"; -import { AtSign, Globe, Leaf } from "lucide-react"; +import { AtSign, Globe } from "lucide-react"; const footerLinks = { "Web App": [ diff --git a/client/components/profile/ProfileCard.tsx b/client/components/profile/ProfileCard.tsx index 962591a..8ea2559 100644 --- a/client/components/profile/ProfileCard.tsx +++ b/client/components/profile/ProfileCard.tsx @@ -1,3 +1,5 @@ +import Image from "next/image"; + import { Calendar, Mail, MapPin, Shield, User } from "lucide-react"; import type { UserData } from "./types"; @@ -23,7 +25,7 @@ export default function ProfileCard({ user }: { user: UserData }) {
{user.picture ? ( - {user.name}= 0.6" + } + }, + "node_modules/@mapbox/mapbox-gl-supported": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@mapbox/mapbox-gl-supported/-/mapbox-gl-supported-3.0.0.tgz", + "integrity": "sha512-2XghOwu16ZwPJLOFVuIOaLbN0iKMn867evzXFyf0P22dqugezfJwLmdanAgU25ITvz1TvOfVP4jsDImlDJzcWg==", + "license": "BSD-3-Clause" + }, + "node_modules/@mapbox/point-geometry": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@mapbox/point-geometry/-/point-geometry-1.1.0.tgz", + "integrity": "sha512-YGcBz1cg4ATXDCM/71L9xveh4dynfGmcLDqufR+nQQy3fKwsAZsWd/x4621/6uJaeB9mwOHE6hPeDgXz9uViUQ==", + "license": "ISC" + }, + "node_modules/@mapbox/tiny-sdf": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/@mapbox/tiny-sdf/-/tiny-sdf-2.0.7.tgz", + "integrity": "sha512-25gQLQMcpivjOSA40g3gO6qgiFPDpWRoMfd+G/GoppPIeP6JDaMMkMrEJnMZhKyyS6iKwVt5YKu02vCUyJM3Ug==", + "license": "BSD-2-Clause" + }, + "node_modules/@mapbox/unitbezier": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/@mapbox/unitbezier/-/unitbezier-0.0.1.tgz", + "integrity": "sha512-nMkuDXFv60aBr9soUG5q+GvZYL+2KZHVvsqFCzqnkGEf46U2fvmytHaEVc1/YZbiLn8X+eR3QzX1+dwDO1lxlw==", + "license": "BSD-2-Clause" + }, + "node_modules/@mapbox/vector-tile": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/@mapbox/vector-tile/-/vector-tile-2.0.4.tgz", + "integrity": "sha512-AkOLcbgGTdXScosBWwmmD7cDlvOjkg/DetGva26pIRiZPdeJYjYKarIlb4uxVzi6bwHO6EWH82eZ5Nuv4T5DUg==", + "license": "BSD-3-Clause", + "dependencies": { + "@mapbox/point-geometry": "~1.1.0", + "@types/geojson": "^7946.0.16", + "pbf": "^4.0.1" + } + }, + "node_modules/@mapbox/whoots-js": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@mapbox/whoots-js/-/whoots-js-3.1.0.tgz", + "integrity": "sha512-Es6WcD0nO5l+2BOQS4uLfNPYQaNDfbot3X1XUoloz+x0mPDS3eeORZJl06HXjwBG1fOGwCRnzK88LMdxKRrd6Q==", + "license": "ISC", + "engines": { + "node": ">=6.0.0" + } + }, "node_modules/@modelcontextprotocol/sdk": { "version": "1.26.0", "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.26.0.tgz", @@ -3866,6 +3919,21 @@ "dev": true, "license": "MIT" }, + "node_modules/@types/geojson": { + "version": "7946.0.16", + "resolved": "https://registry.npmjs.org/@types/geojson/-/geojson-7946.0.16.tgz", + "integrity": "sha512-6C8nqWur3j98U6+lXDfTUWIfgvZU+EumvpHKcYjujKH7woYyLj2sUmff0tRhrqM7BohUw7Pz3ZB1jj2gW9Fvmg==", + "license": "MIT" + }, + "node_modules/@types/geojson-vt": { + "version": "3.2.5", + "resolved": "https://registry.npmjs.org/@types/geojson-vt/-/geojson-vt-3.2.5.tgz", + "integrity": "sha512-qDO7wqtprzlpe8FfQ//ClPV9xiuoh2nkIgiouIptON9w5jvD/fA4szvP9GBlDVdJ5dldAl0kX/sy3URbWwLx0g==", + "license": "MIT", + "dependencies": { + "@types/geojson": "*" + } + }, "node_modules/@types/json-schema": { "version": "7.0.15", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", @@ -3880,6 +3948,12 @@ "dev": true, "license": "MIT" }, + "node_modules/@types/mapbox__point-geometry": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/@types/mapbox__point-geometry/-/mapbox__point-geometry-0.1.4.tgz", + "integrity": "sha512-mUWlSxAmYLfwnRBmgYV86tgYmMIICX4kza8YnE/eIlywGe2XoOxlpVnXWwir92xRLjwyarqwpu2EJKD2pk0IUA==", + "license": "MIT" + }, "node_modules/@types/node": { "version": "20.19.33", "resolved": "https://registry.npmjs.org/@types/node/-/node-20.19.33.tgz", @@ -3890,6 +3964,12 @@ "undici-types": "~6.21.0" } }, + "node_modules/@types/pbf": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/@types/pbf/-/pbf-3.0.5.tgz", + "integrity": "sha512-j3pOPiEcWZ34R6a6mN07mUkM4o4Lwf6hPNt8eilOeZhTFbxFXmKhvXl9Y28jotFPaI1bpPDJsbCprUoNke6OrA==", + "license": "MIT" + }, "node_modules/@types/react": { "version": "19.2.14", "resolved": "https://registry.npmjs.org/@types/react/-/react-19.2.14.tgz", @@ -3917,6 +3997,15 @@ "dev": true, "license": "MIT" }, + "node_modules/@types/supercluster": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/@types/supercluster/-/supercluster-7.1.3.tgz", + "integrity": "sha512-Z0pOY34GDFl3Q6hUFYf3HkTwKEE02e7QgtJppBt+beEAxnyOpJua+voGFvxINBHa06GwLFFym7gRPY2SiKIfIA==", + "license": "MIT", + "dependencies": { + "@types/geojson": "*" + } + }, "node_modules/@types/validate-npm-package-name": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/@types/validate-npm-package-name/-/validate-npm-package-name-4.0.2.tgz", @@ -5084,6 +5173,12 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, + "node_modules/cheap-ruler": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/cheap-ruler/-/cheap-ruler-4.0.0.tgz", + "integrity": "sha512-0BJa8f4t141BYKQyn9NSQt1PguFQXMXwZiA5shfoaBYHAb2fFk2RAX+tiWMoQU+Agtzt3mdt0JtuyshAXqZ+Vw==", + "license": "ISC" + }, "node_modules/class-variance-authority": { "version": "0.7.1", "resolved": "https://registry.npmjs.org/class-variance-authority/-/class-variance-authority-0.7.1.tgz", @@ -5383,6 +5478,12 @@ "node": ">= 8" } }, + "node_modules/csscolorparser": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/csscolorparser/-/csscolorparser-1.0.3.tgz", + "integrity": "sha512-umPSgYwZkdFoUrH5hIq5kf0wPSXiro51nPw0j2K/c83KflkPSTBGMz6NJvMB+07VlL0y7VPo6QJcDjcgKTTm3w==", + "license": "MIT" + }, "node_modules/cssesc": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/cssesc/-/cssesc-3.0.0.tgz", @@ -5680,6 +5781,12 @@ "node": ">= 0.4" } }, + "node_modules/earcut": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/earcut/-/earcut-3.0.2.tgz", + "integrity": "sha512-X7hshQbLyMJ/3RPhyObLARM2sNxxmRALLKx1+NVFFnQ9gKzmCrxm9+uLIAdBcvc8FNLpctqlQ2V6AE92Ol9UDQ==", + "license": "ISC" + }, "node_modules/eciesjs": { "version": "0.4.17", "resolved": "https://registry.npmjs.org/eciesjs/-/eciesjs-0.4.17.tgz", @@ -6874,6 +6981,12 @@ "node": ">=6.9.0" } }, + "node_modules/geojson-vt": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/geojson-vt/-/geojson-vt-4.0.2.tgz", + "integrity": "sha512-AV9ROqlNqoZEIJGfm1ncNjEXfkz2hdFlZf0qkVfmkwdKa8vj7H16YUOT81rJw1rdFhyEDlN2Tds91p/glzbl5A==", + "license": "ISC" + }, "node_modules/get-caller-file": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", @@ -7006,6 +7119,12 @@ "url": "https://github.com/privatenumber/get-tsconfig?sponsor=1" } }, + "node_modules/gl-matrix": { + "version": "3.4.4", + "resolved": "https://registry.npmjs.org/gl-matrix/-/gl-matrix-3.4.4.tgz", + "integrity": "sha512-latSnyDNt/8zYUB6VIJ6PCh2jBjJX6gnDsoCZ7LyW7GkqrD51EWwa9qCoGixj8YqBtETQK/xY7OmpTF8xz1DdQ==", + "license": "MIT" + }, "node_modules/glob-parent": { "version": "6.0.2", "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", @@ -7079,6 +7198,12 @@ "node": "^12.22.0 || ^14.16.0 || ^16.0.0 || >=17.0.0" } }, + "node_modules/grid-index": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/grid-index/-/grid-index-1.1.0.tgz", + "integrity": "sha512-HZRwumpOGUrHyxO5bqKZL0B0GlUpwtCAzZ42sgxUPniu33R1LSFH5yrIcBCHjkctCAh3mtWKcKd9J4vDDdeVHA==", + "license": "ISC" + }, "node_modules/has-bigints": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz", @@ -8114,6 +8239,12 @@ "node": ">=4.0" } }, + "node_modules/kdbush": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/kdbush/-/kdbush-4.0.2.tgz", + "integrity": "sha512-WbCVYJ27Sz8zi9Q7Q0xHC+05iwkm3Znipc2XTlrnJbsHMYktW4hPhXUE8Ys1engBrvffoSCqbil1JQAa7clRpA==", + "license": "ISC" + }, "node_modules/keyv": { "version": "4.5.4", "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", @@ -8544,6 +8675,57 @@ "@jridgewell/sourcemap-codec": "^1.5.5" } }, + "node_modules/mapbox-gl": { + "version": "3.18.1", + "resolved": "https://registry.npmjs.org/mapbox-gl/-/mapbox-gl-3.18.1.tgz", + "integrity": "sha512-Izc8dee2zkmb6Pn9hXFbVioPRLXJz1OFUcrvri69MhFACPU4bhLyVmhEsD9AyW1qOAP0Yvhzm60v63xdMIHPPw==", + "license": "SEE LICENSE IN LICENSE.txt", + "workspaces": [ + "src/style-spec", + "test/build/vite", + "test/build/webpack", + "test/build/typings" + ], + "dependencies": { + "@mapbox/jsonlint-lines-primitives": "^2.0.2", + "@mapbox/mapbox-gl-supported": "^3.0.0", + "@mapbox/point-geometry": "^1.1.0", + "@mapbox/tiny-sdf": "^2.0.6", + "@mapbox/unitbezier": "^0.0.1", + "@mapbox/vector-tile": "^2.0.4", + "@mapbox/whoots-js": "^3.1.0", + "@types/geojson": "^7946.0.16", + "@types/geojson-vt": "^3.2.5", + "@types/mapbox__point-geometry": "^0.1.4", + "@types/pbf": "^3.0.5", + "@types/supercluster": "^7.1.3", + "cheap-ruler": "^4.0.0", + "csscolorparser": "~1.0.3", + "earcut": "^3.0.1", + "geojson-vt": "^4.0.2", + "gl-matrix": "^3.4.4", + "grid-index": "^1.1.0", + "kdbush": "^4.0.2", + "martinez-polygon-clipping": "^0.8.1", + "murmurhash-js": "^1.0.0", + "pbf": "^4.0.1", + "potpack": "^2.0.0", + "quickselect": "^3.0.0", + "supercluster": "^8.0.1", + "tinyqueue": "^3.0.0" + } + }, + "node_modules/martinez-polygon-clipping": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/martinez-polygon-clipping/-/martinez-polygon-clipping-0.8.1.tgz", + "integrity": "sha512-9PLLMzMPI6ihHox4Ns6LpVBLpRc7sbhULybZ/wyaY8sY3ECNe2+hxm1hA2/9bEEpRrdpjoeduBuZLg2aq1cSIQ==", + "license": "MIT", + "dependencies": { + "robust-predicates": "^2.0.4", + "splaytree": "^0.1.4", + "tinyqueue": "3.0.0" + } + }, "node_modules/math-intrinsics": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", @@ -8747,6 +8929,12 @@ "url": "https://opencollective.com/express" } }, + "node_modules/murmurhash-js": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/murmurhash-js/-/murmurhash-js-1.0.0.tgz", + "integrity": "sha512-TvmkNhkv8yct0SVBSy+o8wYzXjE4Zz3PCesbfs8HiCXXdcTuocApFv11UWlNFWKYsP2okqrhb7JNlSm9InBhIw==", + "license": "MIT" + }, "node_modules/mute-stream": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-2.0.0.tgz", @@ -9374,6 +9562,18 @@ "dev": true, "license": "MIT" }, + "node_modules/pbf": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/pbf/-/pbf-4.0.1.tgz", + "integrity": "sha512-SuLdBvS42z33m8ejRbInMapQe8n0D3vN/Xd5fmWM3tufNgRQFBpaW2YVJxQZV4iPNqb0vEFvssMEo5w9c6BTIA==", + "license": "BSD-3-Clause", + "dependencies": { + "resolve-protobuf-schema": "^2.1.0" + }, + "bin": { + "pbf": "bin/pbf" + } + }, "node_modules/picocolors": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", @@ -9456,6 +9656,12 @@ "node": ">=4" } }, + "node_modules/potpack": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/potpack/-/potpack-2.1.0.tgz", + "integrity": "sha512-pcaShQc1Shq0y+E7GqJqvZj8DTthWV1KeHGdi0Z6IAin2Oi3JnLCOfwnCo84qc+HAp52wT9nK9H7FAJp5a44GQ==", + "license": "ISC" + }, "node_modules/powershell-utils": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/powershell-utils/-/powershell-utils-0.1.0.tgz", @@ -9531,6 +9737,12 @@ "react-is": "^16.13.1" } }, + "node_modules/protocol-buffers-schema": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/protocol-buffers-schema/-/protocol-buffers-schema-3.6.0.tgz", + "integrity": "sha512-TdDRD+/QNdrCGCE7v8340QyuXd4kIWIgapsE2+n/SaGiSSbomYl4TjHlvIoCWRpE7wFt02EpB35VVA2ImcBVqw==", + "license": "MIT" + }, "node_modules/proxy-addr": { "version": "2.0.7", "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", @@ -9592,6 +9804,12 @@ ], "license": "MIT" }, + "node_modules/quickselect": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/quickselect/-/quickselect-3.0.0.tgz", + "integrity": "sha512-XdjUArbK4Bm5fLLvlm5KpTFOiOThgfWWI4axAZDWg4E/0mKdZyI9tNEfds27qCi1ze/vwTR16kvmmGhRra3c2g==", + "license": "ISC" + }, "node_modules/radix-ui": { "version": "1.4.3", "resolved": "https://registry.npmjs.org/radix-ui/-/radix-ui-1.4.3.tgz", @@ -9914,6 +10132,15 @@ "url": "https://github.com/privatenumber/resolve-pkg-maps?sponsor=1" } }, + "node_modules/resolve-protobuf-schema": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/resolve-protobuf-schema/-/resolve-protobuf-schema-2.1.0.tgz", + "integrity": "sha512-kI5ffTiZWmJaS/huM8wZfEMer1eRd7oJQhDuxeCLe3t7N7mX3z94CN0xPxBQxFYQTSNz9T0i+v6inKqSdK8xrQ==", + "license": "MIT", + "dependencies": { + "protocol-buffers-schema": "^3.3.1" + } + }, "node_modules/restore-cursor": { "version": "5.1.0", "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-5.1.0.tgz", @@ -9949,6 +10176,12 @@ "node": ">=0.10.0" } }, + "node_modules/robust-predicates": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/robust-predicates/-/robust-predicates-2.0.4.tgz", + "integrity": "sha512-l4NwboJM74Ilm4VKfbAtFeGq7aEjWL+5kVFcmgFA2MrdnQWx9iE/tUGvxY5HyMI7o/WpSIUFLbC5fbeaHgSCYg==", + "license": "Unlicense" + }, "node_modules/router": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/router/-/router-2.2.0.tgz", @@ -10493,6 +10726,12 @@ "node": ">=0.10.0" } }, + "node_modules/splaytree": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/splaytree/-/splaytree-0.1.4.tgz", + "integrity": "sha512-D50hKrjZgBzqD3FT2Ek53f2dcDLAQT8SSGrzj3vidNH5ISRgceeGVJ2dQIthKOuayqFXfFjXheHNo4bbt9LhRQ==", + "license": "MIT" + }, "node_modules/stable-hash": { "version": "0.0.5", "resolved": "https://registry.npmjs.org/stable-hash/-/stable-hash-0.0.5.tgz", @@ -10775,6 +11014,15 @@ } } }, + "node_modules/supercluster": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/supercluster/-/supercluster-8.0.1.tgz", + "integrity": "sha512-IiOea5kJ9iqzD2t7QJq/cREyLHTtSmUT6gQsweojg9WH2sYJqZK9SswTu6jrscO6D1G5v5vYZ9ru/eq85lXeZQ==", + "license": "ISC", + "dependencies": { + "kdbush": "^4.0.2" + } + }, "node_modules/supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", @@ -10910,6 +11158,12 @@ "url": "https://github.com/sponsors/jonschlinkert" } }, + "node_modules/tinyqueue": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/tinyqueue/-/tinyqueue-3.0.0.tgz", + "integrity": "sha512-gRa9gwYU3ECmQYv3lslts5hxuIa90veaEcxDYuu3QGOIAEM2mOZkVHp48ANJuu1CURtRdHKUBY5Lm1tHV+sD4g==", + "license": "ISC" + }, "node_modules/tldts": { "version": "7.0.23", "resolved": "https://registry.npmjs.org/tldts/-/tldts-7.0.23.tgz", diff --git a/client/package.json b/client/package.json index 4879348..082aaa2 100644 --- a/client/package.json +++ b/client/package.json @@ -15,6 +15,7 @@ "class-variance-authority": "^0.7.1", "clsx": "^2.1.1", "lucide-react": "^0.563.0", + "mapbox-gl": "^3.18.1", "next": "16.1.6", "radix-ui": "^1.4.3", "react": "19.2.3", diff --git a/client/tsconfig.json b/client/tsconfig.json index 3a13f90..dab9b34 100644 --- a/client/tsconfig.json +++ b/client/tsconfig.json @@ -28,7 +28,8 @@ "**/*.tsx", ".next/types/**/*.ts", ".next/dev/types/**/*.ts", - "**/*.mts" + "**/*.mts", + "**/*.d.ts" ], "exclude": ["node_modules"] } diff --git a/client/types/global.d.ts b/client/types/global.d.ts new file mode 100644 index 0000000..02e31b5 --- /dev/null +++ b/client/types/global.d.ts @@ -0,0 +1 @@ +declare module "mapbox-gl/dist/mapbox-gl.css"; diff --git a/server/src/middleware/tokenVerify.ts b/server/src/middleware/tokenVerify.ts index b260a7b..1a248a6 100644 --- a/server/src/middleware/tokenVerify.ts +++ b/server/src/middleware/tokenVerify.ts @@ -5,7 +5,7 @@ export const tokenVerify = ( req: Request, res: Response, next: NextFunction -) => { +): Response | void => { try { const token = req.cookies.refreshToken; if (!token) { @@ -16,7 +16,7 @@ export const tokenVerify = ( process.env.REFRESH_TOKEN_SECRET! ) as JwtPayload; req.userId = decoded.userId; - next(); + return next(); } catch (error) { console.log("Error in tokenVerify:", error); return res.status(500).json({ errorMsg: "Internal server error", error }); From 84f3c35c0eb9ea77cd96efd073be9602a706df79 Mon Sep 17 00:00:00 2001 From: Gurudas Bhardwaj Date: Sat, 14 Feb 2026 12:41:21 +0530 Subject: [PATCH 2/2] fix: remove error logging from token verification middleware response --- client/components/home/HomeMap.tsx | 7 ++++++- server/src/middleware/tokenVerify.ts | 5 ++--- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/client/components/home/HomeMap.tsx b/client/components/home/HomeMap.tsx index df8f65d..f56bae0 100644 --- a/client/components/home/HomeMap.tsx +++ b/client/components/home/HomeMap.tsx @@ -37,12 +37,13 @@ export default function HomeMap({ className }: HomeMapProps) { if (!mapboxToken) return; mapboxgl.accessToken = mapboxToken; + let isCancelled = false; const map = new mapboxgl.Map({ container, style: "mapbox://styles/mapbox/light-v11", center: [0, 0], zoom: 2, - attributionControl: false, + attributionControl: true, }); mapRef.current = map; @@ -80,6 +81,7 @@ export default function HomeMap({ className }: HomeMapProps) { if (navigator.geolocation) { navigator.geolocation.getCurrentPosition( (position) => { + if (isCancelled) return; const { longitude, latitude } = position.coords; map.flyTo({ center: [longitude, latitude], @@ -92,6 +94,7 @@ export default function HomeMap({ className }: HomeMapProps) { .addTo(map); }, (error) => { + if (isCancelled) return; setGeoError(error.message || "Location permission was denied."); map.flyTo({ center: [0, 0], zoom: 2 }); }, @@ -99,6 +102,7 @@ export default function HomeMap({ className }: HomeMapProps) { ); } else { setTimeout(() => { + if (isCancelled) return; setGeoError("Geolocation is not supported in this browser."); }, 0); } @@ -114,6 +118,7 @@ export default function HomeMap({ className }: HomeMapProps) { } return () => { + isCancelled = true; map.off("movestart", hideRightModal); map.off("moveend", scheduleShowRightModal); map.off("load", handleMapLoad); diff --git a/server/src/middleware/tokenVerify.ts b/server/src/middleware/tokenVerify.ts index 1a248a6..32eda3a 100644 --- a/server/src/middleware/tokenVerify.ts +++ b/server/src/middleware/tokenVerify.ts @@ -17,8 +17,7 @@ export const tokenVerify = ( ) as JwtPayload; req.userId = decoded.userId; return next(); - } catch (error) { - console.log("Error in tokenVerify:", error); - return res.status(500).json({ errorMsg: "Internal server error", error }); + } catch { + return res.status(500).json({ errorMsg: "Internal server error" }); } };