From 2bc47e81a39c64d9712627cb9fe154932fdd14bd Mon Sep 17 00:00:00 2001 From: Jason Song Date: Mon, 30 Sep 2024 10:28:09 +0800 Subject: [PATCH] Ensure `GetCSRF` doesn't return an empty token (#32130) Since page templates keep changing, some pages that contained forms with CSRF token no longer have them. It leads to some calls of `GetCSRF` returning an empty string, which fails the tests. Like https://github.com/go-gitea/gitea/blob/3269b04d61ffe6a7ce462cd05ee150e4491124e8/tests/integration/attachment_test.go#L62-L63 The test did try to get the CSRF token and provided it, but it was empty. (cherry picked from commit 13283873e9d523d5a5557f55d64f702c1a9f76ec) Conflicts: tests/integration/integration_test.go trivial context conflict --- tests/integration/attachment_test.go | 9 +++------ tests/integration/integration_test.go | 7 ++++++- tests/integration/org_test.go | 4 ---- 3 files changed, 9 insertions(+), 11 deletions(-) diff --git a/tests/integration/attachment_test.go b/tests/integration/attachment_test.go index 7cbc2545d5..7bd3e680f7 100644 --- a/tests/integration/attachment_test.go +++ b/tests/integration/attachment_test.go @@ -30,7 +30,7 @@ func generateImg() bytes.Buffer { return buff } -func createAttachment(t *testing.T, session *TestSession, repoURL, filename string, buff bytes.Buffer, expectedStatus int) string { +func createAttachment(t *testing.T, session *TestSession, csrf, repoURL, filename string, buff bytes.Buffer, expectedStatus int) string { body := &bytes.Buffer{} // Setup multi-part @@ -42,8 +42,6 @@ func createAttachment(t *testing.T, session *TestSession, repoURL, filename stri err = writer.Close() require.NoError(t, err) - csrf := GetCSRF(t, session, repoURL) - req := NewRequestWithBody(t, "POST", repoURL+"/issues/attachments", body) req.Header.Add("X-Csrf-Token", csrf) req.Header.Add("Content-Type", writer.FormDataContentType()) @@ -60,15 +58,14 @@ func createAttachment(t *testing.T, session *TestSession, repoURL, filename stri func TestCreateAnonymousAttachment(t *testing.T) { defer tests.PrepareTestEnv(t)() session := emptyTestSession(t) - // this test is not right because it just doesn't pass the CSRF validation - createAttachment(t, session, "user2/repo1", "image.png", generateImg(), http.StatusBadRequest) + createAttachment(t, session, GetCSRF(t, session, "/user/login"), "user2/repo1", "image.png", generateImg(), http.StatusSeeOther) } func TestCreateIssueAttachment(t *testing.T) { defer tests.PrepareTestEnv(t)() const repoURL = "user2/repo1" session := loginUser(t, "user2") - uuid := createAttachment(t, session, repoURL, "image.png", generateImg(), http.StatusOK) + uuid := createAttachment(t, session, GetCSRF(t, session, repoURL), repoURL, "image.png", generateImg(), http.StatusOK) req := NewRequest(t, "GET", repoURL+"/issues/new") resp := session.MakeRequest(t, req, http.StatusOK) diff --git a/tests/integration/integration_test.go b/tests/integration/integration_test.go index e43200f4cb..606df2ed1c 100644 --- a/tests/integration/integration_test.go +++ b/tests/integration/integration_test.go @@ -663,12 +663,17 @@ func VerifyJSONSchema(t testing.TB, resp *httptest.ResponseRecorder, schemaFile require.NoError(t, schemaValidation) } +// GetCSRF returns CSRF token from body +// If it fails, it means the CSRF token is not found in the response body returned by the url with the given session. +// In this case, you should find a better url to get it. func GetCSRF(t testing.TB, session *TestSession, urlStr string) string { t.Helper() req := NewRequest(t, "GET", urlStr) resp := session.MakeRequest(t, req, http.StatusOK) doc := NewHTMLParser(t, resp.Body) - return doc.GetCSRF() + csrf := doc.GetCSRF() + require.NotEmpty(t, csrf) + return csrf } func GetHTMLTitle(t testing.TB, session *TestSession, urlStr string) string { diff --git a/tests/integration/org_test.go b/tests/integration/org_test.go index a1e448be8a..f907b75c72 100644 --- a/tests/integration/org_test.go +++ b/tests/integration/org_test.go @@ -204,9 +204,7 @@ func TestTeamSearch(t *testing.T) { var results TeamSearchResults session := loginUser(t, user.Name) - csrf := GetCSRF(t, session, "/"+org.Name) req := NewRequestf(t, "GET", "/org/%s/teams/-/search?q=%s", org.Name, "_team") - req.Header.Add("X-Csrf-Token", csrf) resp := session.MakeRequest(t, req, http.StatusOK) DecodeJSON(t, resp, &results) assert.NotEmpty(t, results.Data) @@ -217,9 +215,7 @@ func TestTeamSearch(t *testing.T) { // no access if not organization member user5 := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 5}) session = loginUser(t, user5.Name) - csrf = GetCSRF(t, session, "/"+org.Name) req = NewRequestf(t, "GET", "/org/%s/teams/-/search?q=%s", org.Name, "team") - req.Header.Add("X-Csrf-Token", csrf) session.MakeRequest(t, req, http.StatusNotFound) }