Cors Wildcard in Echo Go with Hmac Signatures
Cors Wildcard in Echo Go with Hmac Signatures — how this specific combination creates or exposes the vulnerability
A CORS wildcard (Access-Control-Allow-Origin: *) combined with Hmac Signatures in an Echo Go service can unintentionally expose authenticated or sensitive endpoints to any origin. In Echo, handlers often rely on custom middleware to validate an Hmac signature (e.g., an x-api-signature header) before processing a request. If the CORS configuration permits any origin while the Hmac validation is performed only after preflight or is inconsistently applied, browsers will still allow cross-origin requests from malicious sites to reach the endpoint. The browser enforces CORS and will block frontend JavaScript from reading the response unless * is set, but a wildcard does not prevent the request from being made; it only affects whether the response is readable. An attacker’s page can issue a cross-origin request with a crafted payload; if the endpoint does not also enforce strict origin checks or referrer checks server-side, the Hmac signature might be leaked via side channels or the request may be processed without proper origin validation, leading to unauthorized actions or data exposure.
Consider an Echo route that requires Hmac authentication but sets app.Use(middleware.CORSWithConfig(middleware.CORSConfig{AllowOrigins: ["*"]})). The preflight request will succeed for any domain, and if the developer assumes the Hmac check suffices, they might overlook that the wildcard enables any site to trigger signed requests. If the Hmac is computed over parts of the request that an attacker can influence (e.g., query parameters or body), and if the server reflects or processes those values without strict referrer/origin checks, this can lead to CSRF-like scenarios against the API. Moreover, if credentials or tokens are included in headers that the client-side JavaScript tries to read, the wildcard enables a broader exposure surface. Even though Echo’s CORS middleware does not disable Hmac validation, the developer must ensure that the set of allowed origins is restricted to known consumers and that the Hmac validation includes origin binding to prevent cross-origin misuse.
Real-world parallels include findings mapped to OWASP API Top 10 A05:2023 (Security Misconfiguration) and A07:2023 (Authentication Failures). For example, a misconfigured wildcard can bypass intended access controls, similar to how improper CORS settings have been observed in CVE-2021-31184-type scenarios where missing origin validation allowed unauthorized cross-origin requests. In an Echo Go service, this becomes critical when Hmac Signatures are used to ensure integrity and authenticity; the signature does not inherently bind the request to a particular origin unless the server explicitly includes the origin or referer in the signed payload or validates the Origin header before processing.
Hmac Signatures-Specific Remediation in Echo Go — concrete code fixes
Remediation focuses on tightening CORS to a controlled allowlist and binding the origin (or referer) into the Hmac verification logic. Below are concrete, working examples for Echo Go that demonstrate a secure configuration.
1. Define a strict CORS configuration
Instead of a wildcard, specify exact origins that are permitted to access the API. This prevents arbitrary web pages from triggering signed requests.
import (
"github.com/labstack/echo/v4"
"github.com/labstack/echo/v4/middleware"
)
func main() {
e := echo.New()
e.Use(middleware.CORSWithConfig(middleware.CORSConfig{
AllowOrigins: []string{"https://app.yourcompany.com", "https://admin.yourcompany.com"},
AllowMethods: []string{echo.GET, echo.POST, echo.PUT, echo.DELETE, echo.OPTIONS},
AllowHeaders: []string{"Content-Type", "Authorization", "X-API-Signature", "X-Timestamp"},
ExposeHeaders: []string{"X-Rate-Limit-Remaining"},
MaxAge: 86400,
}))
// routes here
e.Start(":8080")
}
2. Include the Origin in Hmac computation or validate it explicitly
When computing the Hmac signature, incorporate the request’s Origin header (or Referer) so that a signature is only valid for a specific origin. This prevents a stolen signature from being reused from another domain.
import (
"crypto/hmac"
"crypto/sha256"
"encoding/hex"
"net/http"
"strings"
"time"
)
// computeHmac returns an Hmac hex digest over method, path, timestamp, body, and origin
defaultComputeHmac := func(secret, method, path, body, origin string) string {
msg := method + "\n" + path + "\n" + origin + "\n" + time.Now().Unix() + "\n" + body
key := []byte(secret)
h := hmac.New(sha256.New, key)
h.Write([]byte(msg))
return hex.EncodeToString(h.Sum(nil))
}
// VerifyHmac middleware ensures the signature matches and origin is trusted
func VerifyHmac(secret string) echo.MiddlewareFunc {
return func(next echo.HandlerFunc) echo.HandlerFunc {
return func(c echo.Context) error {
origin := c.Request().Header.Get("Origin")
if origin == "" {
return c.NoContent(http.StatusForbidden)
}
allowedOrigins := map[string]bool{
"https://app.yourcompany.com": true,
"https://admin.yourcompany.com": true,
}
if !allowedOrigins[origin] {
return c.NoContent(http.StatusForbidden)
}
expectedSig := c.Request().Header.Get("X-API-Signature")
if expectedSig == "" {
return c.NoContent(http.StatusForbidden)
}
computedSig := defaultComputeHmac(secret, c.Request().Method, c.Request().RequestURI, "", origin)
if !hmac.Equal([]byte(computedSig), []byte(expectedSig)) {
return c.NoContent(http.StatusForbidden)
}
return next(c)
}
}
}
3. Example route using both CORS and Hmac middleware
Combine the strict CORS with the Hmac verification middleware to ensure only permitted origins can produce valid signed requests.
func main() {
e := echo.New()
e.Use(middleware.CORSWithConfig(middleware.CORSConfig{
AllowOrigins: []string{"https://app.yourcompany.com"},
AllowMethods: []string{echo.POST},
AllowHeaders: []string{"Content-Type", "X-API-Signature", "X-Timestamp"},
MaxAge: 86400,
}))
e.POST("/transfer", VerifyHmac("your-32-byte-secret-key-here123456"), func(c echo.Context) error {
// handler logic
return c.JSON(http.StatusOK, map[string]string{"status": "ok"})
})
e.Start(":8080")
}
These steps ensure that an Hmac Signature is tied to a specific origin, and that CORS does not widen the attack surface to any origin. This aligns with secure defaults and reduces the risk of cross-origin abuse of signed endpoints.
Related CWEs: dataExposure
| CWE ID | Name | Severity |
|---|---|---|
| CWE-200 | Exposure of Sensitive Information | HIGH |
| CWE-209 | Error Information Disclosure | MEDIUM |
| CWE-213 | Exposure of Sensitive Information Due to Incompatible Policies | HIGH |
| CWE-215 | Insertion of Sensitive Information Into Debugging Code | MEDIUM |
| CWE-312 | Cleartext Storage of Sensitive Information | HIGH |
| CWE-359 | Exposure of Private Personal Information (PII) | HIGH |
| CWE-522 | Insufficiently Protected Credentials | CRITICAL |
| CWE-532 | Insertion of Sensitive Information into Log File | MEDIUM |
| CWE-538 | Insertion of Sensitive Information into Externally-Accessible File | HIGH |
| CWE-540 | Inclusion of Sensitive Information in Source Code | HIGH |