# POSTUP: Vývoj aplikace "Živé vzpomínky na dovolenou"

Tento dokument slouží jako detailní technická specifikace a architektonický návod pro vývoj multiplatformní aplikace (pro Linux a Windows). Aplikace bude automaticky vytvářet interaktivní deníky a mapy z dovolených na základě nahraných fotografií a textových zápisků.

Všechny kroky jsou navrženy tak, aby generování výsledného webu probíhalo **lokálně, offline a bez nutnosti platit za AI API (tokeny)**.

---

## Obsah
1. [Volba programovacího jazyka a frameworku](#1-volba-programovacího-jazyka-a-frameworku)
2. [Import a zpracování fotografií (Místní disk, Google Fotky, Rajče)](#2-import-a-zpracování-fotografií)
3. [Získání geolokace a propojení s Wikipedií (bez AI)](#3-získání-geolokace-a-propojení-s-wikipedií)
4. [Struktura deníku a párování dat](#4-struktura-deníku-a-párování-dat)
5. [Generování webové stránky a zabezpečení heslem](#5-generování-webové-stránky-a-zabezpečení-heslem)
6. [Možnosti bezplatného sdílení na internetu](#6-možnosti-bezplatného-sdílení-na-internetu)

---

## 1. Volba programovacího jazyka a frameworku

Pro vývoj multiplatformní aplikace (Linux a Windows) s bohatým vizuálním rozhraním a prací s mapami (Leaflet.js) přicházejí v úvahu tři hlavní přístupy.

### Srovnání technologií

| Technologie | Velikost aplikace | Výkon | Složitost distribuce | Vývoj UI / Mapy | Doporučení |
| :--- | :---: | :---: | :---: | :--- | :--- |
| **Tauri** (Rust backend + HTML/JS frontend) | ~15 MB | Vynikající | Střední (vyžaduje instalaci Rustu při sestavení) | Webové technologie (HTML/CSS/JS), nativní integrace Leaflet.js | **Doporučeno (nativní aplikace)** |
| **Node.js + Local Server** (Vite/React/Svelte + Express) | 0 MB (běží v prohlížeči) | Skvělý | Nízká (vyžaduje Node.js na PC, nebo zabalený přes pkg) | Standardní webové rozhraní v libovolném prohlížeči | **Doporučeno (nejjednodušší na údržbu)** |
| **Python** (Flask/FastAPI backend + PyWebView) | ~60 MB | Střední | Vyšší (PyInstaller občas generuje falešné detekce virů) | Kombinace Pythonu a HTML, dobré knihovny na EXIF | Dobrá alternativa pro čisté Python vývojáře |
| **Flutter** (Dart) | ~30 MB | Vynikající | Nízká (kompiluje přímo do nativního kódu) | Skvělé nativní UI, ale integrace mapy Leaflet.js (web) je složitější | Vhodné, pokud je kladen důraz na mobilní platformy |

### Doporučená architektura: Tauri
Tauri je moderní framework, který používá **Rust** pro systémové operace (čtení EXIF dat z disku, zápis souborů, lokální server) a libovolný **webový frontend (např. HTML/CSS/JS nebo React)** pro uživatelské rozhraní.
- **Proč?** Výsledný vygenerovaný web dovolené je postaven na HTML/CSS/JS (Leaflet.js). Použitím Tauri můžeme totožný mapový kód a komponenty použít jak uvnitř samotné desktopové aplikace (v editoru), tak ve vygenerovaném výsledku pro přátele.

---

## 2. Import a zpracování fotografií

Uživatel musí mít možnost snadno nasměrovat aplikaci na zdroj fotografií.

### Varianta A: Lokální složka v počítači (Nejlepší řešení)
Aplikace otevře nativní systémový dialog pro výběr složky.
1. Backend (Rust v Tauri nebo Node.js fs) projde složku a najde všechny soubory s příponami `.jpg`, `.jpeg`, `.png`.
2. Provede optimalizaci snímků (tzv. **downscaling**):
   - Původní fotky z fotoaparátů mají často 10 MB+ a obrovské rozlišení, což je pro web nepoužitelné.
   - Aplikace automaticky vytvoří složku `fotky/` a v ní vygeneruje:
     - **Webové verze:** max. šířka/výška 1600px (komprese JPEG, cca 300–500 KB) pro zobrazení v galerii.
     - **Miniatury (thumbnails):** max. šířka/výška 300px (cca 30 KB) pro rychlé náhledy v mapě.
   - V Node.js k tomu použijeme knihovnu `sharp`, v Rustu knihovnu `image`.

### Varianta B: Propojení s Google Fotkami (Google Photos API)
Chcete-li stahovat fotky přímo z Google účtu uživatele, je potřeba implementovat OAuth 2.0 autorizaci:
1. **Registrace v Google Cloud Console:** Je nutné vytvořit projekt a povolit **Google Photos Library API**. Získáte `Client ID` a `Client Secret`.
2. **OAuth 2.0 Flow v aplikaci:**
   - Aplikace spustí lokální HTTP server na pozadí (např. na `http://localhost:5000/callback`).
   - Otevře systémový prohlížeč s autorizační URL Google:
     ```text
     https://accounts.google.com/o/oauth2/v2/auth?
     client_id=CLIENT_ID&
     redirect_uri=http://localhost:5000/callback&
     response_type=code&
     scope=https://www.googleapis.com/auth/photoslibrary.readonly
     ```
   - Uživatel schválí přístup. Google přesměruje prohlížeč na lokální server s parametrem `code`.
   - Backend aplikace zachytí kód, vymění ho za `access_token` a `refresh_token`.
3. **Načtení fotek:**
   - Aplikace pošle dotaz na získání médií podle data nebo alb:
     ```bash
     GET https://photoslibrary.googleapis.com/v1/mediaItems
     Authorization: Bearer ACCESS_TOKEN
     ```
   - Google API vrátí metadata včetně odkazu na obrázek (`baseUrl`). Aplikace stáhne vybrané fotky lokálně (přidáním parametrů na konec URL, např. `=w2048-h2048` získáte fotku v plném rozlišení pro uložení).

### Varianta C: Stahování z Rajče.idnes.cz (Rajče API)
Rajče nepoužívá OAuth, ale XML-RPC protokol. Komunikace probíhá zasíláním XML dotazů metodou `POST` na adresu `https://www.rajce.idnes.cz/live/api.php`.

1. **Přihlášení uživatele (`members.login`):**
   ```xml
   <?xml version="1.0" encoding="utf-8"?>
   <methodCall>
     <methodName>members.login</methodName>
     <params>
       <param><value><string>UZIVATELSKE_JMENO</string></value></param>
       <param><value><string>HESLO</string></value></param>
     </params>
   </methodCall>
   ```
   Odpověď obsahuje `sessionToken`, který se používá pro další požadavky.
2. **Získání seznamu alb (`albums.getList`):**
   Aplikace získá seznam alb uživatele a nechá ho vybrat správné album.
3. **Získání fotek z alba (`photos.getList`):**
   Získá seznam URL adres jednotlivých fotografií v albu, které pak aplikace stáhne a zpracuje.

---

## 3. Získání geolokace a propojení s Wikipedií

Klíčová vlastnost: Automatická detekce míst a obohacení textu **zcela bez poplatků za AI**.

```mermaid
graph TD
    A[Fotografie s GPS EXIF] --> B(Čtení EXIF dat)
    B --> C[GPS Souřadnice & Datum/Čas]
    C --> D[Nominatim API - Reverse Geocoding]
    C --> E[Wikipedia Geosearch API]
    D --> F[Název místa / Město]
    E --> G[Wikipedia Články v okolí]
    F & G --> H[Návrh itineráře pro uživatele]
```

### Krok 1: Čtení EXIF dat z fotografií
Většina chytrých telefonů ukládá do hlavičky fotky GPS souřadnice a čas pořízení.
- V JavaScriptu (frontend/Node.js) k tomu použijeme knihovnu `exif-reader` nebo `exif-parser`.
- V Rustu (Tauri) knihovnu `kamadak-exif`.
- **Výstupem** pro každou fotografii je:
  - Datum a čas: `2026-07-01 13:43:24`
  - Zeměpisná šířka (Latitude): `56.0197`
  - Zeměpisná délka (Longitude): `-3.7556`

### Krok 2: Převod souřadnic na názvy míst (Reverse Geocoding)
Chceme zjistit, že souřadnice `56.0197, -3.7556` odpovídají místu "The Kelpies".
Použijeme **Nominatim API (OpenStreetMap)**, které je zdarma.
- **Volání API:**
  ```text
  GET https://nominatim.openstreetmap.org/reverse?format=jsonv2&lat=56.0197&lon=-3.7556&zoom=18
  ```
- **Důležité pravidlo:** Nominatim vyžaduje v hlavičce smysluplný `User-Agent` (název vaší aplikace a e-mail) a povoluje maximálně **1 požadavek za sekundu**. Aplikace proto musí dotazy odesílat s pauzami (rate-limiting).

### Krok 3: Obohacení z Wikipedie přes Geosearch API
Wikipedia nabízí skvělé API, které umí vyhledat články v okolí zadaných souřadnic. Nepotřebujeme k tomu žádný API klíč.

1. **Vyhledání článků v okolí (např. v okruhu 5 km):**
   ```text
   GET https://cs.wikipedia.org/w/api.php?action=query&list=geosearch&gscoord=56.0197|-3.7556&gsradius=5000&gslimit=5&format=json
   ```
   Tento dotaz vrátí seznam nejbližších článků. Například:
   ```json
   {
     "query": {
       "geosearch": [
         { "pageid": 12345, "title": "The Kelpies", "dist": 12.5, "lat": 56.0197, "lon": -3.7556 }
       ]
     }
   }
   ```
2. **Stažení úvodního odstavce článku (Abstract):**
   Jakmile máme název článku (např. "The Kelpies"), stáhneme jeho stručný text v češtině (nebo v jazyce Wikipedie podle lokace):
   ```text
   GET https://cs.wikipedia.org/w/api.php?action=query&prop=extracts&exintro&explaintext&titles=The%20Kelpies&format=json
   ```
   V odpovědi získáte čistý text (např. *"The Kelpies jsou 30 metrů vysoké koňské hlavy tvořící monumentální sochařské dílo..."*), který aplikace automaticky navrhne jako popisek k danému místu.

---

## 4. Struktura deníku a párování dat

Uživatel může mít buď předem napsaný textový deník (např. v Markdownu či TXT), nebo si ho klikáním vytváří přímo v aplikaci.

### Algoritmus automatického párování:
1. **Analýza časů:** Aplikace seřadí všechny fotky chronologicky podle času pořízení (z EXIFu).
2. **Určení dnů:** Podle časových mezer (např. noc) rozdělí fotky do jednotlivých dnů (Den 1, Den 2, Den 3...).
3. **Detekce zastávek:** Pokud se u skupiny fotek výrazně změní souřadnice (např. o více než 5 km od předchozí), aplikace na základě geolokace a Wikipedie vytvoří novou "zastávku" (bod na mapě) v daném dni.
4. **Párování deníku:** Uživatel nahraje svůj deník. Aplikace se pokusí podle klíčových slov (např. "1. den", "Pondělí", data) spárovat text s konkrétním dnem.
5. **Manuální korekce:** V aplikaci se zobrazí přehledný časový editor, kde uživatel může body přesouvat, upravovat texty stažené z Wikipedie, měnit barvy špendlíků a mazat nepovedené fotky.

---

## 5. Generování webové stránky a zabezpečení heslem

Po dokončení úprav aplikace vygeneruje složku s kompletním webem (Static Site).

### Struktura vygenerované složky:
```text
[Název_Dovolené_Web]/
├── index.html            # Hlavní struktura stránky
├── style.css             # Responzivní design a barevné schéma
├── script.js             # Logika mapy Leaflet.js a interaktivity
├── data.js               # Data o dnech, bodech a trasách
└── fotky/
    ├── thumb_PXL_01.jpg  # Miniatury pro rychlé načítání
    └── web_PXL_01.jpg    # Velké fotky pro galerii
```

### Barevné schéma (Layout) přes CSS proměnné
Uživatel volí schéma v úvodu. Stylopis `style.css` bude využívat moderní CSS proměnné, které aplikace při generování zapíše přímo do hlavičky HTML nebo do konfigurace:

```css
/* Tmavé schéma */
:root {
  --panel: 380px;
  --bg: #12181f;
  --paper: #1a232d;
  --ink: #f0f4f8;
  --muted: #8b9bb4;
  --border: #2d3b4e;
}

/* Světlé schéma */
:root {
  --panel: 380px;
  --bg: #f5f7fa;
  --paper: #ffffff;
  --ink: #1e293b;
  --muted: #64748b;
  --border: #e2e8f0;
}
```

### Zabezpečení stránek heslem (offline šifrování)
Jelikož generujeme statický web bez databáze, klasické přihlašování na serveru není možné. Bezpečnost vyřešíme **symetrickým šifrováním dat na straně klienta**:

1. **Při generování (v aplikaci):**
   - Všechna citlivá data (souřadnice, texty deníku, cesty k fotkám) uložená v `data.js` se převedou na JSON řetězec.
   - Tento řetězec se zašifruje pomocí algoritmu **AES-256** se zadaným heslem (např. pomocí knihovny `CryptoJS` v Node.js/Rustu).
   - Do souboru `data.js` se uloží pouze zašifrovaný text:
     ```javascript
     const encryptedData = "U2FsdGVkX19zSGVsbG8gd29ybGQgZnJvbSBjcnlwdG9qcy...";
     ```
2. **Při otevření webu (v prohlížeči přátel):**
   - Stránka se otevře, ale místo mapy zobrazí pouze čisté pozadí se vstupním polem pro heslo.
   - Uživatel zadá heslo.
   - JavaScript na stránce se pokusí dešifrovat řetězec:
     ```javascript
     try {
       const bytes = CryptoJS.AES.decrypt(encryptedData, enteredPassword);
       const decryptedData = JSON.parse(bytes.toString(CryptoJS.enc.Utf8));
       // Inicializace mapy a zobrazení obsahu
       initMap(decryptedData);
     } catch (e) {
       alert("Nesprávné heslo!");
     }
     ```
   - **Výhoda:** Bez znalosti hesla je nemožné data z kódu dešifrovat. Fotky ve složce `fotky/` sice fyzicky existují, ale jejich názvy mohou být náhodně hashované (např. `sha256` hash souboru), takže je nikdo bez dešifrovaného seznamu nedokáže spárovat ani snadno prohlížet.

---

## 6. Možnosti bezplatného sdílení na internetu

Jelikož vygenerovaný web je čistě statický (HTML, CSS, JS, obrázky), lze pro jeho publikaci využít nejlepší bezplatné služby na trhu.

### 1. Cloudflare Pages (Nejlepší volba)
- **Proč:** Zcela zdarma, neomezený přenos dat (bandwidth), extrémně rychlé servery po celém světě.
- **Jak sdílet manuálně:** Uživatel se přihlásí na web Cloudflare, přetáhne vygenerovanou složku myší do okna prohlížeče (Drag & Drop) a web okamžitě běží na bezplatné subdoméně `neco.pages.dev`.
- **Integrace v aplikaci:** Cloudflare nabízí API. Aplikace by mohla po přihlášení uživatele nahrát soubory automaticky na jedno kliknutí.

### 2. Netlify
- **Proč:** Velmi populární, jednoduché rozhraní. Bezplatný tarif nabízí 100 GB přenosu dat za měsíc.
- **Automatické nahrávání z aplikace:** Netlify má velmi jednoduché API pro nahrávání ZIP souborů.
  - Aplikace zabalí vygenerovaný adresář do souboru `web.zip`.
  - Pošle `POST` požadavek na Netlify API s autorizačním tokenem uživatele:
    ```bash
    POST https://api.netlify.com/api/v1/sites/YOUR_SITE_ID/deploys
    Content-Type: application/zip
    Binary Payload: [web.zip]
    ```
  - Web je během několika sekund živý na internetu.

### 3. GitHub Pages
- **Proč:** Výborné pro programátory, plně verzované.
- **Nevýhoda:** Vyžaduje vytvoření GitHub repozitáře (který by pro soukromí musel být privátní, což u Pages zdarma vyžaduje placený GitHub účet nebo složitější nastavení). Pro běžné uživatele je to příliš komplikované.

---

## Shrnutí kroků pro následnou implementaci
Při samotném kódování aplikace se budeme držet tohoto postupu:
1. **Frontend v React/Vite:** Vytvoření moderního tmavého/světlého UI pro správu projektů a průvodce (Wizard).
2. **Tauri Rust backend:** Zprovoznění dialogu pro výběr složky, optimalizace obrázků (`image` crate) a EXIF parseru (`kamadak-exif`).
3. **Implementace API klientů:** Propojení s Nominatim, Wikipedia a případně Google Photos.
4. **Modul pro generování a šifrování:** Sestavení šablony webu a zašifrování dat přes CryptoJS (AES-256).
5. **Modul pro nahrávání:** Integrace Netlify API / Cloudflare Pages pro snadné sdílení.
