package movementtest import ( "strings" "testing" movement "amadan.net/carlos/movement/internal/movement" ) // The app's own Content-Security-Policy broke its own admin sign-in, and did // it silently: the POST succeeded, the 303 to the provider was correct, and // the browser refused to follow it. form-action governs the whole redirect // chain a form submission starts, not only where the form posts. // // The only evidence was a line in somebody's console. That is why this is a // test: nothing server-side fails, so nothing else would ever catch it. func TestSigninProviderIsAllowedByFormAction(t *testing.T) { csp := movement.CSP() formAction := "" for _, d := range strings.Split(csp, ";") { if d = strings.TrimSpace(d); strings.HasPrefix(d, "form-action") { formAction = d } } if formAction == "" { t.Fatal("no form-action directive at all, which is more permissive than the default") } if !strings.Contains(formAction, "'self'") { t.Error("form-action must still allow this app's own forms") } if !strings.Contains(formAction, "https://keymail.dev") { t.Errorf("the sign-in provider is not in form-action, so the browser "+ "will refuse the redirect that starts the ceremony: %q", formAction) } } // Widening one directive must not quietly widen the rest. Everything except // form-action stays exactly as strict as the framework's default. func TestNothingElseInThePolicyWasWidened(t *testing.T) { csp := movement.CSP() for _, want := range []string{ "default-src 'self'", "style-src 'self' 'unsafe-inline'", "img-src 'self' data:", "frame-ancestors 'none'", "base-uri 'self'", } { if !strings.Contains(csp, want) { t.Errorf("the policy no longer carries %q", want) } } if strings.Contains(csp, "script-src") { t.Error("scripts have been given their own directive; they should stay " + "under default-src 'self'") } if strings.Contains(csp, "unsafe-eval") || strings.Contains(csp, "*") { t.Error("the policy contains a wildcard or unsafe-eval") } }