1
0
mirror of https://github.com/raseels-repos/golang-saas-starter-kit.git synced 2025-06-06 23:46:29 +02:00
Lee Brown 24dd0dff42 Complated web-api crud endpoints and unittests. unittest for find
endpoints still need to be implemented.
2019-06-27 04:48:18 -08:00

889 lines
24 KiB
Go

package tests
import (
"context"
"encoding/json"
"fmt"
"net/http"
"testing"
"time"
"geeks-accelerator/oss/saas-starter-kit/example-project/internal/mid"
"geeks-accelerator/oss/saas-starter-kit/example-project/internal/platform/auth"
"geeks-accelerator/oss/saas-starter-kit/example-project/internal/platform/tests"
"geeks-accelerator/oss/saas-starter-kit/example-project/internal/platform/web"
"geeks-accelerator/oss/saas-starter-kit/example-project/internal/project"
"github.com/pborman/uuid"
)
func mockProjectCreateRequest(accountID string) project.ProjectCreateRequest {
return project.ProjectCreateRequest{
Name: fmt.Sprintf("Moon Launch %s", uuid.NewRandom().String()),
AccountID: accountID,
}
}
// mockProject creates a new project for testing and associates it with the supplied account ID.
func newMockProject(accountID string) *project.Project {
req := mockProjectCreateRequest(accountID)
p, err := project.Create(tests.Context(), auth.Claims{}, test.MasterDB, req, time.Now().UTC().AddDate(-1, -1, -1))
if err != nil {
panic(err)
}
return p
}
// TestProjectCRUDAdmin tests all the project CRUD endpoints using an user with role admin.
func TestProjectCRUDAdmin(t *testing.T) {
defer tests.Recover(t)
tr := roleTests[auth.RoleAdmin]
// Add claims to the context for the project.
ctx := context.WithValue(tests.Context(), auth.Key, tr.Claims)
// Test create.
var created project.ProjectResponse
{
expectedStatus := http.StatusCreated
req := mockProjectCreateRequest(tr.Account.ID)
rt := requestTest{
fmt.Sprintf("Create %d w/role %s", expectedStatus, tr.Role),
http.MethodPost,
"/v1/projects",
req,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual project.ProjectResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
created = actual
expectedMap := map[string]interface{}{
"updated_at": web.NewTimeResponse(ctx, actual.UpdatedAt.Value),
"id": actual.ID,
"account_id": req.AccountID,
"status": web.NewEnumResponse(ctx, "active", project.ProjectStatus_Values),
"created_at": web.NewTimeResponse(ctx, actual.CreatedAt.Value),
"name": req.Name,
}
var expected project.ProjectResponse
if err := decodeMapToStruct(expectedMap, &expected); err != nil {
t.Logf("\t\tGot error : %+v\nActual results to format expected : \n", err)
printResultMap(ctx, w.Body.Bytes()) // used to help format expectedMap
t.Fatalf("\t%s\tDecode expected failed.", tests.Failed)
}
if diff := cmpDiff(t, actual, expected); diff {
if len(expectedMap) == 0 {
printResultMap(ctx, w.Body.Bytes()) // used to help format expectedMap
}
t.Fatalf("\t%s\tReceived expected result.", tests.Failed)
}
t.Logf("\t%s\tReceived expected result.", tests.Success)
}
// Test read.
{
expectedStatus := http.StatusOK
rt := requestTest{
fmt.Sprintf("Read %d w/role %s", expectedStatus, tr.Role),
http.MethodGet,
fmt.Sprintf("/v1/projects/%s", created.ID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual project.ProjectResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
if diff := cmpDiff(t, actual, created); diff {
t.Fatalf("\t%s\tReceived expected result.", tests.Failed)
}
t.Logf("\t%s\tReceived expected result.", tests.Success)
}
// Test Read with random ID.
{
expectedStatus := http.StatusNotFound
randID := uuid.NewRandom().String()
rt := requestTest{
fmt.Sprintf("Read %d w/role %s using random ID", expectedStatus, tr.Role),
http.MethodGet,
fmt.Sprintf("/v1/projects/%s", randID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: fmt.Sprintf("project %s not found: Entity not found", randID),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Test Read with forbidden ID.
forbiddenProject := newMockProject(newMockSignup().account.ID)
{
expectedStatus := http.StatusNotFound
rt := requestTest{
fmt.Sprintf("Read %d w/role %s using forbidden ID", expectedStatus, tr.Role),
http.MethodGet,
fmt.Sprintf("/v1/projects/%s", forbiddenProject.ID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: fmt.Sprintf("project %s not found: Entity not found", forbiddenProject.ID),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Test update.
{
expectedStatus := http.StatusNoContent
newName := uuid.NewRandom().String()
rt := requestTest{
fmt.Sprintf("Update %d w/role %s", expectedStatus, tr.Role),
http.MethodPatch,
"/v1/projects",
project.ProjectUpdateRequest{
ID: created.ID,
Name: &newName,
},
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
if len(w.Body.String()) != 0 {
if diff := cmpDiff(t, w.Body.Bytes(), nil); diff {
t.Fatalf("\t%s\tReceived expected empty.", tests.Failed)
}
}
t.Logf("\t%s\tReceived expected empty.", tests.Success)
}
// Test archive.
{
expectedStatus := http.StatusNoContent
rt := requestTest{
fmt.Sprintf("Archive %d w/role %s", expectedStatus, tr.Role),
http.MethodPatch,
"/v1/projects/archive",
project.ProjectArchiveRequest{
ID: created.ID,
},
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
if len(w.Body.String()) != 0 {
if diff := cmpDiff(t, w.Body.Bytes(), nil); diff {
t.Fatalf("\t%s\tReceived expected empty.", tests.Failed)
}
}
t.Logf("\t%s\tReceived expected empty.", tests.Success)
}
// Test delete.
{
expectedStatus := http.StatusNoContent
rt := requestTest{
fmt.Sprintf("Delete %d w/role %s", expectedStatus, tr.Role),
http.MethodDelete,
fmt.Sprintf("/v1/projects/%s", created.ID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
if len(w.Body.String()) != 0 {
if diff := cmpDiff(t, w.Body.Bytes(), nil); diff {
t.Fatalf("\t%s\tReceived expected empty.", tests.Failed)
}
}
t.Logf("\t%s\tReceived expected empty.", tests.Success)
}
}
// TestProjectCRUDUser tests all the project CRUD endpoints using an user with role project.
func TestProjectCRUDUser(t *testing.T) {
defer tests.Recover(t)
tr := roleTests[auth.RoleUser]
// Add claims to the context for the project.
ctx := context.WithValue(tests.Context(), auth.Key, tr.Claims)
// Test create.
{
expectedStatus := http.StatusForbidden
req := mockProjectCreateRequest(tr.Account.ID)
rt := requestTest{
fmt.Sprintf("Create %d w/role %s", expectedStatus, tr.Role),
http.MethodPost,
"/v1/projects",
req,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: mid.ErrForbidden.Error(),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Since role doesn't support create, bypass auth to test other endpoints.
created := newMockProject(tr.Account.ID).Response(ctx)
// Test read.
{
expectedStatus := http.StatusOK
rt := requestTest{
fmt.Sprintf("Read %d w/role %s", expectedStatus, tr.Role),
http.MethodGet,
fmt.Sprintf("/v1/projects/%s", created.ID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual *project.ProjectResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
if diff := cmpDiff(t, actual, created); diff {
t.Fatalf("\t%s\tReceived expected result.", tests.Failed)
}
t.Logf("\t%s\tReceived expected result.", tests.Success)
}
// Test Read with random ID.
{
expectedStatus := http.StatusNotFound
randID := uuid.NewRandom().String()
rt := requestTest{
fmt.Sprintf("Read %d w/role %s using random ID", expectedStatus, tr.Role),
http.MethodGet,
fmt.Sprintf("/v1/projects/%s", randID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: fmt.Sprintf("project %s not found: Entity not found", randID),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Test Read with forbidden ID.
forbiddenProject := newMockProject(newMockSignup().account.ID)
{
expectedStatus := http.StatusNotFound
rt := requestTest{
fmt.Sprintf("Read %d w/role %s using forbidden ID", expectedStatus, tr.Role),
http.MethodGet,
fmt.Sprintf("/v1/projects/%s", forbiddenProject.ID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: fmt.Sprintf("project %s not found: Entity not found", forbiddenProject.ID),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Test update.
{
expectedStatus := http.StatusForbidden
newName := uuid.NewRandom().String()
rt := requestTest{
fmt.Sprintf("Update %d w/role %s", expectedStatus, tr.Role),
http.MethodPatch,
"/v1/projects",
project.ProjectUpdateRequest{
ID: created.ID,
Name: &newName,
},
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: mid.ErrForbidden.Error(),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Test archive.
{
expectedStatus := http.StatusForbidden
rt := requestTest{
fmt.Sprintf("Archive %d w/role %s", expectedStatus, tr.Role),
http.MethodPatch,
"/v1/projects/archive",
project.ProjectArchiveRequest{
ID: created.ID,
},
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: mid.ErrForbidden.Error(),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Test delete.
{
expectedStatus := http.StatusForbidden
rt := requestTest{
fmt.Sprintf("Delete %d w/role %s", expectedStatus, tr.Role),
http.MethodDelete,
fmt.Sprintf("/v1/projects/%s", created.ID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: mid.ErrForbidden.Error(),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
}
// TestProjectCreate validates create project endpoint.
func TestProjectCreate(t *testing.T) {
defer tests.Recover(t)
tr := roleTests[auth.RoleAdmin]
// Add claims to the context for the project.
ctx := context.WithValue(tests.Context(), auth.Key, tr.Claims)
// Test create with invalid data.
{
expectedStatus := http.StatusBadRequest
req := mockProjectCreateRequest(tr.Account.ID)
invalidStatus := project.ProjectStatus("invalid status")
req.Status = &invalidStatus
rt := requestTest{
fmt.Sprintf("Create %d w/role %s using invalid data", expectedStatus, tr.Role),
http.MethodPost,
"/v1/projects",
req,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: "field validation error",
Fields: []web.FieldError{
{Field: "status", Error: "Key: 'ProjectCreateRequest.status' Error:Field validation for 'status' failed on the 'oneof' tag"},
},
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
}
// TestProjectUpdate validates update project endpoint.
func TestProjectUpdate(t *testing.T) {
defer tests.Recover(t)
tr := roleTests[auth.RoleAdmin]
// Add claims to the context for the project.
ctx := context.WithValue(tests.Context(), auth.Key, tr.Claims)
// Test update with invalid data.
{
expectedStatus := http.StatusBadRequest
invalidStatus := project.ProjectStatus("invalid status")
rt := requestTest{
fmt.Sprintf("Update %d w/role %s using invalid data", expectedStatus, tr.Role),
http.MethodPatch,
"/v1/projects",
project.ProjectUpdateRequest{
ID: uuid.NewRandom().String(),
Status: &invalidStatus,
},
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: "field validation error",
Fields: []web.FieldError{
{Field: "status", Error: "Key: 'ProjectUpdateRequest.status' Error:Field validation for 'status' failed on the 'oneof' tag"},
},
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
}
// TestProjectArchive validates archive project endpoint.
func TestProjectArchive(t *testing.T) {
defer tests.Recover(t)
tr := roleTests[auth.RoleAdmin]
// Add claims to the context for the project.
ctx := context.WithValue(tests.Context(), auth.Key, tr.Claims)
forbiddenProject := newMockProject(newMockSignup().account.ID)
// Test archive with invalid data.
{
expectedStatus := http.StatusBadRequest
rt := requestTest{
fmt.Sprintf("Archive %d w/role %s using invalid data", expectedStatus, tr.Role),
http.MethodPatch,
"/v1/projects/archive",
project.ProjectArchiveRequest{
ID: "a",
},
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: "field validation error",
Fields: []web.FieldError{
{Field: "id", Error: "Key: 'ProjectArchiveRequest.id' Error:Field validation for 'id' failed on the 'uuid' tag"},
},
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Test archive with forbidden ID.
{
expectedStatus := http.StatusForbidden
rt := requestTest{
fmt.Sprintf("Archive %d w/role %s using forbidden ID", expectedStatus, tr.Role),
http.MethodPatch,
"/v1/projects/archive",
project.ProjectArchiveRequest{
ID: forbiddenProject.ID,
},
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: project.ErrForbidden.Error(),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
}
// TestProjectDelete validates delete project endpoint.
func TestProjectDelete(t *testing.T) {
defer tests.Recover(t)
tr := roleTests[auth.RoleAdmin]
// Add claims to the context for the project.
ctx := context.WithValue(tests.Context(), auth.Key, tr.Claims)
forbiddenProject := newMockProject(newMockSignup().account.ID)
// Test delete with invalid data.
{
expectedStatus := http.StatusBadRequest
rt := requestTest{
fmt.Sprintf("Delete %d w/role %s using invalid data", expectedStatus, tr.Role),
http.MethodDelete,
"/v1/projects/a",
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: "field validation error",
Fields: []web.FieldError{
{Field: "id", Error: "Key: 'id' Error:Field validation for 'id' failed on the 'uuid' tag"},
},
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
// Test delete with forbidden ID.
{
expectedStatus := http.StatusForbidden
rt := requestTest{
fmt.Sprintf("Delete %d w/role %s using forbidden ID", expectedStatus, tr.Role),
http.MethodDelete,
fmt.Sprintf("/v1/projects/%s", forbiddenProject.ID),
nil,
tr.Token,
tr.Claims,
expectedStatus,
nil,
}
t.Logf("\tTest: %s - %s %s", rt.name, rt.method, rt.url)
w, ok := executeRequestTest(t, rt, ctx)
if !ok {
t.Fatalf("\t%s\tExecute request failed.", tests.Failed)
}
t.Logf("\t%s\tReceived valid status code of %d.", tests.Success, w.Code)
var actual web.ErrorResponse
if err := json.Unmarshal(w.Body.Bytes(), &actual); err != nil {
t.Logf("\t\tGot error : %+v", err)
t.Fatalf("\t%s\tDecode response body failed.", tests.Failed)
}
expected := web.ErrorResponse{
Error: project.ErrForbidden.Error(),
}
if diff := cmpDiff(t, actual, expected); diff {
t.Fatalf("\t%s\tReceived expected error.", tests.Failed)
}
t.Logf("\t%s\tReceived expected error.", tests.Success)
}
}