From 9f44b8c4f2001407fed42db82d889d6c0153210d Mon Sep 17 00:00:00 2001 From: Ferdinand Urban Date: Mon, 13 Apr 2026 14:13:43 +0000 Subject: [PATCH] =?UTF-8?q?chore:=20CLAUDE.md=20compliance=20=E2=80=94=20r?= =?UTF-8?q?elative=20paths,=20CORS,=20README=20tech=20stack,=20.vch-descri?= =?UTF-8?q?ption?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Fix absolute API paths in index.html (/analyze, /move, /preview → relative) - Allow all CORS origins in server.py for reverse-proxy compatibility - Add tech stack section to README.md - Create .vch-description for VCH Showcase Co-Authored-By: Claude Sonnet 4.6 --- .vch-description | 1 + README.md | 8 ++++++++ index.html | 8 ++++---- server.py | 2 +- 4 files changed, 14 insertions(+), 5 deletions(-) create mode 100644 .vch-description diff --git a/.vch-description b/.vch-description new file mode 100644 index 0000000..8738db8 --- /dev/null +++ b/.vch-description @@ -0,0 +1 @@ +Foto-Kurator hilft Fotografen dabei, schlechte Fotos aus einem Shooting schnell auszusortieren. Die App analysiert einen Ordner automatisch auf unscharfe, über- oder unterbelichtete Fotos sowie Duplikate — optional auch mit KI. Bevor Fotos verschoben werden, zeigt die App eine Übersicht zur manuellen Kontrolle an. diff --git a/README.md b/README.md index 0a1247e..b4c149e 100644 --- a/README.md +++ b/README.md @@ -30,3 +30,11 @@ Der Browser öffnet automatisch http://localhost:8000. - **KI-Analyse** — Claude Vision API (optional, ca. 0,003 € / Foto) Aussortierte Fotos landen in `_aussortiert/` im analysierten Ordner. + +## Tech Stack + +- **Backend:** Python 3, FastAPI, Uvicorn +- **Bildanalyse:** OpenCV (Laplacian Variance), Pillow, ImageHash (pHash/MD5) +- **KI-Analyse (optional):** Anthropic Claude Vision API +- **Frontend:** Vanilla HTML/CSS/JavaScript (kein Framework) +- **Konfiguration:** python-dotenv diff --git a/index.html b/index.html index a5bb3b4..6bf4249 100644 --- a/index.html +++ b/index.html @@ -218,7 +218,7 @@ // --- Folder picker --- el("pick-btn").addEventListener("click", async () => { try { - const res = await fetch("/pick-folder"); + const res = await fetch("pick-folder"); if (res.status === 204) return; const data = await res.json(); el("folder-input").value = data.folder; @@ -250,7 +250,7 @@ let data; try { - const res = await fetch("/analyze", { + const res = await fetch("analyze", { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify(payload), @@ -285,7 +285,7 @@ // --- Review --- function makeThumb(path, name) { const img = document.createElement("img"); - img.src = "/preview?path=" + encodeURIComponent(path); + img.src = "preview?path=" + encodeURIComponent(path); img.alt = name; img.onerror = function() { this.style.display = "none"; }; img.addEventListener("click", () => openLightbox(img.src, name)); @@ -380,7 +380,7 @@ el("progress-label").textContent = "Verschiebe " + toMove.length + " Fotos..."; try { - const res = await fetch("/move", { + const res = await fetch("move", { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ paths: toMove, folder: currentFolder }), diff --git a/server.py b/server.py index 3e2f488..f9c91d4 100644 --- a/server.py +++ b/server.py @@ -19,7 +19,7 @@ app = FastAPI(title="Foto-Kurator") app.add_middleware( CORSMiddleware, - allow_origins=["http://localhost:8000"], + allow_origins=["*"], allow_methods=["GET", "POST"], allow_headers=["Content-Type"], )