255e8dcf71
Frontend C++ ImGui (main.cpp + 4 paneles) + backend Go (HTTP + SQLite + fsnotify + SSE). Reusa parse/scan/watch funcs del registry (issue 0130a).
81 lines
1.7 KiB
Go
81 lines
1.7 KiB
Go
package main
|
|
|
|
import (
|
|
"context"
|
|
"log"
|
|
"strings"
|
|
|
|
"fn-registry/functions/infra"
|
|
)
|
|
|
|
func (s *Server) watchLoop(ctx context.Context, root, kind string) {
|
|
ch, err := infra.WatchDirFsnotify(ctx, root)
|
|
if err != nil {
|
|
log.Printf("watcher %s: %v", root, err)
|
|
return
|
|
}
|
|
for ev := range ch {
|
|
if !strings.HasSuffix(ev.Path, ".md") {
|
|
continue
|
|
}
|
|
s.handleFsEvent(kind, ev)
|
|
}
|
|
}
|
|
|
|
func (s *Server) handleFsEvent(kind string, ev infra.FsEvent) {
|
|
switch kind {
|
|
case "issue":
|
|
s.handleIssueEvent(ev)
|
|
case "flow":
|
|
s.handleFlowEvent(ev)
|
|
}
|
|
}
|
|
|
|
func (s *Server) handleIssueEvent(ev infra.FsEvent) {
|
|
id := issueIDFromPath(ev.Path, s.issuesDir)
|
|
if id == "" {
|
|
return
|
|
}
|
|
if ev.Op == "remove" || ev.Op == "rename" {
|
|
s.deleteIssue(id)
|
|
s.hub.broadcast(SSEEvent{Type: "removed", ID: id, Path: ev.Path})
|
|
return
|
|
}
|
|
iss, _, err := infra.ParseIssueMd(ev.Path)
|
|
if err != nil {
|
|
log.Printf("parse %s: %v", ev.Path, err)
|
|
return
|
|
}
|
|
if err := s.upsertIssueRow(iss); err != nil {
|
|
log.Printf("upsert %s: %v", iss.ID, err)
|
|
return
|
|
}
|
|
s.hub.broadcast(SSEEvent{Type: "updated", ID: iss.ID, Path: ev.Path})
|
|
}
|
|
|
|
func (s *Server) handleFlowEvent(ev infra.FsEvent) {
|
|
id := issueIDFromPath(ev.Path, s.flowsDir)
|
|
if id == "" {
|
|
return
|
|
}
|
|
if ev.Op == "remove" || ev.Op == "rename" {
|
|
s.deleteFlow(id)
|
|
s.hub.broadcast(SSEEvent{Type: "flow_removed", ID: id, Path: ev.Path})
|
|
return
|
|
}
|
|
flows, err := infra.ScanFlowsDir(s.flowsDir)
|
|
if err != nil {
|
|
log.Printf("scan flows: %v", err)
|
|
return
|
|
}
|
|
for _, fl := range flows {
|
|
if fl.ID == id {
|
|
if err := s.upsertFlowRow(fl); err != nil {
|
|
log.Printf("upsert flow %s: %v", id, err)
|
|
}
|
|
s.hub.broadcast(SSEEvent{Type: "flow_updated", ID: id, Path: ev.Path})
|
|
return
|
|
}
|
|
}
|
|
}
|