mirror of
https://github.com/navidrome/navidrome.git
synced 2026-08-01 07:21:17 +00:00
refactor(lyrics): centralize lyric kind constants
The "main"/"translation"/"pronunciation" kind values were redefined in three places (ttmlLyricKind* in the TTML parser, lyricsfileKindMain in the Lyricsfile parser, and inline literals in the subsonic response builder). Define them once as model.LyricKind* (kept as wire-compatible string values) plus a LyricKindOrMain helper, and use them everywhere a kind is produced, defaulted, or filtered. No wire-facing types change.
This commit is contained in:
parent
7796faa1b2
commit
943cbc5f08
@ -45,6 +45,23 @@ type Lyrics struct {
|
||||
Synced bool `structs:"synced" json:"synced"`
|
||||
}
|
||||
|
||||
// Lyric kinds, as defined by the OpenSubsonic songLyrics v2 contract. These are
|
||||
// the canonical wire values; keep them in sync with the spec.
|
||||
const (
|
||||
LyricKindMain = "main"
|
||||
LyricKindTranslation = "translation"
|
||||
LyricKindPronunciation = "pronunciation"
|
||||
)
|
||||
|
||||
// LyricKindOrMain returns kind, defaulting to LyricKindMain when empty. A blank
|
||||
// kind means an untyped (single-track) lyric, which the contract treats as main.
|
||||
func LyricKindOrMain(kind string) string {
|
||||
if strings.TrimSpace(kind) == "" {
|
||||
return LyricKindMain
|
||||
}
|
||||
return kind
|
||||
}
|
||||
|
||||
// support the standard [mm:ss.mm], as well as [hh:*] and [*.mmm]
|
||||
const timeRegexString = `\[([0-9]{1,2}:)?([0-9]{1,2}):([0-9]{1,2})(\.[0-9]{1,3})?\]`
|
||||
|
||||
|
||||
@ -21,10 +21,7 @@ const (
|
||||
defaultTTMLSubFrameRate = 1.0
|
||||
defaultTTMLTickRate = 1.0
|
||||
|
||||
ttmlLyricKindMain = "main"
|
||||
ttmlLyricKindTranslation = "translation"
|
||||
ttmlLyricKindPronunciation = "pronunciation"
|
||||
ttmlBackgroundAgentPrefix = "__nd_bg__|"
|
||||
ttmlBackgroundAgentPrefix = "__nd_bg__|"
|
||||
)
|
||||
|
||||
var offsetTimeRegex = regexp.MustCompile(`^([0-9]+(?:\.[0-9]+)?)(h|m|s|ms|f|t)$`)
|
||||
@ -157,9 +154,9 @@ func (p *ttmlParser) parseElement(start xml.StartElement, parent ttmlTimingConte
|
||||
|
||||
switch local {
|
||||
case "translation":
|
||||
return p.parseMetadataTrack(start, parent, ttmlLyricKindTranslation)
|
||||
return p.parseMetadataTrack(start, parent, LyricKindTranslation)
|
||||
case "transliteration":
|
||||
return p.parseMetadataTrack(start, parent, ttmlLyricKindPronunciation)
|
||||
return p.parseMetadataTrack(start, parent, LyricKindPronunciation)
|
||||
case "agent":
|
||||
return p.parseAgentDefinition(start)
|
||||
}
|
||||
@ -582,15 +579,15 @@ func (p *ttmlParser) toLyricList() LyricList {
|
||||
continue
|
||||
}
|
||||
res = append(res, p.finalizeLyrics(Lyrics{
|
||||
Kind: ttmlLyricKindMain,
|
||||
Kind: LyricKindMain,
|
||||
Lang: lang,
|
||||
Line: lines,
|
||||
Synced: linesAreSynced(lines),
|
||||
}))
|
||||
}
|
||||
|
||||
res = append(res, p.buildMetadataLyrics(ttmlLyricKindTranslation, p.translationLangOrder, p.translationEntriesByLg)...)
|
||||
res = append(res, p.buildMetadataLyrics(ttmlLyricKindPronunciation, p.pronunciationLangOrder, p.pronunciationEntriesByLg)...)
|
||||
res = append(res, p.buildMetadataLyrics(LyricKindTranslation, p.translationLangOrder, p.translationEntriesByLg)...)
|
||||
res = append(res, p.buildMetadataLyrics(LyricKindPronunciation, p.pronunciationLangOrder, p.pronunciationEntriesByLg)...)
|
||||
return res
|
||||
}
|
||||
|
||||
@ -854,12 +851,12 @@ func (p *ttmlParser) addMetadataEntry(kind string, lang string, entry ttmlMetada
|
||||
p.metadataSeq++
|
||||
|
||||
switch kind {
|
||||
case ttmlLyricKindTranslation:
|
||||
case LyricKindTranslation:
|
||||
if _, ok := p.translationEntriesByLg[lang]; !ok {
|
||||
p.translationLangOrder = append(p.translationLangOrder, lang)
|
||||
}
|
||||
p.translationEntriesByLg[lang] = append(p.translationEntriesByLg[lang], entry)
|
||||
case ttmlLyricKindPronunciation:
|
||||
case LyricKindPronunciation:
|
||||
if _, ok := p.pronunciationEntriesByLg[lang]; !ok {
|
||||
p.pronunciationLangOrder = append(p.pronunciationLangOrder, lang)
|
||||
}
|
||||
|
||||
@ -35,7 +35,7 @@ func ParseLyricsfile(text string) (LyricList, error) {
|
||||
DisplayArtist: str.SanitizeText(doc.Metadata.Artist),
|
||||
DisplayTitle: str.SanitizeText(doc.Metadata.Title),
|
||||
Lang: normalizeLyricsfileLang(doc.Metadata.Language),
|
||||
Kind: lyricsfileKindMain,
|
||||
Kind: LyricKindMain,
|
||||
}
|
||||
if doc.Metadata.OffsetMs != 0 {
|
||||
off := doc.Metadata.OffsetMs
|
||||
@ -62,10 +62,7 @@ func ParseLyricsfile(text string) (LyricList, error) {
|
||||
return LyricList{NormalizeLyrics(lyrics)}, nil
|
||||
}
|
||||
|
||||
const (
|
||||
lyricsfileVersion = "1.0"
|
||||
lyricsfileKindMain = "main"
|
||||
)
|
||||
const lyricsfileVersion = "1.0"
|
||||
|
||||
type lyricsfileDocument struct {
|
||||
Version string `yaml:"version"`
|
||||
|
||||
@ -581,11 +581,7 @@ func buildStructuredLyric(mf *model.MediaFile, lyrics model.Lyrics, enhanced boo
|
||||
}
|
||||
|
||||
if enhanced {
|
||||
kind := strings.TrimSpace(lyrics.Kind)
|
||||
if kind == "" {
|
||||
kind = "main"
|
||||
}
|
||||
structured.Kind = kind
|
||||
structured.Kind = model.LyricKindOrMain(lyrics.Kind)
|
||||
if len(cueLines) > 0 && len(responseAgents) > 0 {
|
||||
structured.Agents = responseAgents
|
||||
}
|
||||
@ -637,10 +633,9 @@ func buildLyricsList(mf *model.MediaFile, lyricsList model.LyricList, enhanced b
|
||||
if enhanced {
|
||||
filtered = lyricsList
|
||||
} else {
|
||||
// Without enhanced, only return "main" kind entries
|
||||
// Without enhanced, only return main-kind entries (a blank kind is main).
|
||||
for _, l := range lyricsList {
|
||||
kind := strings.TrimSpace(l.Kind)
|
||||
if kind == "" || kind == "main" {
|
||||
if model.LyricKindOrMain(l.Kind) == model.LyricKindMain {
|
||||
filtered = append(filtered, l)
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user