P2.3: timing-safe сравнение admin bearer-токена

bearerAuthMiddleware теперь сравнивает Authorization через subtle.ConstantTimeCompare
(с предварительной проверкой длины), а не через != — устраняет timing side-channel
при подборе admin-токена.
This commit is contained in:
Repinoid
2026-10-06 18:14:27 +03:00
parent 424ec32a6a
commit 876971eea8
+6 -1
View File
@@ -6,6 +6,7 @@ package admin
import (
"context"
"crypto/subtle"
"encoding/json"
"net/http"
"os"
@@ -119,8 +120,12 @@ func (h *Handler) RegisterPublicRoutes(r *mux.Router) {
func (h *Handler) bearerAuthMiddleware(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
authHeader := r.Header.Get("Authorization")
// Timing-safe сравнение: длина префикса и сам токен проверяются отдельно,
// само сравнение значения — через subtle.ConstantTimeCompare, чтобы не
// давать timing side-channel при подборе admin-токена.
expected := "Bearer " + h.adminToken
if authHeader != expected {
if len(authHeader) != len(expected) ||
subtle.ConstantTimeCompare([]byte(authHeader), []byte(expected)) != 1 {
w.Header().Set("Content-Type", "application/json")
w.WriteHeader(http.StatusUnauthorized)
json.NewEncoder(w).Encode(map[string]string{"error": "unauthorized"})