docs: reorganize project documentation
This commit is contained in:
207
README.md
207
README.md
@@ -1,32 +1,33 @@
|
||||
# wtr.
|
||||
|
||||
**Pogoda z danych IMGW. Prosto. Pięknie. Aktualnie.**
|
||||
`wtr.` to mobilna PWA pogodowa dla Polski oparta o publiczne dane IMGW oraz jawnie oznaczoną prognozę modelową łączącą IMGW ALARO z Open-Meteo.
|
||||
|
||||
`wtr.` to nowoczesna pogodowa PWA dla Polski oparta o publiczne dane IMGW i jawnie oznaczoną prognozę modelową łączącą IMGW ALARO z Open-Meteo. Aplikacja prezentuje bieżącą analizę pogody IMGW Hybrid, odczyty synoptyczne, prognozę godzinową i 7-dniową, regułowy brief dnia, stacje hydrologiczne oraz ostrzeżenia w spokojnym, mobilnym interfejsie z czytelną typografią, opaque surfaces i subtelnymi animacjami. Dashboard pokazuje rozszerzony desktopowy podgląd godzin z podsumowaniem najbliższej doby, a także wykresy temperatury i opadu dla bieżącego dnia. Każdy dzień prognozy można także otworzyć w animowanym widoku szczegółowym z przebiegiem godzinowym oraz wykresami.
|
||||
Aplikacja pokazuje bieżącą analizę IMGW Hybrid, pomiary synoptyczne, prognozę godzinową i 7-dniową, ostrzeżenia meteorologiczne i hydrologiczne, dane hydro oraz deterministyczne briefy pogodowe bez użycia zewnętrznego modelu AI.
|
||||
|
||||
Interfejs jest dostępny po polsku i angielsku. Wybrany język jest zapisywany lokalnie w przeglądarce. Oryginalne treści ostrzeżeń oraz nazwy stacji pochodzą bezpośrednio z API IMGW i nie są automatycznie tłumaczone.
|
||||
## Najważniejsze funkcje
|
||||
|
||||
Wyszukiwarka na stronie głównej obsługuje miejscowości w całej Polsce. Nazwa miejscowości jest rozpoznawana przez Open-Meteo Geocoding API oparte o GeoNames. Bieżące warunki są analizowane lokalnie przez IMGW Hybrid, a najbliższa rzeczywista stacja IMGW jest pokazywana jako kontekst i fallback. Interfejs jawnie pokazuje nazwę tej stacji oraz przybliżoną odległość.
|
||||
|
||||
Użytkownik może opcjonalnie udostępnić położenie GPS. Pozycja jest zaokrąglana do trzech miejsc po przecinku, czyli około 100 metrów, a nazwa miejscowości jest ustalana przez Nominatim / OpenStreetMap. Po zgodzie aplikacja wybiera lokalizację, najbliższą stację IMGW i prognozę. Geolocation API wymaga bezpiecznego kontekstu HTTPS. Wyjątkiem jest `localhost`; wejście z iPhone przez lokalny adres typu `http://192.168.x.x:3000` nie uruchomi systemowego pytania Safari.
|
||||
|
||||
Widok ostrzeżeń priorytetyzuje komunikaty dla obszaru wynikającego z miejscowości lub stacji wybranej w pogodzie. Dla ostrzeżeń meteorologicznych, gdy aplikacja rozpozna powiat wybranej miejscowości, filtrowanie odbywa się po kodzie TERYT powiatu; w przeciwnym razie pozostaje fallback wojewódzki. W każdej grupie ostrzeżenia meteorologiczne, np. o burzach lub silnym wietrze, są wyświetlane przed hydrologicznymi. Ostrzeżenia meteorologiczne IMGW przypisuje do regionów na podstawie kodów TERYT, a hydrologiczne na podstawie jawnych pól województwa z API. Pozostałe aktywne komunikaty są wyświetlane niżej. Dashboard pokazuje dodatkowo kompaktowy panel aktywnych i nadchodzących ostrzeżeń meteo dla wybranego obszaru. Panel automatycznie ukrywa komunikaty po upływie ich czasu obowiązywania i nie obejmuje ostrzeżeń hydrologicznych.
|
||||
|
||||
Publiczne endpointy ostrzeżeń IMGW potrafią zwrócić HTTP `404` z treścią `{"status":false,"message":"No products were found"}`. Aplikacja traktuje taki wariant jako poprawną pustą listę ostrzeżeń, a nie awarię źródła danych.
|
||||
- Bieżące warunki z lokalnej analizy IMGW Hybrid, z opisanym fallbackiem do stacji synoptycznej.
|
||||
- Prognoza modelowa 7 dni: IMGW ALARO dla dostępnych godzin oraz Open-Meteo jako uzupełnienie i fallback.
|
||||
- Wyszukiwanie miejscowości w Polsce oraz opcjonalny wybór lokalizacji GPS.
|
||||
- Ostrzeżenia IMGW z filtrowaniem meteo po powiecie TERYT, gdy lokalizacja go dostarcza.
|
||||
- Powiadomienia Web Push o nowych ostrzeżeniach, porannym briefie dnia i wieczornym briefie na jutro.
|
||||
- Widoki dashboardu, prognozy szczegółowej dnia, ostrzeżeń, hydro, stacji i ustawień.
|
||||
- PWA z manifestem, własnym service workerem i podstawowym fallbackiem offline.
|
||||
- Interfejs po polsku i angielsku.
|
||||
|
||||
## Stack
|
||||
|
||||
- Next.js z App Router i TypeScript
|
||||
- Tailwind CSS oraz komponenty w stylu shadcn/ui
|
||||
- Next.js App Router, React, TypeScript
|
||||
- Tailwind CSS
|
||||
- TanStack Query
|
||||
- Zustand
|
||||
- Framer Motion
|
||||
- Recharts
|
||||
- Lucide React
|
||||
- TanStack Query
|
||||
- Zustand z trwałym stanem `localStorage`
|
||||
- web-push do wysyłki Web Push
|
||||
- własny service worker, manifest i offline fallback
|
||||
- `web-push`
|
||||
- własny service worker i manifest PWA
|
||||
|
||||
## Uruchomienie
|
||||
## Szybki Start
|
||||
|
||||
Wymagany jest Node.js 20.9 lub nowszy.
|
||||
|
||||
@@ -37,131 +38,11 @@ npm run dev
|
||||
|
||||
Aplikacja będzie dostępna pod adresem `http://localhost:3000`.
|
||||
|
||||
Sprawdzenie jakości i build produkcyjny:
|
||||
## Konfiguracja
|
||||
|
||||
```bash
|
||||
npm run lint
|
||||
npm run build
|
||||
npm run start
|
||||
```
|
||||
Do podstawowego uruchomienia aplikacji pogodowej nie są potrzebne klucze API. Publiczne dane IMGW, Open-Meteo i Nominatim są pobierane przez route handlery Next.js.
|
||||
|
||||
Worker powiadomień uruchamiany obok aplikacji:
|
||||
|
||||
```bash
|
||||
npm run start
|
||||
npm run notifications:worker
|
||||
```
|
||||
|
||||
Worker musi mieć dostęp do działającej aplikacji Next.js. Domyślnie odpytuje `http://127.0.0.1:3000`; jeśli aplikacja działa pod innym adresem albo portem, ustaw `WTR_APP_URL`. Skrypt workera sam wczytuje `.env` i `.env.local`, a zmienne podane bezpośrednio w shellu mają pierwszeństwo.
|
||||
|
||||
## Źródła danych
|
||||
|
||||
Bieżące pomiary i komunikaty pochodzą z rzeczywistych publicznych danych IMGW:
|
||||
|
||||
- bieżąca analiza IMGW Hybrid używana przez oficjalny portal: `https://meteo.imgw.pl/api/v1/forecast/fcapi`
|
||||
- prognoza godzinowa IMGW ALARO używana przez oficjalny portal: `https://meteo.imgw.pl/api/v1/forecast/fcapi?m=alaro`
|
||||
- dane synoptyczne: `https://danepubliczne.imgw.pl/api/data/synop`
|
||||
- pojedyncza stacja synoptyczna: `https://danepubliczne.imgw.pl/api/data/synop/id/{id}`
|
||||
- dane hydrologiczne: `https://danepubliczne.imgw.pl/api/data/hydro/`
|
||||
- ostrzeżenia meteorologiczne: `https://danepubliczne.imgw.pl/api/data/warningsmeteo`
|
||||
- ostrzeżenia hydrologiczne: `https://danepubliczne.imgw.pl/api/data/warningshydro`
|
||||
- dane meteorologiczne: `https://danepubliczne.imgw.pl/api/data/meteo/`
|
||||
- lista produktów: `https://danepubliczne.imgw.pl/api/data/product`
|
||||
|
||||
Prognoza modelowa łączy dwa źródła. IMGW ALARO dostarcza dostępne godziny prognozy, zwykle około 72 godzin od cyklu modelu. Open-Meteo Forecast API (`https://api.open-meteo.com/v1/forecast`) dostarcza prawdopodobieństwo opadu dla całego zakresu, uzupełnia dalszy horyzont do pełnych 7 dni i pozostaje fallbackiem, jeśli ALARO chwilowo nie odpowiada. Interfejs pokazuje oba źródła i ich role.
|
||||
|
||||
Do wyszukiwania nazw miejscowości używany jest endpoint `https://geocoding-api.open-meteo.com/v1/search`. Przed wdrożeniem komercyjnym należy sprawdzić aktualne warunki korzystania z Open-Meteo lub zastąpić usługę własnym dostawcą.
|
||||
|
||||
Opcjonalny reverse geocoding dla GPS korzysta z publicznego endpointu Nominatim: `https://nominatim.openstreetmap.org/reverse`. Wywołanie następuje wyłącznie po zgodzie użytkownika. Interfejs pokazuje atrybucję OpenStreetMap. Przed wdrożeniem o większym ruchu należy sprawdzić aktualną politykę użycia publicznej instancji Nominatim lub zastąpić ją własną usługą.
|
||||
|
||||
Przeglądarka pobiera dane przez route handlery Next.js. Proxy IMGW w `app/api/imgw/[...path]/route.ts` pozwala ujednolicić cache, błędy API i bezpiecznie obsłużyć hydro bez mixed content. Bieżącą analizę pogody obsługuje `app/api/imgw-current/route.ts`, prognozę `app/api/forecast/route.ts`, a reverse geocoding GPS `app/api/locations/reverse/route.ts`.
|
||||
|
||||
## Wewnętrzne endpointy API
|
||||
|
||||
| Metoda | Endpoint | Przeznaczenie |
|
||||
| --- | --- | --- |
|
||||
| `GET` | `/api/forecast?latitude={lat}&longitude={lon}` | Zwraca 7-dniową prognozę modelową dla współrzędnych, łącząc IMGW ALARO z fallbackiem Open-Meteo. Odpowiedź ma cache `s-maxage=900`. |
|
||||
| `GET` | `/api/imgw-current?latitude={lat}&longitude={lon}` | Pobiera lokalną analizę IMGW Hybrid z oficjalnego portalu IMGW dla współrzędnych. Cache jest krótki, `s-maxage=120`. |
|
||||
| `GET` | `/api/imgw/{path}` | Proxy allowlistowanych publicznych endpointów IMGW `danepubliczne.imgw.pl`, m.in. `synop`, `synop/id/{id}`, `hydro`, `meteo`, `warningsmeteo`, `warningshydro` i `product`. Empty `warningsmeteo`/`warningshydro` z komunikatem `No products were found` jest normalizowane do pustej listy. |
|
||||
| `GET` | `/api/locations/search?name={query}` | Wyszukuje miejscowości w Polsce przez Open-Meteo Geocoding i zwraca znormalizowane lokalizacje dla wyszukiwarki. Cache `s-maxage=86400`. |
|
||||
| `GET` | `/api/locations/reverse?latitude={lat}&longitude={lon}` | Ustala nazwę miejsca dla pozycji GPS przez Nominatim / OpenStreetMap po zgodzie użytkownika. Cache `s-maxage=86400`. |
|
||||
| `GET` | `/api/notifications/vapid-key` | Zwraca publiczny klucz VAPID i informację, czy Web Push jest skonfigurowany. Używane przez `/settings`. |
|
||||
| `POST` | `/api/notifications/subscriptions` | Zapisuje lub aktualizuje subskrypcję Web Push dla urządzenia, wraz z preferencjami ostrzeżeń, briefu o 7:00, briefu o 18:00, lokalizacją i powiatem TERYT. Wymaga skonfigurowanych kluczy VAPID. |
|
||||
| `DELETE` | `/api/notifications/subscriptions` | Usuwa subskrypcję Web Push na podstawie endpointu subskrypcji. |
|
||||
| `GET` | `/api/notifications/check` | Endpoint harmonogramu sprawdzający nowe ostrzeżenia meteorologiczne IMGW i wysyłający Web Push do pasujących subskrypcji. W produkcji wymaga `Authorization: Bearer <NOTIFICATIONS_CRON_SECRET>` albo `x-cron-secret`. |
|
||||
| `GET` | `/api/notifications/daily-brief` | Endpoint harmonogramu wysyłający raz dziennie poranny brief o 7:00 dla subskrypcji z włączoną opcją i zapisaną lokalizacją. W produkcji wymaga sekretu crona. |
|
||||
| `GET` | `/api/notifications/tomorrow-brief` | Endpoint harmonogramu wysyłający wieczorny brief o 18:00 z prognozą na jutro, w tym sygnałami burz z modelu. W produkcji wymaga sekretu crona. |
|
||||
| `POST` | `/api/notifications/test` | Wysyła testowe powiadomienie Web Push na konkretny endpoint subskrypcji. Używane wyłącznie z `/settings`. |
|
||||
|
||||
## Ograniczenia API
|
||||
|
||||
Dashboard korzysta z publicznego endpointu IMGW Hybrid używanego przez oficjalny portal `meteo.imgw.pl`. Bieżące warunki są wybierane z pierwszego pełnego rekordu analizy Hybrid dla współrzędnych miejscowości, preferując rekord 10-minutowy i wymagając realnych wartości liczbowych. Jeśli pełny rekord 10-minutowy jest wyraźnie starszy niż pełny rekord godzinowy z tej samej odpowiedzi, aplikacja wybiera świeższy rekord godzinowy zamiast nadpisywać aktualny fallback starymi danymi. Dzięki temu `null` z rekordów MERGE nie jest traktowany jako pełny pomiar. Interfejs może dodatkowo pokazać rzeczywisty opad z ostatnich 10 minut, oddzielnie opisuje lokalną analizę Hybrid oraz najbliższą stację pomiarową IMGW. Pokrycie Hybrid może być częściowe: jeśli IMGW publikuje lokalny opad MERGE bez pełnego rekordu parametrów, hero zachowuje lokalny opad, a temperaturę, wiatr, wilgotność i ciśnienie jawnie uzupełnia fallbackiem ze stacji. Jeśli usługa Hybrid nie odpowiada, hero zachowuje cały pomiar `synop` jako oznaczony fallback. Gdy fallback pochodzi ze stacji oddalonej od miejscowości o co najmniej 30 km, interfejs ostrzega o możliwej różnicy warunków lokalnych. Endpoint Hybrid jest częścią publicznego frontendu IMGW, ale nie jest opisany w stabilnej dokumentacji `danepubliczne.imgw.pl`, więc integrację należy monitorować przy zmianach portalu.
|
||||
|
||||
Publiczny endpoint synoptyczny IMGW udostępnia najnowszy pomiar, a nie historię odczytów. Prognoza modelowa jest wyraźnie oddzielona od pomiarów IMGW oraz bieżącej analizy Hybrid. Parametry ALARO mają pierwszeństwo w godzinach objętych tym modelem, natomiast prawdopodobieństwo opadu i dalszy horyzont pochodzą z Open-Meteo, ponieważ ALARO nie publikuje prawdopodobieństwa opadu i nie obejmuje pełnych 7 dni. `wtr.` nie generuje fikcyjnych prognoz. Widok stacji prezentuje aktualne parametry i jawnie opisany snapshot pomiarowy. Brakujące wartości są oznaczane jako `Brak danych`.
|
||||
|
||||
Brief dnia jest deterministycznym podsumowaniem danych, a nie wywołaniem modelu AI. Moduł `lib/weather-brief.ts` analizuje najbliższe 24 godziny prognozy modelowej oraz aktywne i nadchodzące ostrzeżenia meteo IMGW dla obszaru użytkownika. Ten sam moduł przygotowuje osobny brief na jutro z pełnego jutrzejszego dnia prognozy, wykrywając m.in. burze po kodach pogodowych modelu także wtedy, gdy IMGW nie opublikowało jeszcze oficjalnego ostrzeżenia. Na tej podstawie tworzy dłuższy opis na dashboard oraz krótsze wersje do powiadomień. Dzięki temu funkcja nie wymaga klucza OpenAI API i działa przewidywalnie na małym serwerze, np. Raspberry Pi.
|
||||
|
||||
Pole `suma_opadu` z endpointu synoptycznego jest prezentowane jako akumulowana suma opadu. Nie służy do wnioskowania, że w danej chwili pada, ani do uruchamiania animacji deszczu.
|
||||
|
||||
Czas aktualizacji parametrów hydrologicznych może się różnić. Interfejs pokazuje czas pomiaru, aby starsze odczyty nie wyglądały na bieżące.
|
||||
|
||||
## Stany pogody i efekty wizualne
|
||||
|
||||
Prognoza godzinowa i dzienna rozpoznaje następujące stany warunków pogodowych:
|
||||
|
||||
| Stan | Opis w interfejsie |
|
||||
| --- | --- |
|
||||
| `clear` | Bezchmurnie |
|
||||
| `partlyCloudy` | Częściowe zachmurzenie |
|
||||
| `cloudy` | Pochmurno |
|
||||
| `fog` | Mgła |
|
||||
| `drizzle` | Mżawka |
|
||||
| `rain` | Opady deszczu |
|
||||
| `snow` | Opady śniegu |
|
||||
| `thunderstorm` | Burza |
|
||||
| `unknown` | Brak opisu |
|
||||
|
||||
Bieżąca analiza IMGW Hybrid rozpoznaje bezpośrednio opad deszczu, śnieg i burzę. Gdy żadne z tych zjawisk nie występuje, hero może pokazać pomocniczy opis: `Silny wiatr`, `Wilgotne warunki` albo `Spokojne warunki`.
|
||||
|
||||
Hero aktualnej pogody korzysta z uproszczonego nastroju wizualnego do wyboru ikony, tekstu i małego akcentu stanu. Nie steruje już pełnoekranowym gradientem.
|
||||
|
||||
| Mood | Obecna reguła |
|
||||
| --- | --- |
|
||||
| `night` | godzina przed `06:00` lub od `21:00` |
|
||||
| `wind` | wiatr od `8 m/s` |
|
||||
| `cold` | temperatura do `3°C` |
|
||||
| `cloudy` | wilgotność od `80%` |
|
||||
| `warm` | temperatura od `20°C` |
|
||||
| `mild` | pozostałe przypadki |
|
||||
|
||||
Warstwa efektów wizualnych jest ograniczona do subtelnych efektów informacyjnych: kropli przy lokalnym opadzie oraz błysku przy burzy. Mood hero jest obecnie heurystyką opartą o porę dnia, temperaturę, wilgotność i wiatr. Nie jest jeszcze pełną klasyfikacją sterowaną kodem warunków IMGW Hybrid.
|
||||
|
||||
## Struktura projektu
|
||||
|
||||
```text
|
||||
app/ routing, layout, proxy danych, offline fallback
|
||||
components/forecast/ prognoza godzinowa i dzienna IMGW ALARO + Open-Meteo
|
||||
components/charts/ wykresy odczytów i szczegółów prognozy
|
||||
components/dashboard dashboard aplikacji
|
||||
components/weather/ hero, stacje, metryki i szczegóły
|
||||
components/warnings/ alerty meteo i hydro
|
||||
components/hydro/ lista stacji hydrologicznych
|
||||
components/settings/ ustawienia języka, motywu i preferencji alertów
|
||||
components/ui/ bazowe komponenty interfejsu
|
||||
components/states/ loading, empty i error states
|
||||
hooks/ zapytania TanStack Query
|
||||
lib/ API, normalizacja, helpery i stan
|
||||
types/ typy danych IMGW
|
||||
public/ manifest, ikony i service worker
|
||||
```
|
||||
|
||||
## PWA i offline
|
||||
|
||||
Manifest znajduje się w `public/manifest.json`, a service worker w `public/sw.js`. Rejestracja service workera działa w buildzie produkcyjnym. Powłoka aplikacji ma podstawowy offline fallback. Odpowiedzi API mogą być dostępne z pamięci urządzenia przy braku sieci, ale UI nadal prezentuje czas pomiaru i status świeżości.
|
||||
|
||||
Widok `/settings` zawiera konfigurację powiadomień o ostrzeżeniach meteorologicznych IMGW: wybór województwa, zgodę Web Push, zapis subskrypcji urządzenia, poranny brief, wieczorny brief na jutro i wysłanie powiadomienia testowego. Na iOS/iPadOS powiadomienia webowe wymagają dodania PWA do ekranu początkowego i uruchomienia aplikacji z ikony. Na Androidzie i desktopie wystarczy HTTPS oraz przeglądarka obsługująca Web Push; instalacja PWA nie jest wymagana. Endpoint `/api/notifications/check` sprawdza `warningsmeteo` i wysyła tylko nowe ostrzeżenia meteo do pasujących subskrypcji, `/api/notifications/daily-brief` wysyła raz dziennie krótkie podsumowanie dla subskrypcji z zapisaną lokalizacją, `/api/notifications/tomorrow-brief` wysyła wieczorem prognozę na kolejny dzień, a `/api/notifications/test` wysyła test na wskazany endpoint subskrypcji. Endpointy harmonogramu nie uruchamiają się same: na self-hostingu uruchom `npm run notifications:worker` obok `npm run start`, albo użyj zewnętrznego crona. Obecny magazyn subskrypcji działa w pamięci procesu, więc produkcja wymaga podmiany `lib/push-store.ts` na trwałą bazę lub KV.
|
||||
|
||||
Do wysyłki Web Push wymagane są zmienne środowiskowe:
|
||||
Powiadomienia Web Push wymagają zmiennych środowiskowych:
|
||||
|
||||
```bash
|
||||
WEB_PUSH_VAPID_PUBLIC_KEY=
|
||||
@@ -174,17 +55,45 @@ NOTIFICATIONS_MORNING_BRIEF_TIME=07:00
|
||||
NOTIFICATIONS_TOMORROW_BRIEF_TIME=18:00
|
||||
```
|
||||
|
||||
Klucze VAPID można wygenerować poleceniem `npx web-push generate-vapid-keys`. Worker `npm run notifications:worker` wczytuje `.env` i `.env.local`, domyślnie odpytuje `http://127.0.0.1:3000`, więc `npm run start` musi działać równolegle na tym samym hoście albo `WTR_APP_URL` musi wskazywać właściwy adres aplikacji. Worker sprawdza ostrzeżenia co 5 minut, wysyła poranny brief po 07:00 i wieczorny brief na jutro po 18:00 czasu polskiego. Jeśli używasz zewnętrznego crona zamiast workera, cron ostrzeżeń powinien wywoływać `GET /api/notifications/check` z nagłówkiem `Authorization: Bearer <NOTIFICATIONS_CRON_SECRET>` albo `x-cron-secret`. Drugi cron, ustawiony na około 07:00 czasu polskiego, powinien wywoływać `GET /api/notifications/daily-brief`, a trzeci cron około 18:00 `GET /api/notifications/tomorrow-brief` z tym samym nagłówkiem.
|
||||
Przykład znajduje się w [.env.example](.env.example).
|
||||
|
||||
## Wdrożenie na Vercel
|
||||
## Komendy
|
||||
|
||||
1. Umieść repozytorium w serwisie Git.
|
||||
2. Importuj projekt do Vercel jako aplikację Next.js.
|
||||
3. Nie dodawaj kluczy API: publiczne endpointy IMGW ich nie wymagają.
|
||||
4. Wdróż standardowym poleceniem builda `npm run build`.
|
||||
| Komenda | Opis |
|
||||
| --- | --- |
|
||||
| `npm run dev` | Uruchamia serwer deweloperski Next.js. |
|
||||
| `npm run lint` | Uruchamia ESLint. |
|
||||
| `npm run build` | Buduje aplikację produkcyjnie i uruchamia kontrolę TypeScript wykonywaną przez Next.js. |
|
||||
| `npm run start` | Uruchamia zbudowaną aplikację. |
|
||||
| `npm run notifications:worker` | Uruchamia self-hostowany worker powiadomień. Wymaga działającej aplikacji Next.js. |
|
||||
|
||||
Proxy IMGW działa jako route handler Next.js i jest zgodne z hostingiem Vercel.
|
||||
Repozytorium nie ma obecnie osobnego skryptu testów, type-check ani formattera.
|
||||
|
||||
## Bezpieczeństwo zależności
|
||||
## Struktura Projektu
|
||||
|
||||
Projekt używa stabilnego Next.js `16.2.6`. `npm audit --omit=dev` raportuje obecnie umiarkowane zgłoszenie `GHSA-qx2v-qp2m-jg93` dla PostCSS `8.4.31` bundlowanego bezpośrednio przez najnowszy Next.js. Główna konfiguracja projektu korzysta z poprawionego PostCSS `8.5.x`, ale wewnętrznej kopii Next.js nie należy ręcznie podmieniać. Po publikacji poprawki upstream należy zaktualizować Next.js i ponownie uruchomić audyt.
|
||||
```text
|
||||
app/ routing, layout, route handlery i strony
|
||||
components/ komponenty widoków, UI, stanów, prognozy, hydro i ostrzeżeń
|
||||
hooks/ hooki TanStack Query
|
||||
lib/ fetchery, normalizacja danych, Web Push, i18n, store i helpery
|
||||
types/ typy danych IMGW, prognozy, lokalizacji i powiadomień
|
||||
public/ manifest, service worker i ikony PWA
|
||||
scripts/ worker powiadomień dla self-hostingu
|
||||
docs/ szczegółowa dokumentacja techniczna
|
||||
```
|
||||
|
||||
## Dokumentacja
|
||||
|
||||
- [Architektura i przepływ danych](docs/architecture.md)
|
||||
- [Wewnętrzne endpointy API](docs/api.md)
|
||||
- [Źródła danych i cache](docs/data-sources.md)
|
||||
- [Logika pogody i fallbacki](docs/weather-logic.md)
|
||||
- [Powiadomienia Web Push](docs/notifications.md)
|
||||
- [Wdrożenie i uruchamianie](docs/deployment.md)
|
||||
|
||||
## Status i Ograniczenia
|
||||
|
||||
- `lib/push-store.ts` przechowuje subskrypcje Web Push w pamięci procesu. Produkcyjne wdrożenie wymaga trwałego magazynu, np. bazy danych albo KV.
|
||||
- Endpoint IMGW Hybrid używany przez dashboard pochodzi z publicznego frontendu `meteo.imgw.pl`, a nie ze stabilnie opisanej dokumentacji `danepubliczne.imgw.pl`.
|
||||
- Publiczne API IMGW potrafi zwrócić `404` z komunikatem `No products were found` dla pustych list ostrzeżeń; aplikacja traktuje to jako brak ostrzeżeń.
|
||||
- Prognoza jest prognozą modelową, nie pomiarem IMGW. Bieżące pomiary i prognozy są w UI rozdzielane.
|
||||
|
||||
Reference in New Issue
Block a user