Added panic mode protections to make the server more secure
This commit is contained in:
@@ -1,4 +1,3 @@
|
||||
// cmd/shard/main.go
|
||||
package main
|
||||
|
||||
import (
|
||||
@@ -26,8 +25,9 @@ func getenvBool(key string, def bool) bool {
|
||||
}
|
||||
|
||||
func staticHeaders(next http.Handler) http.Handler {
|
||||
onion := os.Getenv("GC_ONION_LOCATION") // optional: e.g., http://xxxxxxxx.onion/
|
||||
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||
// Security headers
|
||||
// Security headers + strict CSP (no inline) + COEP
|
||||
w.Header().Set("Referrer-Policy", "no-referrer")
|
||||
w.Header().Set("Cross-Origin-Opener-Policy", "same-origin")
|
||||
w.Header().Set("Cross-Origin-Resource-Policy", "same-site")
|
||||
@@ -35,6 +35,19 @@ func staticHeaders(next http.Handler) http.Handler {
|
||||
w.Header().Set("X-Frame-Options", "DENY")
|
||||
w.Header().Set("X-Content-Type-Options", "nosniff")
|
||||
w.Header().Set("Strict-Transport-Security", "max-age=15552000; includeSubDomains; preload")
|
||||
w.Header().Set("Cross-Origin-Embedder-Policy", "require-corp")
|
||||
// Allow only self + HTTPS for fetch/SSE; no inline styles/scripts
|
||||
w.Header().Set("Content-Security-Policy",
|
||||
"default-src 'self'; "+
|
||||
"script-src 'self'; "+
|
||||
"style-src 'self'; "+
|
||||
"img-src 'self' data:; "+
|
||||
"connect-src 'self' https:; "+
|
||||
"frame-ancestors 'none'; object-src 'none'; base-uri 'none'; form-action 'self'; "+
|
||||
"require-trusted-types-for 'script'")
|
||||
if onion != "" {
|
||||
w.Header().Set("Onion-Location", onion)
|
||||
}
|
||||
|
||||
// Basic CORS for static (GET only effectively)
|
||||
w.Header().Set("Access-Control-Allow-Origin", "*")
|
||||
@@ -72,12 +85,17 @@ func main() {
|
||||
dataDir = "/var/lib/greencoast"
|
||||
}
|
||||
|
||||
coarseTS := getenvBool("GC_COARSE_TS", false)
|
||||
coarseTS := getenvBool("GC_COARSE_TS", true) // safer default (less precise metadata)
|
||||
zeroTrust := getenvBool("GC_ZERO_TRUST", true)
|
||||
encRequired := getenvBool("GC_ENCRYPTION_REQUIRED", true) // operator-blind by default
|
||||
requirePOP := getenvBool("GC_REQUIRE_POP", true) // for logging only; API defaults to true internally
|
||||
requirePOP := getenvBool("GC_REQUIRE_POP", true) // logged only here
|
||||
|
||||
signingSecretHex := os.Getenv("GC_SIGNING_SECRET_HEX")
|
||||
if len(signingSecretHex) < 64 {
|
||||
log.Printf("WARN: GC_SIGNING_SECRET_HEX length=%d (need >=64 hex chars)", len(signingSecretHex))
|
||||
} else {
|
||||
log.Printf("GC_SIGNING_SECRET_HEX OK (len=%d)", len(signingSecretHex))
|
||||
}
|
||||
|
||||
discID := os.Getenv("GC_DISCORD_CLIENT_ID")
|
||||
discSecret := os.Getenv("GC_DISCORD_CLIENT_SECRET")
|
||||
@@ -90,13 +108,17 @@ func main() {
|
||||
}
|
||||
ix := index.New()
|
||||
|
||||
// Reindex on boot from whatever files exist on disk
|
||||
// Reindex on boot from existing files (coarse time if enabled)
|
||||
if err := store.Walk(func(hash string, size int64, mod time.Time) error {
|
||||
when := mod.UTC()
|
||||
if coarseTS {
|
||||
when = when.Truncate(time.Minute)
|
||||
}
|
||||
return ix.Put(index.Entry{
|
||||
Hash: hash,
|
||||
Bytes: size,
|
||||
StoredAt: mod.UTC().Format(time.RFC3339Nano),
|
||||
Private: false, // unknown here; safe default
|
||||
StoredAt: when.Format(time.RFC3339Nano),
|
||||
Private: false, // unknown here
|
||||
})
|
||||
}); err != nil {
|
||||
log.Printf("reindex on boot: %v", err)
|
||||
|
Reference in New Issue
Block a user