Files
tver/internal/media/path.go
T

62 lines
1.4 KiB
Go

package media
import (
"path/filepath"
"strings"
"unicode"
)
const maxComponentRunes = 80
const maxComponentBytes = 60
// RelativeVideoPath は worker と web が共有する保存先の相対パスを返す。
func RelativeVideoPath(seriesTitle, episodeTitle, episodeID string) string {
series := sanitizeComponent(seriesTitle)
episode := sanitizeComponent(episodeTitle)
id := sanitizeComponent(episodeID)
return filepath.Join(series, series+" "+episode+" ["+id+"].mp4")
}
func sanitizeComponent(value string) string {
var result []rune
lastReplacement := false
for _, r := range value {
invalid := unicode.IsControl(r) || strings.ContainsRune(`<>:"/\|?*`, r)
if invalid {
if !lastReplacement {
result = append(result, '_')
lastReplacement = true
}
continue
}
if unicode.IsSpace(r) {
r = ' '
}
result = append(result, r)
lastReplacement = false
}
clean := strings.Trim(string(result), " .")
if clean == "" || clean == "." || clean == ".." {
return "名称未設定"
}
runes := []rune(clean)
if len(runes) > maxComponentRunes {
runes = runes[:maxComponentRunes]
}
var limited []rune
bytes := 0
for _, r := range runes {
size := len(string(r))
if bytes+size > maxComponentBytes {
break
}
limited = append(limited, r)
bytes += size
}
clean = strings.Trim(string(limited), " .")
if clean == "" || clean == "." || clean == ".." {
return "名称未設定"
}
return clean
}