veza/veza-backend-api/internal/services/track_service_stats_test.go.disabled
2025-12-03 20:29:37 +01:00

303 lines
7.1 KiB
Text

package services
import (
"context"
"github.com/google/uuid"
"testing"
"time"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"go.uber.org/zap"
"gorm.io/driver/sqlite"
"gorm.io/gorm"
"veza-backend-api/internal/models"
)
func setupTestTrackStatsDB(t *testing.T) (*TrackService, *gorm.DB, func()) {
// Setup in-memory SQLite database
db, err := gorm.Open(sqlite.Open(":memory:"), &gorm.Config{})
require.NoError(t, err)
// Auto-migrate
err = db.AutoMigrate(
&models.User{},
&models.Track{},
&models.TrackLike{},
&models.TrackComment{},
&models.TrackPlay{},
&models.TrackShare{},
)
require.NoError(t, err)
// Create test user
user := &models.User{
ID: 1,
Username: "testuser",
Email: "test@example.com",
IsActive: true,
}
err = db.Create(user).Error
require.NoError(t, err)
// Create logger
logger := zap.NewNop()
// Create service
service := NewTrackService(db, logger, "test_uploads")
// Cleanup function
cleanup := func() {
// SQLite in-memory database doesn't need explicit cleanup
}
return service, db, cleanup
}
func TestTrackService_GetTrackStats_Success(t *testing.T) {
service, db, cleanup := setupTestTrackStatsDB(t)
defer cleanup()
ctx := context.Background()
// Create a track
track := &models.Track{
UserID: 1,
Title: "Test Track",
FilePath: "/path/to/track.mp3",
FileSize: 1024,
Format: "MP3",
Duration: 180,
IsPublic: true,
Status: models.TrackStatusCompleted,
}
err := db.Create(track).Error
require.NoError(t, err)
// Create some likes
like1 := &models.TrackLike{UserID: 1, TrackID: track.ID}
like2 := &models.TrackLike{UserID: 2, TrackID: track.ID}
err = db.Create(like1).Error
require.NoError(t, err)
err = db.Create(like2).Error
require.NoError(t, err)
// Create some comments
comment1 := &models.TrackComment{
TrackID: track.ID,
UserID: 1,
Content: "Great track!",
}
comment2 := &models.TrackComment{
TrackID: track.ID,
UserID: 2,
Content: "Love it!",
}
err = db.Create(comment1).Error
require.NoError(t, err)
err = db.Create(comment2).Error
require.NoError(t, err)
// Create some plays
play1 := &models.TrackPlay{
TrackID: track.ID,
UserID: &[]int64{1}[0],
Duration: 120,
PlayedAt: time.Now(),
}
play2 := &models.TrackPlay{
TrackID: track.ID,
UserID: &[]int64{2}[0],
Duration: 150,
PlayedAt: time.Now(),
}
play3 := &models.TrackPlay{
TrackID: track.ID,
UserID: nil, // Anonymous play
Duration: 60,
PlayedAt: time.Now(),
}
err = db.Create(play1).Error
require.NoError(t, err)
err = db.Create(play2).Error
require.NoError(t, err)
err = db.Create(play3).Error
require.NoError(t, err)
// Create a share with download permission and access count
share := &models.TrackShare{
TrackID: track.ID,
UserID: 1,
ShareToken: "test-token",
Permissions: "read,download",
AccessCount: 5,
}
err = db.Create(share).Error
require.NoError(t, err)
// Get stats
stats, err := service.GetTrackStats(ctx, track.ID)
require.NoError(t, err)
require.NotNil(t, stats)
// Verify stats
assert.Equal(t, int64(3), stats.Views) // 3 plays
assert.Equal(t, int64(2), stats.Likes) // 2 likes
assert.Equal(t, int64(2), stats.Comments) // 2 comments
assert.Equal(t, int64(330), stats.TotalPlayTime) // 120 + 150 + 60 = 330 seconds
assert.Equal(t, int64(5), stats.Downloads) // 5 downloads from share
}
func TestTrackService_GetTrackStats_TrackNotFound(t *testing.T) {
service, _, cleanup := setupTestTrackStatsDB(t)
defer cleanup()
ctx := context.Background()
// Try to get stats for non-existent track
stats, err := service.GetTrackStats(ctx, 999)
assert.Error(t, err)
assert.Nil(t, stats)
assert.Equal(t, ErrTrackNotFound, err)
}
func TestTrackService_GetTrackStats_EmptyStats(t *testing.T) {
service, db, cleanup := setupTestTrackStatsDB(t)
defer cleanup()
ctx := context.Background()
// Create a track with no interactions
track := &models.Track{
UserID: 1,
Title: "Empty Track",
FilePath: "/path/to/track.mp3",
FileSize: 1024,
Format: "MP3",
Duration: 180,
IsPublic: true,
Status: models.TrackStatusCompleted,
}
err := db.Create(track).Error
require.NoError(t, err)
// Get stats
stats, err := service.GetTrackStats(ctx, track.ID)
require.NoError(t, err)
require.NotNil(t, stats)
// Verify all stats are zero
assert.Equal(t, int64(0), stats.Views)
assert.Equal(t, int64(0), stats.Likes)
assert.Equal(t, int64(0), stats.Comments)
assert.Equal(t, int64(0), stats.TotalPlayTime)
assert.Equal(t, int64(0), stats.Downloads)
}
func TestTrackService_GetTrackStats_MultipleShares(t *testing.T) {
service, db, cleanup := setupTestTrackStatsDB(t)
defer cleanup()
ctx := context.Background()
// Create a track
track := &models.Track{
UserID: 1,
Title: "Shared Track",
FilePath: "/path/to/track.mp3",
FileSize: 1024,
Format: "MP3",
Duration: 180,
IsPublic: true,
Status: models.TrackStatusCompleted,
}
err := db.Create(track).Error
require.NoError(t, err)
// Create multiple shares with download permissions
share1 := &models.TrackShare{
TrackID: track.ID,
UserID: 1,
ShareToken: "token1",
Permissions: "read,download",
AccessCount: 3,
}
share2 := &models.TrackShare{
TrackID: track.ID,
UserID: 1,
ShareToken: "token2",
Permissions: "download",
AccessCount: 2,
}
share3 := &models.TrackShare{
TrackID: track.ID,
UserID: 1,
ShareToken: "token3",
Permissions: "read", // No download permission
AccessCount: 10,
}
err = db.Create(share1).Error
require.NoError(t, err)
err = db.Create(share2).Error
require.NoError(t, err)
err = db.Create(share3).Error
require.NoError(t, err)
// Get stats
stats, err := service.GetTrackStats(ctx, track.ID)
require.NoError(t, err)
require.NotNil(t, stats)
// Verify downloads count only shares with download permission
assert.Equal(t, int64(5), stats.Downloads) // 3 + 2 = 5 (share3 excluded)
}
func TestTrackService_GetTrackStats_SoftDeletedComments(t *testing.T) {
service, db, cleanup := setupTestTrackStatsDB(t)
defer cleanup()
ctx := context.Background()
// Create a track
track := &models.Track{
UserID: 1,
Title: "Track with Deleted Comments",
FilePath: "/path/to/track.mp3",
FileSize: 1024,
Format: "MP3",
Duration: 180,
IsPublic: true,
Status: models.TrackStatusCompleted,
}
err := db.Create(track).Error
require.NoError(t, err)
// Create comments
comment1 := &models.TrackComment{
TrackID: track.ID,
UserID: 1,
Content: "Comment 1",
}
comment2 := &models.TrackComment{
TrackID: track.ID,
UserID: 2,
Content: "Comment 2",
}
err = db.Create(comment1).Error
require.NoError(t, err)
err = db.Create(comment2).Error
require.NoError(t, err)
// Soft delete one comment
err = db.Delete(comment1).Error
require.NoError(t, err)
// Get stats
stats, err := service.GetTrackStats(ctx, track.ID)
require.NoError(t, err)
require.NotNil(t, stats)
// Verify only non-deleted comments are counted
// Note: GORM's Count by default excludes soft-deleted records
assert.Equal(t, int64(1), stats.Comments)
}