mirror of
https://github.com/3ybactuk/marketplace-go-service-project.git
synced 2025-10-30 22:13:44 +03:00
[hw-5] concurrency, graceful shutdown, concurrent tests
This commit is contained in:
@@ -2,15 +2,21 @@ package repository
|
||||
|
||||
import (
|
||||
"context"
|
||||
"sync"
|
||||
"testing"
|
||||
|
||||
"route256/cart/internal/domain/entity"
|
||||
"route256/cart/internal/domain/model"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
"go.uber.org/goleak"
|
||||
|
||||
"route256/cart/internal/domain/entity"
|
||||
"route256/cart/internal/domain/model"
|
||||
)
|
||||
|
||||
func TestMain(m *testing.M) {
|
||||
goleak.VerifyTestMain(m)
|
||||
}
|
||||
|
||||
func TestAddItem(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
@@ -267,3 +273,135 @@ func TestDeleteItemsByUserID(t *testing.T) {
|
||||
|
||||
assert.Len(t, repo.storage, 0, "check storage length")
|
||||
}
|
||||
|
||||
func TestConcurrent_AddItemSameSku(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
const (
|
||||
goroutines = 100
|
||||
userID = entity.UID(42)
|
||||
sku = entity.Sku(777)
|
||||
)
|
||||
|
||||
repo := NewInMemoryRepository(1)
|
||||
ctx := context.Background()
|
||||
|
||||
var wg sync.WaitGroup
|
||||
|
||||
wg.Add(goroutines)
|
||||
|
||||
for i := 0; i < goroutines; i++ {
|
||||
go func() {
|
||||
defer wg.Done()
|
||||
|
||||
item := &model.Item{
|
||||
Product: &model.Product{Sku: sku},
|
||||
Count: 1,
|
||||
}
|
||||
require.NoError(t, repo.AddItem(ctx, userID, item))
|
||||
}()
|
||||
}
|
||||
|
||||
wg.Wait()
|
||||
|
||||
cart, err := repo.GetItemsByUserID(ctx, userID)
|
||||
require.NoError(t, err)
|
||||
|
||||
assert.Len(t, cart.Items, 1, "only one item should exist")
|
||||
assert.Equal(t, uint32(goroutines), cart.ItemCount[sku], "wrong count")
|
||||
}
|
||||
|
||||
func TestConcurrent_AddItemDifferentUsers(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
const (
|
||||
users = 50
|
||||
addsPerUser = 10
|
||||
)
|
||||
|
||||
repo := NewInMemoryRepository(users)
|
||||
ctx := context.Background()
|
||||
|
||||
var wg sync.WaitGroup
|
||||
|
||||
for u := 0; u < users; u++ {
|
||||
uid := entity.UID(u)
|
||||
wg.Add(1)
|
||||
|
||||
go func(id entity.UID) {
|
||||
defer wg.Done()
|
||||
|
||||
for i := 0; i < addsPerUser; i++ {
|
||||
item := &model.Item{
|
||||
Product: &model.Product{Sku: entity.Sku(i)},
|
||||
Count: 1,
|
||||
}
|
||||
require.NoError(t, repo.AddItem(ctx, id, item))
|
||||
}
|
||||
}(uid)
|
||||
}
|
||||
|
||||
wg.Wait()
|
||||
|
||||
for u := 0; u < users; u++ {
|
||||
uid := entity.UID(u)
|
||||
cart, err := repo.GetItemsByUserID(ctx, uid)
|
||||
require.NoError(t, err)
|
||||
|
||||
assert.Lenf(t, cart.Items, addsPerUser, "user %d has wrong item count", u)
|
||||
for i := 0; i < addsPerUser; i++ {
|
||||
sku := entity.Sku(i)
|
||||
assert.Equalf(t, uint32(1), cart.ItemCount[sku], "user %d: sku %d count", u, sku)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestConcurrent_AddAndRead(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
repo := NewInMemoryRepository(1)
|
||||
ctx := context.Background()
|
||||
uid := entity.UID(1)
|
||||
sku := entity.Sku(9)
|
||||
|
||||
const (
|
||||
writerGoroutines = 20
|
||||
readerGoroutines = 20
|
||||
iterations = 100
|
||||
)
|
||||
|
||||
var wg sync.WaitGroup
|
||||
|
||||
for i := 0; i < writerGoroutines; i++ {
|
||||
wg.Add(1)
|
||||
go func() {
|
||||
defer wg.Done()
|
||||
for j := 0; j < iterations; j++ {
|
||||
item := &model.Item{
|
||||
Product: &model.Product{Sku: sku},
|
||||
Count: 1,
|
||||
}
|
||||
require.NoError(t, repo.AddItem(ctx, uid, item))
|
||||
}
|
||||
}()
|
||||
}
|
||||
|
||||
for i := 0; i < readerGoroutines; i++ {
|
||||
wg.Add(1)
|
||||
go func() {
|
||||
defer wg.Done()
|
||||
for j := 0; j < iterations; j++ {
|
||||
_, err := repo.GetItemsByUserID(ctx, uid)
|
||||
require.NoError(t, err)
|
||||
}
|
||||
}()
|
||||
}
|
||||
|
||||
wg.Wait()
|
||||
|
||||
cart, err := repo.GetItemsByUserID(ctx, uid)
|
||||
require.NoError(t, err)
|
||||
expected := uint32(writerGoroutines * iterations)
|
||||
|
||||
assert.Equal(t, expected, cart.ItemCount[sku], "wrong item count")
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user