package user import ( "bytes" "encoding/json" "io/ioutil" "net/http/httptest" "testing" "git.samuelpua.com/telboon/ktm-train-bot/backend/internal/common" ) func TestRegistration(t *testing.T) { db := common.TestDBInit() defer common.DestroyTestingDB(db) db.AutoMigrate(&User{}) db.AutoMigrate(&Profile{}) db.AutoMigrate(&Session{}) t.Setenv("ALLOW_REGISTRATION", "true") router := UserRoutes(db) testCases := []struct { username string password string statusCode int }{ { username: "testusername", password: "testpassword", statusCode: 201, }, { username: "", password: "testpassword", statusCode: 422, }, { username: "testusername", password: "", statusCode: 422, }, { username: "t", password: "testpassword", statusCode: 422, }, { username: "testusername", password: "test", statusCode: 422, }, } for _, currentTestCase := range testCases { rr := httptest.NewRecorder() currBody := struct { Username string `json:"username"` Password string `json:"password"` }{ Username: currentTestCase.username, Password: currentTestCase.password, } reqBody, err := json.Marshal(currBody) if err != nil { t.Errorf("Error creating a new request body: %v", err) } reqBodyReader := bytes.NewReader(reqBody) req := httptest.NewRequest("POST", "/register", reqBodyReader) router.ServeHTTP(rr, req) // Check results if rr.Code != currentTestCase.statusCode { t.Errorf("Expected status code %d, got %d", currentTestCase.statusCode, rr.Code) } } } func TestLogin(t *testing.T) { db := common.TestDBInit() defer common.DestroyTestingDB(db) db.AutoMigrate(&User{}) db.AutoMigrate(&Profile{}) db.AutoMigrate(&Session{}) t.Setenv("ALLOW_REGISTRATION", "true") t.Setenv("COOKIE_STRING", "supercustomcookie") router := UserRoutes(db) testCases := []struct { username string password string statusCode int }{ { username: "testusername", password: "testpassword", statusCode: 200, }, { username: "", password: "testpassword", statusCode: 422, }, { username: "testusername", password: "", statusCode: 422, }, { username: "t", password: "testpassword", statusCode: 422, }, { username: "testusername", password: "test", statusCode: 500, }, { username: "testusername", password: "", statusCode: 422, }, } // Register user rr := httptest.NewRecorder() currBody := struct { Username string `json:"username"` Password string `json:"password"` }{ Username: "testusername", Password: "testpassword", } reqBody, err := json.Marshal(currBody) if err != nil { t.Errorf("Error creating a new request body: %v", err) } reqBodyReader := bytes.NewReader(reqBody) req := httptest.NewRequest("POST", "/register", reqBodyReader) router.ServeHTTP(rr, req) // Check registration results if rr.Code != 201 { t.Errorf("Expected status code %d, got %d", 201, rr.Code) } for _, currentTestCase := range testCases { // Start checking login rrLogin := httptest.NewRecorder() currBody = struct { Username string `json:"username"` Password string `json:"password"` }{ Username: currentTestCase.username, Password: currentTestCase.password, } reqBody, err = json.Marshal(currBody) if err != nil { t.Errorf("Error creating a new request body: %v", err) } reqBodyReader = bytes.NewReader(reqBody) req = httptest.NewRequest("POST", "/login", reqBodyReader) router.ServeHTTP(rrLogin, req) // Check login results if rrLogin.Code != currentTestCase.statusCode { t.Errorf("Expected status code %d, got %d", currentTestCase.statusCode, rrLogin.Code) } if rrLogin.Code == 200 { if rrLogin.Header().Get("Set-Cookie") == "" { t.Errorf("Expected a cookie to be set, but it wasn't") } } } } func TestGetMe(t *testing.T) { db := common.TestDBInit() defer common.DestroyTestingDB(db) db.AutoMigrate(&User{}) db.AutoMigrate(&Profile{}) db.AutoMigrate(&Session{}) t.Setenv("ALLOW_REGISTRATION", "true") t.Setenv("COOKIE_STRING", "supercustomcookie") router := UserRoutes(db) testCases := []struct { cookieEnabled bool statusCode int }{ { cookieEnabled: true, statusCode: 200, }, { cookieEnabled: false, statusCode: 500, }, } // Register user rr := httptest.NewRecorder() currBody := struct { Username string `json:"username"` Password string `json:"password"` }{ Username: "testusername", Password: "testpassword", } reqBody, err := json.Marshal(currBody) if err != nil { t.Errorf("Error creating a new request body: %v", err) } reqBodyReader := bytes.NewReader(reqBody) req := httptest.NewRequest("POST", "/register", reqBodyReader) router.ServeHTTP(rr, req) // Check registration results if rr.Code != 201 { t.Errorf("Expected status code %d, got %d", 201, rr.Code) } // Login to get cookie rr = httptest.NewRecorder() currBodyLogin := struct { Username string `json:"username"` Password string `json:"password"` }{ Username: "testusername", Password: "testpassword", } reqBody, err = json.Marshal(currBodyLogin) if err != nil { t.Errorf("Error creating a new request body: %v", err) } reqBodyReader = bytes.NewReader(reqBody) req = httptest.NewRequest("POST", "/login", reqBodyReader) router.ServeHTTP(rr, req) for _, currentTestCase := range testCases { // Start checking Profile rrProfile := httptest.NewRecorder() if err != nil { t.Errorf("Error creating a new request body: %v", err) } req = httptest.NewRequest("GET", "/me", nil) if currentTestCase.cookieEnabled { req.AddCookie(rr.Result().Cookies()[0]) } router.ServeHTTP(rrProfile, req) // Check Profile results if rrProfile.Code != currentTestCase.statusCode { t.Errorf("Expected status code %d, got %d", currentTestCase.statusCode, rrProfile.Code) } if currentTestCase.statusCode == 200 { var resultsObj map[string]any resBodyBytes, err := ioutil.ReadAll(rrProfile.Body) if err != nil { t.Errorf("Error reading response body: %v", err) } err = json.Unmarshal(resBodyBytes, &resultsObj) if err != nil { t.Errorf("Error unmarshalling response body: %v", err) } if resultsObj["username"] != "testusername" { t.Errorf("Expected username %s, got %s", "testusername", resultsObj["username"]) } } } }