Add highlight marking and AI API

This commit is contained in:
human insan
2026-08-27 22:43:30 +01:00
parent 6c0d06de77
commit 5a0e83fb4c
3 changed files with 165 additions and 2 deletions
+52
View File
@@ -59,6 +59,8 @@ class PlayerHandler(BaseHTTPRequestHandler):
return self.send_recordings(request.query)
if request.path == "/api/encode/status":
return self.send_json(self.server.encode_status)
if request.path == "/api/highlights":
return self.send_json(self.server.highlights)
if request.path == "/video":
return self.send_video(request.query)
self.send_error(404)
@@ -68,8 +70,41 @@ class PlayerHandler(BaseHTTPRequestHandler):
if not self.server.encode_status["running"]:
threading.Thread(target=run_encoding, args=(self.server,), daemon=True).start()
return self.send_json(self.server.encode_status)
if urlparse(self.path).path == "/api/highlights":
try:
length = int(self.headers.get("Content-Length", "0"))
item = json.loads(self.rfile.read(length))
date = str(item["date"])
start = float(item["start"])
end = float(item["end"])
if not DATE_RE.fullmatch(date) or not (0 <= start < end <= 86400):
raise ValueError
highlight = {
"id": max((entry["id"] for entry in self.server.highlights), default=0) + 1,
"date": date,
"start": start,
"end": end,
"label": str(item.get("label", "Untitled highlight"))[:120],
}
except (KeyError, TypeError, ValueError, json.JSONDecodeError):
return self.send_error(400, "Invalid highlight")
self.server.highlights.append(highlight)
save_highlights(self.server.highlights_path, self.server.highlights)
return self.send_json(highlight)
self.send_error(404)
def do_DELETE(self):
request = urlparse(self.path)
if request.path != "/api/highlights":
return self.send_error(404)
try:
highlight_id = int(parse_qs(request.query).get("id", [""])[0])
except ValueError:
return self.send_error(400, "Invalid highlight id")
self.server.highlights[:] = [item for item in self.server.highlights if item["id"] != highlight_id]
save_highlights(self.server.highlights_path, self.server.highlights)
self.send_json({"ok": True})
def send_json(self, payload):
data = json.dumps(payload).encode()
self.send_response(200)
@@ -213,6 +248,8 @@ def main():
server.recordings = recordings
server.source_root = args.source.expanduser().resolve()
server.output_root = args.root.expanduser().resolve()
server.highlights_path = server.output_root / "highlights.json"
server.highlights = load_highlights(server.highlights_path)
server.encode_status = {"running": False, "total": 0, "completed": 0, "skipped": 0, "failed": 0}
count = sum(map(len, recordings.values()))
print(f"Indexed {count} recordings across {len(recordings)} days")
@@ -263,5 +300,20 @@ def run_encoding(server):
status["running"] = False
def load_highlights(path):
try:
data = json.loads(path.read_text())
return data if isinstance(data, list) else []
except (FileNotFoundError, json.JSONDecodeError, OSError):
return []
def save_highlights(path, highlights):
path.parent.mkdir(parents=True, exist_ok=True)
temporary = path.with_suffix(".tmp")
temporary.write_text(json.dumps(highlights, indent=2) + "\n")
temporary.replace(path)
if __name__ == "__main__":
main()