From f3472ce3d2ca6d7a1cf9a0d4ee652da46f9cb86c Mon Sep 17 00:00:00 2001 From: Mattthew R Kasun Date: Fri, 26 Mar 2021 17:55:52 -0400 Subject: [PATCH] checkpoint commit --- go.mod | 29 ------ go.sum | 2 + user_test.go | 290 +++++++++++++++++++++++++++++++++++---------------- 3 files changed, 201 insertions(+), 120 deletions(-) delete mode 100644 go.mod diff --git a/go.mod b/go.mod deleted file mode 100644 index 4cf428e33..000000000 --- a/go.mod +++ /dev/null @@ -1,29 +0,0 @@ -module github.com/gravitl/netmaker - -go 1.15 - -require ( - github.com/davecgh/go-spew v1.1.1 - github.com/dgrijalva/jwt-go v3.2.0+incompatible - github.com/go-playground/universal-translator v0.17.0 // indirect - github.com/golang/protobuf v1.5.1 - github.com/gorilla/handlers v1.5.1 - github.com/gorilla/mux v1.8.0 - github.com/grpc-ecosystem/go-grpc-middleware v1.0.0 - github.com/leodido/go-urn v1.2.0 // indirect - github.com/mitchellh/go-homedir v1.1.0 - github.com/robfig/cron v1.2.0 - github.com/spf13/cobra v0.0.3 - github.com/spf13/viper v1.7.1 - github.com/takama/daemon v1.0.0 - github.com/vishvananda/netlink v1.1.0 - go.mongodb.org/mongo-driver v1.4.3 - golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9 - golang.org/x/net v0.0.0-20210324205630-d1beb07c2056 // indirect - golang.org/x/text v0.3.5 // indirect - golang.zx2c4.com/wireguard/wgctrl v0.0.0-20200609130330-bd2cb7843e1b - google.golang.org/genproto v0.0.0-20210325141258-5636347f2b14 // indirect - google.golang.org/grpc v1.36.0 - gopkg.in/go-playground/validator.v9 v9.31.0 - gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c -) diff --git a/go.sum b/go.sum index 9610cf675..8fac41839 100644 --- a/go.sum +++ b/go.sum @@ -221,6 +221,7 @@ github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINE github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= +github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI= github.com/prometheus/client_golang v0.9.1/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw= @@ -267,6 +268,7 @@ github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXf github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= +github.com/stretchr/testify v1.6.1 h1:hDPOHmpOpP40lSULcqw7IrRb/u7w6RpDC9399XyoNd0= github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/subosito/gotenv v1.2.0 h1:Slr1R9HxAlEKefgq5jn9U+DnETlIUa6HfgEzj0g5d7s= github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69rRypqCw= diff --git a/user_test.go b/user_test.go index 2c9fba8e7..8b067a863 100644 --- a/user_test.go +++ b/user_test.go @@ -16,6 +16,7 @@ import ( "github.com/stretchr/testify/assert" ) +//change this --- there is an existing type type AuthorizationResponse struct { Username string AuthToken string @@ -32,7 +33,15 @@ type badResponse struct { Message string } -//assumption: starting with empty database +type AuthorizeTestCase struct { + testname string + name string + password string + code int + tokenExpected bool + errMessage string +} + func TestMain(m *testing.M) { mongoconn.ConnectDatabase() var waitgroup sync.WaitGroup @@ -45,90 +54,105 @@ func TestMain(m *testing.M) { func TestUsers(t *testing.T) { - t.Run("check that admin user does not exist", func(t *testing.T) { - response := checkAdminExists(t) - assert.Equal(t, false, response) - }) + // t.Run("check that admin user does not exist", func(t *testing.T) { + // response := checkAdminExists(t) + // assert.Equal(t, false, response) + // }) - t.Run("add admin user", func(t *testing.T) { + t.Run("Admin Creation", func(t *testing.T) { var admin, user models.User admin.UserName = "admin" admin.Password = "password" + if !adminExists(t) { + t.Run("AdminCreationValid", func(t *testing.T) { + response, err := api(admin, http.MethodPost, "http://localhost:8081/users/createadmin", "") + if err != nil { + t.Error("error calling createadmin", err) + } + defer response.Body.Close() + json.NewDecoder(response.Body).Decode(&user) + assert.Equal(t, admin.UserName, user.UserName) + assert.Equal(t, true, user.IsAdmin) + assert.Equal(t, http.StatusOK, response.StatusCode) + assert.True(t, adminExists(t), "Admin creation failed") + }) + t.Run("AdminCreationInvalid", func(t *testing.T) { + response, err := api(admin, http.MethodPost, "http://localhost:8081/users/createadmin", "") + if err != nil { + t.Error("error calling createadmin", err) + } + defer response.Body.Close() + var message badResponse + json.NewDecoder(response.Body).Decode(&message) + assert.Equal(t, http.StatusUnauthorized, response.StatusCode) + assert.Equal(t, http.StatusUnauthorized, message.Code) + assert.Equal(t, "W1R3: Admin already exists! ", message.Message) + }) + } else { + t.Run("AdminCreationInvalid", func(t *testing.T) { + response, err := api(admin, http.MethodPost, "http://localhost:8081/users/createadmin", "") - //payload := map[string]string{"username": "admin", "password": "admin"} - payload, _ := json.Marshal(admin) - request, err := http.NewRequest(http.MethodPost, "http://localhost:8081/users/createadmin", bytes.NewBuffer(payload)) - if err != nil { - t.Error(err) + if err != nil { + t.Error("error calling createadmin", err) + } + defer response.Body.Close() + var message badResponse + json.NewDecoder(response.Body).Decode(&message) + assert.Equal(t, http.StatusUnauthorized, response.StatusCode) + assert.Equal(t, http.StatusUnauthorized, message.Code) + assert.Equal(t, "W1R3: Admin already exists! ", message.Message) + }) + //deleteAdmin() + t.Run("Admin Creation - Valid", func(t *testing.T) { + t.Skip() + response, err := api(admin, http.MethodPost, "http://localhost:8081/users/createadmin", "") + if err != nil { + t.Error("error calling createadmin", err) + } + defer response.Body.Close() + json.NewDecoder(response.Body).Decode(&user) + assert.Equal(t, admin.UserName, user.UserName) + assert.Equal(t, true, user.IsAdmin) + assert.Equal(t, http.StatusOK, response.StatusCode) + assert.True(t, adminExists(t), "Admin creation failed") + }) } - request.Header.Set("Authorization", "Bearer secretkey") - request.Header.Set("Content-Type", "application/json") - client := &http.Client{} - response, err := client.Do(request) - if err != nil { - t.Error("error calling createadmin", err) - } - defer response.Body.Close() - body, _ := ioutil.ReadAll(response.Body) - _ = json.Unmarshal(body, &user) - assert.Equal(t, admin.UserName, user.UserName) - assert.Equal(t, true, user.IsAdmin) - assert.Equal(t, http.StatusOK, response.StatusCode) - adminExists := checkAdminExists(t) - assert.Equal(t, true, adminExists) }) t.Run("GetUser", func(t *testing.T) { - t.Skip() //ensure admin exists - if !checkAdminExists(t) { + if !adminExists(t) { t.Error("admin account does not exist") return } //authenticate - var admin models.User - admin.UserName = "admin" - admin.Password = "admin" - - payload, _ := json.Marshal(admin) - request, err := http.NewRequest(http.MethodPut, "http://localhost:8081/users/authenticate", bytes.NewBuffer(payload)) + token, err := authenticate() if err != nil { - t.Error(err) + t.Error("could not authenticate") } - request.Header.Set("Content-Type", "application/json") - client := &http.Client{} - - response, err := client.Do(request) + response, err := api("", http.MethodGet, "http://localhost:8081/users/admin", token) if err != nil { - t.Error("error calling authenticate", err) + t.Error("could not get user") } defer response.Body.Close() - body := models.User{} - json.NewDecoder(response.Body).Decode(&body) - t.Log(body) + var user models.User + json.NewDecoder(response.Body).Decode(&user) assert.Equal(t, http.StatusOK, response.StatusCode) - assert.Equal(t, "admin", body.UserName) + assert.Equal(t, "admin", user.UserName) + assert.Equal(t, true, user.IsAdmin) - request, err = http.NewRequest(http.MethodGet, "http://localhost:8081/users/admim", nil) - if err != nil { - t.Error(err) - } - request.Header.Set("Authorization", "Bearer secretkey") - client = &http.Client{} - response, err = client.Do(request) - if err != nil { - t.Error(err) - } - defer response.Body.Close() - body = models.User{} - json.NewDecoder(response.Body).Decode(&body) - t.Log(body) - assert.Equal(t, http.StatusOK, response.StatusCode) - assert.Equal(t, "admin", body.UserName) }) t.Run("Update User", func(t *testing.T) { t.Skip() + if !adminExists(t) { + addAdmin(t) + } + //token, err := authenticate() + //if err != nil { + // t.Error("could not authenticate") + //} + var admin, user models.User admin.UserName = "admin" admin.Password = "admin" @@ -156,48 +180,132 @@ func TestUsers(t *testing.T) { }) t.Run("Authenticate User", func(t *testing.T) { - var admin models.User - - admin.UserName = "admin" - admin.Password = "password" - - payload, _ := json.Marshal(admin) - request, err := http.NewRequest(http.MethodPost, "http://localhost:8081/users/authenticate", bytes.NewBuffer(payload)) - if err != nil { - t.Error(err) + cases := []AuthorizeTestCase{ + AuthorizeTestCase{ + testname: "Invalid User", + name: "invaliduser", + password: "password", + code: http.StatusBadRequest, + tokenExpected: false, + errMessage: "W1R3: It's not you it's me.", + }, + AuthorizeTestCase{ + testname: "empty user", + name: "", + password: "password", + code: http.StatusBadRequest, + tokenExpected: false, + errMessage: "W1R3: Username can't be empty", + }, + AuthorizeTestCase{ + testname: "empty password", + name: "admin", + password: "", + code: http.StatusBadRequest, + tokenExpected: false, + errMessage: "W1R3: Password can't be empty", + }, + AuthorizeTestCase{ + testname: "Invalid Passord", + name: "admin", + password: "xxxxxxx", + code: http.StatusBadRequest, + tokenExpected: false, + errMessage: "W1R3: It's not you it's me.", + }, + AuthorizeTestCase{ + testname: "Valid User", + name: "admin", + password: "password", + code: http.StatusOK, + tokenExpected: true, + errMessage: "W1R3: Device Admin Authorized", + }, } - request.Header.Set("Authorization", "Bearer secretkey") - request.Header.Set("Content-Type", "application/json") - client := &http.Client{} - response, err := client.Do(request) - if err != nil { - t.Error(err) - } - defer response.Body.Close() - message := goodResponse{} - json.NewDecoder(response.Body).Decode(&message) - assert.Equal(t, http.StatusOK, response.StatusCode) - assert.Equal(t, "W1R3: Device admin Authorized", message.Message) - }) - t.Run("empty test", func(t *testing.T) { - assert.Equal(t, true, true) + for _, tc := range cases { + t.Run(tc.testname, func(t *testing.T) { + if !adminExists(t) { + addAdmin(t) + } + var admin models.User + admin.UserName = tc.name + admin.Password = tc.password + response, err := api(admin, http.MethodPost, "http://localhost:8081/users/authenticate", "secretkey") + if err != nil { + t.Error("authenticate api call failed") + } + if tc.tokenExpected { + var body goodResponse + json.NewDecoder(response.Body).Decode(&body) + assert.NotEmpty(t, body.Response.AuthToken, "token not returned") + assert.Equal(t, "W1R3: Device admin Authorized", body.Message) + } else { + var body badResponse + json.NewDecoder(response.Body).Decode(&body) + assert.Equal(t, tc.errMessage, body.Message) + } + assert.Equal(t, tc.code, response.StatusCode) + }) + } }) - } -func checkAdminExists(t *testing.T) bool { +func adminExists(t *testing.T) bool { response, err := http.Get("http://localhost:8081/users/hasadmin") if err != nil { t.Fatal("error calling users/hasadmin", err) } + assert.Equal(t, http.StatusOK, response.StatusCode) defer response.Body.Close() var body bool json.NewDecoder(response.Body).Decode(&body) return body - //body, _ := ioutil.ReadAll(response.Body) - //vif body { - // return true - //} - //return false +} + +func api(data interface{}, method, url, authorization string) (*http.Response, error) { + payload, err := json.Marshal(data) + if err != nil { + return nil, err + } + request, err := http.NewRequest(method, url, bytes.NewBuffer(payload)) + if err != nil { + return nil, err + } + request.Header.Set("Content-Type", "application/json") + if authorization != "" { + request.Header.Set("Authorization", "Bearer "+authorization) + } + client := http.Client{} + return client.Do(request) +} + +func addAdmin(t *testing.T) { + var admin models.User + admin.UserName = "admin" + admin.Password = "password" + payload, _ := json.Marshal(admin) + request, err := http.NewRequest(http.MethodPost, "http://localhost:8081/users/createadmin", + bytes.NewBuffer(payload)) + assert.NotNilf(t, err, "none nil error creating http request") + request.Header.Set("Authorization", "Bearer secretkey") + request.Header.Set("Content-Type", "application/json") + client := &http.Client{} + response, err := client.Do(request) + assert.NotNilf(t, err, "non nil err response from createadmin") + assert.Equal(t, http.StatusOK, response.StatusCode) +} + +func authenticate() (string, error) { + var admin models.User + admin.UserName = "admin" + admin.Password = "password" + response, err := api(admin, http.MethodPost, "http://localhost:8081/users/authenticate", "secretkey") + if err != nil { + return "", err + } + var body goodResponse + json.NewDecoder(response.Body).Decode(&body) + token := body.Response.AuthToken + return token, nil }