events: config surface for the webhook receiver
[events] listen/state_dir plus per-source secret refs (env:/file:/literal:) for redmine, discourse and gitea webhooks. Defaults: :4100, state/events, X-Redmine/X-Discourse-Webhook-Secret headers. Refs validate fail-fast; set refs must be well-formed or config load names the [events.*] section.
This commit is contained in:
@@ -200,3 +200,92 @@ func TestResolveKeyRef(t *testing.T) {
|
||||
t.Errorf("bare ref error leaks value: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestEventsDefaults(t *testing.T) {
|
||||
cfg, err := Load(writeTemp(t, `
|
||||
vertical = "demo"
|
||||
[litellm]
|
||||
base_url = "http://x:4001"
|
||||
key_ref = "literal:test-key"
|
||||
[models]
|
||||
mopac-primary = "glm-5.3"
|
||||
`))
|
||||
if err != nil {
|
||||
t.Fatalf("Load: %v", err)
|
||||
}
|
||||
if cfg.Events.Listen != ":4100" {
|
||||
t.Errorf("default listen = %q, want :4100", cfg.Events.Listen)
|
||||
}
|
||||
if cfg.Events.StateDir != "state/events" {
|
||||
t.Errorf("default state_dir = %q, want state/events", cfg.Events.StateDir)
|
||||
}
|
||||
if cfg.Events.Redmine.SecretHeader != "X-Redmine-Webhook-Secret" {
|
||||
t.Errorf("default redmine secret_header = %q", cfg.Events.Redmine.SecretHeader)
|
||||
}
|
||||
if cfg.Events.Discourse.SecretHeader != "X-Discourse-Webhook-Secret" {
|
||||
t.Errorf("default discourse secret_header = %q", cfg.Events.Discourse.SecretHeader)
|
||||
}
|
||||
}
|
||||
|
||||
func TestEventsConfigParsed(t *testing.T) {
|
||||
cfg, err := Load(writeTemp(t, `
|
||||
vertical = "demo"
|
||||
[litellm]
|
||||
base_url = "http://x:4001"
|
||||
key_ref = "literal:test-key"
|
||||
[models]
|
||||
mopac-primary = "glm-5.3"
|
||||
|
||||
[events]
|
||||
listen = "127.0.0.1:9999"
|
||||
state_dir = "st/ev"
|
||||
|
||||
[events.redmine]
|
||||
secret_ref = "env:HARNESS_RM_HOOK"
|
||||
secret_header = "X-Custom-Redmine"
|
||||
|
||||
[events.discourse]
|
||||
secret_ref = "file:/run/secrets/discourse"
|
||||
|
||||
[events.gitea]
|
||||
secret_ref = "env:HARNESS_GITEA_HOOK"
|
||||
`))
|
||||
if err != nil {
|
||||
t.Fatalf("Load: %v", err)
|
||||
}
|
||||
if cfg.Events.Listen != "127.0.0.1:9999" || cfg.Events.StateDir != "st/ev" {
|
||||
t.Errorf("events core wrong: %+v", cfg.Events)
|
||||
}
|
||||
if cfg.Events.Redmine.SecretRef != "env:HARNESS_RM_HOOK" ||
|
||||
cfg.Events.Redmine.SecretHeader != "X-Custom-Redmine" {
|
||||
t.Errorf("redmine source wrong: %+v", cfg.Events.Redmine)
|
||||
}
|
||||
if cfg.Events.Discourse.SecretRef != "file:/run/secrets/discourse" {
|
||||
t.Errorf("discourse source wrong: %+v", cfg.Events.Discourse)
|
||||
}
|
||||
if cfg.Events.Gitea.SecretRef != "env:HARNESS_GITEA_HOOK" {
|
||||
t.Errorf("gitea source wrong: %+v", cfg.Events.Gitea)
|
||||
}
|
||||
}
|
||||
|
||||
func TestEventsValidateBadRef(t *testing.T) {
|
||||
_, err := Load(writeTemp(t, `
|
||||
vertical = "demo"
|
||||
[litellm]
|
||||
base_url = "http://x:4001"
|
||||
key_ref = "literal:test-key"
|
||||
[models]
|
||||
mopac-primary = "glm-5.3"
|
||||
[events.gitea]
|
||||
secret_ref = "HARNESS_GITEA_HOOK"
|
||||
`))
|
||||
if err == nil {
|
||||
t.Fatalf("expected validation error for unprefixed secret_ref")
|
||||
}
|
||||
if !strings.Contains(err.Error(), "[events.gitea]") {
|
||||
t.Errorf("error %q does not name [events.gitea]", err)
|
||||
}
|
||||
if strings.Contains(err.Error(), "HARNESS_GITEA_HOOK") {
|
||||
t.Errorf("error leaks ref value: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user