381 lines
9 KiB
Go
381 lines
9 KiB
Go
package services
|
|
|
|
import (
|
|
"context"
|
|
"fmt"
|
|
"testing"
|
|
"time"
|
|
|
|
"go.uber.org/zap"
|
|
)
|
|
|
|
func TestNewCDNService(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
|
|
if service == nil {
|
|
t.Error("NewCDNService() returned nil")
|
|
}
|
|
if service.logger == nil {
|
|
t.Error("NewCDNService() returned service with nil logger")
|
|
}
|
|
if service.config.Provider != CDNProviderCloudFront {
|
|
t.Errorf("NewCDNService() provider = %v, want %v", service.config.Provider, CDNProviderCloudFront)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GetURL(t *testing.T) {
|
|
tests := []struct {
|
|
name string
|
|
config CDNConfig
|
|
path string
|
|
expected string
|
|
}{
|
|
{
|
|
name: "CloudFront enabled",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
path: "/audio/track123.mp3",
|
|
expected: "https://d1234567890.cloudfront.net/audio/track123.mp3",
|
|
},
|
|
{
|
|
name: "CDN disabled",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: false,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
path: "/audio/track123.mp3",
|
|
expected: "/audio/track123.mp3",
|
|
},
|
|
{
|
|
name: "None provider",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderNone,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
path: "/audio/track123.mp3",
|
|
expected: "/audio/track123.mp3",
|
|
},
|
|
{
|
|
name: "Path without leading slash",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
path: "audio/track123.mp3",
|
|
expected: "https://d1234567890.cloudfront.net/audio/track123.mp3",
|
|
},
|
|
}
|
|
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
service := NewCDNService(tt.config)
|
|
result := service.GetURL(tt.path)
|
|
if result != tt.expected {
|
|
t.Errorf("GetURL(%s) = %s, want %s", tt.path, result, tt.expected)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GetAssetURL(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
url := service.GetAssetURL("js", "app.js")
|
|
|
|
expected := "https://d1234567890.cloudfront.net/assets/js/app.js"
|
|
if url != expected {
|
|
t.Errorf("GetAssetURL() = %s, want %s", url, expected)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GetAudioURL(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
url := service.GetAudioURL("track-123", "audio.mp3")
|
|
|
|
expected := "https://d1234567890.cloudfront.net/audio/track-123/audio.mp3"
|
|
if url != expected {
|
|
t.Errorf("GetAudioURL() = %s, want %s", url, expected)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GetHLSURL(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
url := service.GetHLSURL("track-123", "master.m3u8")
|
|
|
|
expected := "https://d1234567890.cloudfront.net/hls/track-123/master.m3u8"
|
|
if url != expected {
|
|
t.Errorf("GetHLSURL() = %s, want %s", url, expected)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GetImageURL(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
url := service.GetImageURL("avatars", "user-123.jpg")
|
|
|
|
expected := "https://d1234567890.cloudfront.net/images/avatars/user-123.jpg"
|
|
if url != expected {
|
|
t.Errorf("GetImageURL() = %s, want %s", url, expected)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_IsEnabled(t *testing.T) {
|
|
tests := []struct {
|
|
name string
|
|
config CDNConfig
|
|
expected bool
|
|
}{
|
|
{
|
|
name: "enabled CloudFront",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
expected: true,
|
|
},
|
|
{
|
|
name: "disabled",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
Enabled: false,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
expected: false,
|
|
},
|
|
{
|
|
name: "none provider",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderNone,
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
expected: false,
|
|
},
|
|
}
|
|
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
service := NewCDNService(tt.config)
|
|
result := service.IsEnabled()
|
|
if result != tt.expected {
|
|
t.Errorf("IsEnabled() = %v, want %v", result, tt.expected)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GetProvider(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderCloudflare,
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
provider := service.GetProvider()
|
|
|
|
if provider != CDNProviderCloudflare {
|
|
t.Errorf("GetProvider() = %v, want %v", provider, CDNProviderCloudflare)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GetBaseURL(t *testing.T) {
|
|
expectedURL := "https://d1234567890.cloudfront.net"
|
|
config := CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: expectedURL,
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
baseURL := service.GetBaseURL()
|
|
|
|
if baseURL != expectedURL {
|
|
t.Errorf("GetBaseURL() = %s, want %s", baseURL, expectedURL)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GetCacheHeaders(t *testing.T) {
|
|
tests := []struct {
|
|
name string
|
|
config CDNConfig
|
|
expectedHeader string
|
|
}{
|
|
{
|
|
name: "CloudFront enabled",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
expectedHeader: "public, max-age=31536000, immutable",
|
|
},
|
|
{
|
|
name: "Cloudflare enabled",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderCloudflare,
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
expectedHeader: "public, max-age=31536000, immutable",
|
|
},
|
|
{
|
|
name: "CDN disabled",
|
|
config: CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
Enabled: false,
|
|
Logger: zap.NewNop(),
|
|
},
|
|
expectedHeader: "no-cache",
|
|
},
|
|
}
|
|
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
service := NewCDNService(tt.config)
|
|
headers := service.GetCacheHeaders()
|
|
|
|
cacheControl := headers["Cache-Control"]
|
|
if cacheControl != tt.expectedHeader {
|
|
t.Errorf("GetCacheHeaders() Cache-Control = %s, want %s", cacheControl, tt.expectedHeader)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCDNService_InvalidateCache(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderGeneric,
|
|
BaseURL: "https://cdn.example.com",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
ctx := context.Background()
|
|
|
|
paths := []string{"/audio/track1.mp3", "/audio/track2.mp3"}
|
|
err := service.InvalidateCache(ctx, paths)
|
|
if err != nil {
|
|
t.Errorf("InvalidateCache() error = %v", err)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_BatchInvalidate(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderGeneric,
|
|
BaseURL: "https://cdn.example.com",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
ctx := context.Background()
|
|
|
|
paths := make([]string, 25)
|
|
for i := 0; i < 25; i++ {
|
|
paths[i] = fmt.Sprintf("/audio/track%d.mp3", i)
|
|
}
|
|
|
|
err := service.BatchInvalidate(ctx, paths, 10)
|
|
if err != nil {
|
|
t.Errorf("BatchInvalidate() error = %v", err)
|
|
}
|
|
}
|
|
|
|
func TestCDNService_GenerateSignedURL(t *testing.T) {
|
|
config := CDNConfig{
|
|
Provider: CDNProviderCloudFront,
|
|
BaseURL: "https://d1234567890.cloudfront.net",
|
|
Enabled: true,
|
|
Logger: zap.NewNop(),
|
|
}
|
|
|
|
service := NewCDNService(config)
|
|
url, err := service.GenerateSignedURL("/audio/track123.mp3", time.Hour)
|
|
if err != nil {
|
|
t.Errorf("GenerateSignedURL() error = %v", err)
|
|
}
|
|
if url == "" {
|
|
t.Error("GenerateSignedURL() returned empty URL")
|
|
}
|
|
}
|
|
|
|
// Note: Full integration tests would require:
|
|
// 1. Real CDN provider credentials
|
|
// 2. Actual CDN distribution/zone
|
|
// 3. Verification of cache invalidation
|
|
// 4. Testing of signed URL generation
|
|
//
|
|
// Example integration test structure:
|
|
// func TestCDNService_InvalidateCache_Integration(t *testing.T) {
|
|
// // Skip if CDN not configured
|
|
// if os.Getenv("CDN_ENABLED") != "true" {
|
|
// t.Skip("CDN not configured")
|
|
// }
|
|
//
|
|
// config := CDNConfig{
|
|
// Provider: CDNProviderCloudFront,
|
|
// BaseURL: os.Getenv("CDN_BASE_URL"),
|
|
// DistributionID: os.Getenv("CDN_DISTRIBUTION_ID"),
|
|
// APIKey: os.Getenv("CDN_API_KEY"),
|
|
// Enabled: true,
|
|
// Logger: zap.NewNop(),
|
|
// }
|
|
//
|
|
// service := NewCDNService(config)
|
|
// ctx := context.Background()
|
|
//
|
|
// paths := []string{"/test/path1.mp3", "/test/path2.mp3"}
|
|
// err := service.InvalidateCache(ctx, paths)
|
|
// if err != nil {
|
|
// t.Fatalf("InvalidateCache() error = %v", err)
|
|
// }
|
|
//
|
|
// // Verify invalidation was successful (check CDN API)
|
|
// }
|