fix(security): SSRF protection for alarm webhooks (FLAW-05)

Discord and custom webhook URLs are checked when saved and before every
call: https only, Discord URLs must point to discord.com. A guarded HTTP
client resolves hosts itself and connects only to allowed IPs; localhost,
link-local and cloud metadata are always blocked, LAN ranges (incl.
Tailscale CGNAT) and plain http only with the new admin switch.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
sandrodachandClaude Opus 5.5 committed 2026-10-29 07:37:39 +01:00
1 parent 4cdbcbd6b5
commit 62463bc6fd
8 files changed
+288 -16

No files matched your search

+14 -11
View File
@@ -278,17 +278,20 @@ type TeamMember struct {
}
type SystemSettings struct {
SharingMode string `json:"sharingMode"` // private | organizations | open
AllowRegistration bool `json:"allowRegistration"`
InstanceName string `json:"instanceName"`
SMTPHost string `json:"smtpHost"`
SMTPPort string `json:"smtpPort"`
SMTPUser string `json:"smtpUser"`
SMTPPass string `json:"smtpPass"`
SMTPFrom string `json:"smtpFrom"`
SMTPTLS bool `json:"smtpTls"`
SMTPSkipVerify bool `json:"smtpSkipVerify"` // accept self-signed certificates
SMTPConfiguredViaEnv bool `json:"smtpConfiguredViaEnv,omitempty"`
SharingMode string `json:"sharingMode"` // private | organizations | open
AllowRegistration bool `json:"allowRegistration"`
InstanceName string `json:"instanceName"`
SMTPHost string `json:"smtpHost"`
SMTPPort string `json:"smtpPort"`
SMTPUser string `json:"smtpUser"`
SMTPPass string `json:"smtpPass"`
SMTPFrom string `json:"smtpFrom"`
SMTPTLS bool `json:"smtpTls"`
SMTPSkipVerify bool `json:"smtpSkipVerify"` // accept self-signed certificates
// AllowPrivateWebhooks lets alarm webhooks reach LAN addresses (and plain http); localhost and cloud
// metadata stay blocked
AllowPrivateWebhooks bool `json:"allowPrivateWebhooks"`
SMTPConfiguredViaEnv bool `json:"smtpConfiguredViaEnv,omitempty"`
}
// UnmarshalJSON accepts smtpPort as text or number: older clients sent a number, which made the whole