sub-cli/internal/format/lrc/converter_test.go
2025-04-23 19:22:41 +08:00

181 lines
5.3 KiB
Go

package lrc
import (
"os"
"path/filepath"
"strings"
"testing"
"sub-cli/internal/model"
)
func TestConvertToSubtitle(t *testing.T) {
// Create a temporary test file
content := `[ti:Test LRC File]
[ar:Test Artist]
[00:01.00]This is the first line.
[00:05.00]This is the second line.
`
tempDir := t.TempDir()
testFile := filepath.Join(tempDir, "test.lrc")
if err := os.WriteFile(testFile, []byte(content), 0644); err != nil {
t.Fatalf("Failed to create test file: %v", err)
}
// Convert to subtitle
subtitle, err := ConvertToSubtitle(testFile)
if err != nil {
t.Fatalf("ConvertToSubtitle failed: %v", err)
}
// Check result
if subtitle.Format != "lrc" {
t.Errorf("Expected format 'lrc', got '%s'", subtitle.Format)
}
if len(subtitle.Entries) != 2 {
t.Errorf("Expected 2 entries, got %d", len(subtitle.Entries))
}
// Check first entry
if subtitle.Entries[0].StartTime.Hours != 0 || subtitle.Entries[0].StartTime.Minutes != 0 ||
subtitle.Entries[0].StartTime.Seconds != 1 || subtitle.Entries[0].StartTime.Milliseconds != 0 {
t.Errorf("First entry start time: expected 00:01.00, got %+v", subtitle.Entries[0].StartTime)
}
if subtitle.Entries[0].Text != "This is the first line." {
t.Errorf("First entry text: expected 'This is the first line.', got '%s'", subtitle.Entries[0].Text)
}
// Check metadata conversion
if subtitle.Title != "Test LRC File" {
t.Errorf("Expected title 'Test LRC File', got '%s'", subtitle.Title)
}
if subtitle.Metadata["ar"] != "Test Artist" {
t.Errorf("Expected artist metadata 'Test Artist', got '%s'", subtitle.Metadata["ar"])
}
}
func TestConvertFromSubtitle(t *testing.T) {
// Create a subtitle
subtitle := model.NewSubtitle()
subtitle.Format = "lrc"
subtitle.Title = "Test LRC File"
subtitle.Metadata["ar"] = "Test Artist"
entry1 := model.NewSubtitleEntry()
entry1.Index = 1
entry1.StartTime = model.Timestamp{Hours: 0, Minutes: 0, Seconds: 1, Milliseconds: 0}
entry1.EndTime = model.Timestamp{Hours: 0, Minutes: 0, Seconds: 4, Milliseconds: 0}
entry1.Text = "This is the first line."
entry2 := model.NewSubtitleEntry()
entry2.Index = 2
entry2.StartTime = model.Timestamp{Hours: 0, Minutes: 0, Seconds: 5, Milliseconds: 0}
entry2.EndTime = model.Timestamp{Hours: 0, Minutes: 0, Seconds: 8, Milliseconds: 0}
entry2.Text = "This is the second line."
subtitle.Entries = append(subtitle.Entries, entry1, entry2)
// Convert to LRC
tempDir := t.TempDir()
outputFile := filepath.Join(tempDir, "output.lrc")
err := ConvertFromSubtitle(subtitle, outputFile)
if err != nil {
t.Fatalf("ConvertFromSubtitle failed: %v", err)
}
// Verify by reading the file directly
content, err := os.ReadFile(outputFile)
if err != nil {
t.Fatalf("Failed to read output file: %v", err)
}
// Check content
contentStr := string(content)
// Check metadata
if !strings.Contains(contentStr, "[ti:Test LRC File]") {
t.Errorf("Expected title metadata in output, not found")
}
if !strings.Contains(contentStr, "[ar:Test Artist]") {
t.Errorf("Expected artist metadata in output, not found")
}
// Check timeline entries
if !strings.Contains(contentStr, "[00:01.000]This is the first line.") {
t.Errorf("Expected first timeline entry in output, not found")
}
if !strings.Contains(contentStr, "[00:05.000]This is the second line.") {
t.Errorf("Expected second timeline entry in output, not found")
}
}
func TestConvertToSubtitle_FileError(t *testing.T) {
// Test with non-existent file
_, err := ConvertToSubtitle("/nonexistent/file.lrc")
if err == nil {
t.Error("Expected error when converting non-existent file, got nil")
}
}
func TestConvertToSubtitle_EdgeCases(t *testing.T) {
// Test with empty lyrics (no content/timeline)
tempDir := t.TempDir()
emptyLyricsFile := filepath.Join(tempDir, "empty_lyrics.lrc")
content := `[ti:Test LRC File]
[ar:Test Artist]
`
if err := os.WriteFile(emptyLyricsFile, []byte(content), 0644); err != nil {
t.Fatalf("Failed to create empty lyrics test file: %v", err)
}
subtitle, err := ConvertToSubtitle(emptyLyricsFile)
if err != nil {
t.Fatalf("ConvertToSubtitle failed on empty lyrics: %v", err)
}
if len(subtitle.Entries) != 0 {
t.Errorf("Expected 0 entries for empty lyrics, got %d", len(subtitle.Entries))
}
if subtitle.Title != "Test LRC File" {
t.Errorf("Expected title 'Test LRC File', got '%s'", subtitle.Title)
}
// Test with more content than timeline entries
moreContentFile := filepath.Join(tempDir, "more_content.lrc")
content = `[ti:Test LRC File]
[00:01.00]This has a timestamp.
This doesn't have a timestamp but is content.
`
if err := os.WriteFile(moreContentFile, []byte(content), 0644); err != nil {
t.Fatalf("Failed to create more content test file: %v", err)
}
subtitle, err = ConvertToSubtitle(moreContentFile)
if err != nil {
t.Fatalf("ConvertToSubtitle failed on file with more content than timestamps: %v", err)
}
if len(subtitle.Entries) != 1 {
t.Errorf("Expected 1 entry (only the one with timestamp), got %d", len(subtitle.Entries))
}
}
func TestConvertFromSubtitle_FileError(t *testing.T) {
// Create simple subtitle
subtitle := model.NewSubtitle()
subtitle.Entries = append(subtitle.Entries, model.NewSubtitleEntry())
// Test with invalid path
err := ConvertFromSubtitle(subtitle, "/nonexistent/directory/file.lrc")
if err == nil {
t.Error("Expected error when converting to invalid path, got nil")
}
}