package api import ( "embed" "io/fs" "net/http" "github.com/go-chi/chi/v5" "github.com/johanj/clawvault/lib" ) // NewRouter creates the main router with all routes registered. func NewRouter(db *lib.DB, cfg *lib.Config, webFS embed.FS) *chi.Mux { r := chi.NewRouter() h := NewHandlers(db, cfg) // Global middleware r.Use(LoggingMiddleware) r.Use(CORSMiddleware) r.Use(SecurityHeadersMiddleware) r.Use(RateLimitMiddleware(120)) // 120 req/min per IP // Health check (unauthenticated) r.Get("/health", h.Health) // Setup endpoint (creates initial session) r.Post("/api/auth/setup", h.Setup) // API routes (authenticated) r.Route("/api", func(r chi.Router) { r.Use(AuthMiddleware(db)) // Entries CRUD r.Get("/entries", h.ListEntries) r.Post("/entries", h.CreateEntry) r.Get("/entries/{id}", h.GetEntry) r.Put("/entries/{id}", h.UpdateEntry) r.Delete("/entries/{id}", h.DeleteEntry) // Search r.Get("/search", h.SearchEntries) // Password generator r.Get("/generate", h.GeneratePassword) // Import r.Post("/import", h.ImportEntries) r.Post("/import/confirm", h.ImportConfirm) // Audit log r.Get("/audit", h.GetAuditLog) // Extension API r.Get("/ext/totp/{id}", h.GetTOTP) r.Get("/ext/match", h.MatchURL) r.Post("/ext/map", h.MapFields) }) // MCP endpoint (authenticated) r.With(AuthMiddleware(db)).Post("/mcp", h.MCPHandler) // Embedded web UI webRoot, err := fs.Sub(webFS, "web") if err == nil { fileServer := http.FileServer(http.FS(webRoot)) r.Handle("/*", fileServer) } return r }