- controllers/trigger_controller.go: полная реализация, HTTP->Ingress+Service, Cron->CronJob
- internal/config: добавлены IngressHost, APIToken
- internal/api/router.go: gorilla/mux роутер /v1/namespaces/{ns}/...
- internal/api/handler/: functions, triggers, invocations, base handler с slog
- internal/api/middleware/: auth (Bearer token) + logging (slog)
- main.go: запуск operator + HTTP сервера параллельно
- go.sum: добавлен gorilla/mux v1.8.1
41 lines
1.4 KiB
Go
41 lines
1.4 KiB
Go
// Изменено: 2026-03-07
|
||
// Auth middleware — проверяет Bearer токен из заголовка Authorization.
|
||
// В v1: сравниваем с SLESS_API_TOKEN из конфига.
|
||
// В prod: вызываем auth-сервис nubes.ru (TODO v2).
|
||
|
||
package middleware
|
||
|
||
import (
|
||
"log/slog"
|
||
"net/http"
|
||
"strings"
|
||
)
|
||
|
||
// Auth возвращает middleware которое требует заголовок:
|
||
//
|
||
// Authorization: Bearer <token>
|
||
//
|
||
// и сравнивает его с allowedToken.
|
||
func Auth(allowedToken string, log *slog.Logger, next http.Handler) http.Handler {
|
||
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||
header := r.Header.Get("Authorization")
|
||
if header == "" {
|
||
log.Warn("auth: missing authorization header", "remote", r.RemoteAddr, "path", r.URL.Path)
|
||
http.Error(w, `{"error":"authorization required"}`, http.StatusUnauthorized)
|
||
return
|
||
}
|
||
parts := strings.SplitN(header, " ", 2)
|
||
if len(parts) != 2 || !strings.EqualFold(parts[0], "bearer") {
|
||
log.Warn("auth: invalid authorization format", "remote", r.RemoteAddr)
|
||
http.Error(w, `{"error":"invalid authorization format, use Bearer <token>"}`, http.StatusUnauthorized)
|
||
return
|
||
}
|
||
if parts[1] != allowedToken {
|
||
log.Warn("auth: invalid token", "remote", r.RemoteAddr, "path", r.URL.Path)
|
||
http.Error(w, `{"error":"invalid token"}`, http.StatusForbidden)
|
||
return
|
||
}
|
||
next.ServeHTTP(w, r)
|
||
})
|
||
}
|