forked from tangled.org/core
this repo has no description
1package knotserver 2 3import ( 4 "crypto/hmac" 5 "crypto/sha256" 6 "encoding/hex" 7 "log" 8 "net/http" 9 "time" 10) 11 12func (h *Handle) VerifySignature(next http.Handler) http.Handler { 13 if h.c.Server.Dev { 14 return next 15 } 16 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { 17 signature := r.Header.Get("X-Signature") 18 log.Println(signature) 19 if signature == "" || !h.verifyHMAC(signature, r) { 20 writeError(w, "signature verification failed", http.StatusForbidden) 21 return 22 } 23 next.ServeHTTP(w, r) 24 }) 25} 26 27func (h *Handle) verifyHMAC(signature string, r *http.Request) bool { 28 secret := h.c.Server.Secret 29 timestamp := r.Header.Get("X-Timestamp") 30 if timestamp == "" { 31 return false 32 } 33 34 // Verify that the timestamp is not older than a minute 35 reqTime, err := time.Parse(time.RFC3339, timestamp) 36 if err != nil { 37 return false 38 } 39 if time.Since(reqTime) > time.Minute { 40 return false 41 } 42 43 message := r.Method + r.URL.Path + timestamp 44 45 mac := hmac.New(sha256.New, []byte(secret)) 46 mac.Write([]byte(message)) 47 expectedMAC := mac.Sum(nil) 48 49 signatureBytes, err := hex.DecodeString(signature) 50 if err != nil { 51 return false 52 } 53 54 return hmac.Equal(signatureBytes, expectedMAC) 55}