mirror of
https://github.com/3ybactuk/marketplace-go-service-project.git
synced 2025-10-30 14:03:45 +03:00
[hw-2] add tests, coverage, benchmarks
This commit is contained in:
193
cart/tests/integration/cart_integration_test.go
Normal file
193
cart/tests/integration/cart_integration_test.go
Normal file
@@ -0,0 +1,193 @@
|
||||
//go:build integration
|
||||
// +build integration
|
||||
|
||||
package integration
|
||||
|
||||
import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/ozontech/allure-go/pkg/framework/provider"
|
||||
"github.com/ozontech/allure-go/pkg/framework/suite"
|
||||
"github.com/testcontainers/testcontainers-go"
|
||||
"github.com/testcontainers/testcontainers-go/wait"
|
||||
|
||||
"route256/cart/internal/app"
|
||||
"route256/cart/internal/domain/cart/repository"
|
||||
cartService "route256/cart/internal/domain/cart/service"
|
||||
"route256/cart/internal/domain/entity"
|
||||
"route256/cart/internal/domain/model"
|
||||
productsService "route256/cart/internal/domain/products/service"
|
||||
)
|
||||
|
||||
const (
|
||||
productServiceImage = "gitlab-registry.ozon.dev/go/classroom-18/students/base/products:latest"
|
||||
testToken = "testToken"
|
||||
|
||||
testSku = 1076963
|
||||
testName = "Теория нравственных чувств | Смит Адам"
|
||||
testUID = entity.UID(1337)
|
||||
)
|
||||
|
||||
type CartHandlerSuite struct {
|
||||
suite.Suite
|
||||
|
||||
psContainer testcontainers.Container
|
||||
server *httptest.Server
|
||||
|
||||
cartSvc *cartService.CartService
|
||||
}
|
||||
|
||||
func TestCartHandlerSuite(t *testing.T) {
|
||||
suite.RunSuite(t, new(CartHandlerSuite))
|
||||
}
|
||||
|
||||
func (s *CartHandlerSuite) BeforeAll(t provider.T) {
|
||||
ctx := context.Background()
|
||||
|
||||
t.WithNewStep("start product-service container", func(sCtx provider.StepCtx) {
|
||||
req := testcontainers.ContainerRequest{
|
||||
Image: productServiceImage,
|
||||
ExposedPorts: []string{"8082/tcp"},
|
||||
WaitingFor: wait.ForHTTP("/docs").WithStartupTimeout(10 * time.Second),
|
||||
}
|
||||
container, err := testcontainers.GenericContainer(ctx,
|
||||
testcontainers.GenericContainerRequest{
|
||||
ContainerRequest: req,
|
||||
Started: true,
|
||||
})
|
||||
sCtx.Require().NoError(err, "create container")
|
||||
s.psContainer = container
|
||||
})
|
||||
|
||||
var productURL string
|
||||
t.WithNewStep("discover product-service URL", func(sCtx provider.StepCtx) {
|
||||
endpoint, err := s.psContainer.Endpoint(ctx, "")
|
||||
sCtx.Require().NoError(err)
|
||||
productURL = endpoint
|
||||
})
|
||||
|
||||
t.WithNewStep("init cart-service", func(sCtx provider.StepCtx) {
|
||||
prodClient := productsService.NewProductService(
|
||||
*http.DefaultClient,
|
||||
testToken,
|
||||
productURL,
|
||||
)
|
||||
|
||||
repo := repository.NewInMemoryRepository(10)
|
||||
s.cartSvc = cartService.NewCartService(repo, prodClient)
|
||||
|
||||
appSrv := &app.App{}
|
||||
|
||||
s.server = httptest.NewServer(appSrv.BootstrapHandlers(s.cartSvc))
|
||||
})
|
||||
}
|
||||
|
||||
func (s *CartHandlerSuite) AfterAll(t provider.T) {
|
||||
_ = s.psContainer.Terminate(context.Background())
|
||||
s.server.Close()
|
||||
}
|
||||
|
||||
// DELETE /user/<user_id>/cart/<sku_id>
|
||||
func (s *CartHandlerSuite) TestDeleteItemPositive(t provider.T) {
|
||||
ctx := context.Background()
|
||||
|
||||
item := &model.Item{
|
||||
Product: &model.Product{
|
||||
Sku: testSku,
|
||||
},
|
||||
Count: 1,
|
||||
}
|
||||
|
||||
t.WithNewStep("fill cart in usecase", func(sCtx provider.StepCtx) {
|
||||
err := s.cartSvc.AddItem(context.Background(),
|
||||
testUID, item)
|
||||
sCtx.Require().NoError(err)
|
||||
|
||||
cart, err := s.cartSvc.GetItemsByUserID(ctx, testUID)
|
||||
sCtx.Require().NoError(err)
|
||||
|
||||
sCtx.Require().Len(cart.Items, 1, "check cart contains product")
|
||||
sCtx.Require().Equal(testUID, cart.UserID, "check user ID equals")
|
||||
sCtx.Require().Equal(item.Product.Sku, cart.Items[0].Product.Sku, "check product sku equals")
|
||||
})
|
||||
|
||||
t.WithNewStep("call DELETE handler", func(sCtx provider.StepCtx) {
|
||||
url := fmt.Sprintf("%s/user/%d/cart/%d", s.server.URL, testUID, testSku)
|
||||
|
||||
req, err := http.NewRequest(http.MethodDelete, url, nil)
|
||||
sCtx.Require().NoError(err)
|
||||
|
||||
resp, err := s.server.Client().Do(req)
|
||||
sCtx.Require().NoError(err)
|
||||
defer resp.Body.Close()
|
||||
|
||||
sCtx.Require().Equal(http.StatusNoContent, resp.StatusCode, "delete handler unexpected status code")
|
||||
})
|
||||
|
||||
t.WithNewStep("check cart empty in usecase", func(sCtx provider.StepCtx) {
|
||||
_, err := s.cartSvc.GetItemsByUserID(ctx, testUID)
|
||||
sCtx.Require().Error(err)
|
||||
})
|
||||
}
|
||||
|
||||
// GET /user/<user_id>/cart
|
||||
func (s *CartHandlerSuite) TestGetCartPositive(t provider.T) {
|
||||
ctx := context.Background()
|
||||
|
||||
item := &model.Item{
|
||||
Product: &model.Product{
|
||||
Sku: testSku,
|
||||
},
|
||||
Count: 2,
|
||||
}
|
||||
|
||||
t.WithNewStep("fill cart in usecase", func(sCtx provider.StepCtx) {
|
||||
err := s.cartSvc.AddItem(context.Background(),
|
||||
testUID, item)
|
||||
sCtx.Require().NoError(err)
|
||||
|
||||
cart, err := s.cartSvc.GetItemsByUserID(ctx, testUID)
|
||||
sCtx.Require().NoError(err)
|
||||
|
||||
sCtx.Require().Len(cart.Items, 1, "check cart contains product")
|
||||
sCtx.Require().Equal(testUID, cart.UserID, "check user ID equals")
|
||||
sCtx.Require().Equal(item.Product.Sku, cart.Items[0].Product.Sku, "check product sku equals")
|
||||
sCtx.Require().Equal(item.Count, cart.Items[0].Count, "check product count")
|
||||
})
|
||||
|
||||
t.WithNewStep("call GET handler", func(sCtx provider.StepCtx) {
|
||||
url := fmt.Sprintf("%s/user/%d/cart", s.server.URL, testUID)
|
||||
|
||||
req, err := http.NewRequest(http.MethodGet, url, nil)
|
||||
sCtx.Require().NoError(err)
|
||||
|
||||
resp, err := s.server.Client().Do(req)
|
||||
sCtx.Require().NoError(err)
|
||||
defer resp.Body.Close()
|
||||
|
||||
sCtx.Require().Equal(http.StatusOK, resp.StatusCode, "check GET status code")
|
||||
sCtx.Require().Equal("application/json", resp.Header.Get("Content-Type"), "check GET content type")
|
||||
|
||||
var body struct {
|
||||
Items []struct {
|
||||
Sku int64 `json:"sku"`
|
||||
Name string `json:"name"`
|
||||
Count uint32 `json:"count"`
|
||||
Price uint32 `json:"price"`
|
||||
} `json:"items"`
|
||||
TotalPrice uint32 `json:"total_price"`
|
||||
}
|
||||
sCtx.Require().NoError(json.NewDecoder(resp.Body).Decode(&body))
|
||||
|
||||
sCtx.Require().Len(body.Items, 1, "check items len")
|
||||
sCtx.Require().Equal(int64(testSku), body.Items[0].Sku, "check sku")
|
||||
sCtx.Require().Equal(uint32(2), body.Items[0].Count, "check item count")
|
||||
sCtx.Require().Greater(body.TotalPrice, uint32(0), "check price")
|
||||
})
|
||||
}
|
||||
Reference in New Issue
Block a user