Replace the plain ASCII spinner with a Charmbracelet-style TUI panel rendered in the browser: a dark terminal card holding a rounded purple box (╭─╮╰─╯│) around a pink block-char tapir (▄▓▀█) with mint eyes (◕ ◕) and a snout that wiggles ∩→∪→~ across three cross-faded frames, plus a lipgloss-style progress bar whose mint fill grows over a dim track via an 8s CSS clip animation. Colours come from named palette consts (CharmPurple/Pink/Mint/Cream/Dim) applied as inline span styles, so the box and CSS share one source of truth. Frames are built by a small run/line helper that pads each row to a fixed interior width — an internal test asserts every box row is the same cell width so the border stays flush. Honours prefers-reduced-motion (static frame + partial bar). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
51 lines
1.6 KiB
Go
51 lines
1.6 KiB
Go
package web
|
|
|
|
import (
|
|
"regexp"
|
|
"strings"
|
|
"testing"
|
|
"unicode/utf8"
|
|
)
|
|
|
|
func TestEmbedURL(t *testing.T) {
|
|
tests := []struct {
|
|
name string
|
|
id string
|
|
wantURL string
|
|
wantOK bool
|
|
}{
|
|
{"valid 11-char id", "dQw4w9WgXcQ", "https://www.youtube-nocookie.com/embed/dQw4w9WgXcQ", true},
|
|
{"valid with dash and underscore", "a_b-cD12345", "https://www.youtube-nocookie.com/embed/a_b-cD12345", true},
|
|
{"empty", "", "", false},
|
|
{"too short", "abc", "", false},
|
|
{"too long", "dQw4w9WgXcQX", "", false},
|
|
{"invalid char", "dQw4w9WgXc!", "", false},
|
|
{"space", "dQw4w9WgX Q", "", false},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
gotURL, gotOK := embedURL(tt.id)
|
|
if gotURL != tt.wantURL || gotOK != tt.wantOK {
|
|
t.Errorf("embedURL(%q) = (%q, %v), want (%q, %v)",
|
|
tt.id, gotURL, gotOK, tt.wantURL, tt.wantOK)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
// TestTapirFrameRowsAligned asserts every box row has the same cell width once
|
|
// the inline-colour spans are stripped, so the rounded border lines up on every
|
|
// line (the panel only looks right if the right │ is flush across all rows).
|
|
func TestTapirFrameRowsAligned(t *testing.T) {
|
|
stripSpan := regexp.MustCompile(`</?span[^>]*>`)
|
|
for name, frame := range map[string]string{"f1": tapirFrameHTML1, "f2": tapirFrameHTML2, "f3": tapirFrameHTML3} {
|
|
plain := stripSpan.ReplaceAllString(frame, "")
|
|
want := tapirInteriorW + 2 // both purple side borders
|
|
for i, line := range strings.Split(plain, "\n") {
|
|
if got := utf8.RuneCountInString(line); got != want {
|
|
t.Errorf("%s line %d width = %d, want %d: %q", name, i, got, want, line)
|
|
}
|
|
}
|
|
}
|
|
}
|