| 1073 | } |
| 1074 | |
| 1075 | func TestCSRFRequired(t *testing.T) { |
| 1076 | t.Parallel() |
| 1077 | |
| 1078 | baseURL := startHTTP(t, apiCfg) |
| 1079 | |
| 1080 | cli := &http.Client{ |
| 1081 | Timeout: time.Minute, |
| 1082 | } |
| 1083 | |
| 1084 | // Getting the base URL (i.e. "/") should succeed. |
| 1085 | |
| 1086 | resp, err := cli.Get(baseURL) |
| 1087 | if err != nil { |
| 1088 | t.Fatal("Unexpected error from getting base URL:", err) |
| 1089 | } |
| 1090 | resp.Body.Close() |
| 1091 | if resp.StatusCode != http.StatusOK { |
| 1092 | t.Fatal("Getting base URL should succeed, not", resp.Status) |
| 1093 | } |
| 1094 | |
| 1095 | // Find the returned CSRF token for future use |
| 1096 | |
| 1097 | var csrfTokenName, csrfTokenValue string |
| 1098 | for _, cookie := range resp.Cookies() { |
| 1099 | if strings.HasPrefix(cookie.Name, "CSRF-Token") { |
| 1100 | csrfTokenName = cookie.Name |
| 1101 | csrfTokenValue = cookie.Value |
| 1102 | break |
| 1103 | } |
| 1104 | } |
| 1105 | |
| 1106 | if csrfTokenValue == "" { |
| 1107 | t.Fatal("Failed to initialize CSRF test: no CSRF cookie returned from " + baseURL) |
| 1108 | } |
| 1109 | |
| 1110 | t.Run("/rest without a token should fail", func(t *testing.T) { |
| 1111 | t.Parallel() |
| 1112 | resp, err := cli.Get(baseURL + "/rest/system/config") |
| 1113 | if err != nil { |
| 1114 | t.Fatal("Unexpected error from getting /rest/system/config:", err) |
| 1115 | } |
| 1116 | resp.Body.Close() |
| 1117 | if resp.StatusCode != http.StatusForbidden { |
| 1118 | t.Fatal("Getting /rest/system/config without CSRF token should fail, not", resp.Status) |
| 1119 | } |
| 1120 | }) |
| 1121 | |
| 1122 | t.Run("/rest with a token should succeed", func(t *testing.T) { |
| 1123 | t.Parallel() |
| 1124 | req, _ := http.NewRequest("GET", baseURL+"/rest/system/config", nil) |
| 1125 | req.Header.Set("X-"+csrfTokenName, csrfTokenValue) |
| 1126 | resp, err := cli.Do(req) |
| 1127 | if err != nil { |
| 1128 | t.Fatal("Unexpected error from getting /rest/system/config:", err) |
| 1129 | } |
| 1130 | resp.Body.Close() |
| 1131 | if resp.StatusCode != http.StatusOK { |
| 1132 | t.Fatal("Getting /rest/system/config with CSRF token should succeed, not", resp.Status) |