mirror of
https://github.com/issadarkthing/gomu.git
synced 2025-04-26 13:49:21 +08:00
176 lines
4.4 KiB
Go
176 lines
4.4 KiB
Go
package lyric
|
|
|
|
import (
|
|
"encoding/json"
|
|
"errors"
|
|
"fmt"
|
|
"net/http"
|
|
"net/url"
|
|
"strconv"
|
|
"strings"
|
|
|
|
"github.com/ztrue/tracerr"
|
|
)
|
|
|
|
// tagNetease is the tag get from netease
|
|
type tagNetease struct {
|
|
Album string `json:"album"`
|
|
Artist []string `json:"artist"`
|
|
ID int64 `json:"id"`
|
|
LyricID int64 `json:"lyric_id"`
|
|
Name string `json:"name"`
|
|
PicID string `json:"pic_id"`
|
|
Source string `json:"source"`
|
|
URLID int64 `json:"url_id"`
|
|
}
|
|
|
|
// tagKugou is the tag get from kugou
|
|
type tagKugou struct {
|
|
Album string `json:"album"`
|
|
Artist []string `json:"artist"`
|
|
ID string `json:"id"`
|
|
LyricID string `json:"lyric_id"`
|
|
Name string `json:"name"`
|
|
PicID string `json:"pic_id"`
|
|
Source string `json:"source"`
|
|
URLID string `json:"url_id"`
|
|
}
|
|
|
|
// tagLyric is the lyric json get from both netease and kugou
|
|
type tagLyric struct {
|
|
Lyric string `json:"lyric"`
|
|
Tlyric string `json:"tlyric"`
|
|
}
|
|
|
|
type LyricFetcherCn struct{}
|
|
|
|
// LyricOptions queries available song lyrics. It returns slice of SongTag
|
|
func (cn LyricFetcherCn) LyricOptions(search string) ([]*SongTag, error) {
|
|
|
|
serviceProvider := "netease"
|
|
results, err := getLyricOptionsCnByProvider(search, serviceProvider)
|
|
if err != nil {
|
|
return nil, tracerr.Wrap(err)
|
|
}
|
|
serviceProvider = "kugou"
|
|
results2, err := getLyricOptionsCnByProvider(search, serviceProvider)
|
|
if err != nil {
|
|
return nil, tracerr.Wrap(err)
|
|
}
|
|
|
|
results = append(results, results2...)
|
|
|
|
return results, err
|
|
}
|
|
|
|
// LyricFetch should receive songTag that was returned from getLyricOptions
|
|
// and returns lyric of the queried song.
|
|
func (cn LyricFetcherCn) LyricFetch(songTag *SongTag) (lyricString string, err error) {
|
|
|
|
urlSearch := "http://api.sunyj.xyz"
|
|
|
|
params := url.Values{}
|
|
params.Add("site", songTag.ServiceProvider)
|
|
params.Add("lyric", songTag.LyricID)
|
|
resp, err := http.Get(urlSearch + "?" + params.Encode())
|
|
if err != nil {
|
|
return "", tracerr.Wrap(err)
|
|
}
|
|
defer resp.Body.Close()
|
|
|
|
if resp.StatusCode != 200 {
|
|
return "", fmt.Errorf("http response error: %d", resp.StatusCode)
|
|
}
|
|
|
|
var tagLyric tagLyric
|
|
err = json.NewDecoder(resp.Body).Decode(&tagLyric)
|
|
if err != nil {
|
|
return "", tracerr.Wrap(err)
|
|
}
|
|
lyricString = tagLyric.Lyric
|
|
if lyricString == "" {
|
|
return "", errors.New("no lyric available")
|
|
}
|
|
|
|
if looksLikeLRC(lyricString) {
|
|
lyricString = cleanLRC(lyricString)
|
|
return lyricString, nil
|
|
}
|
|
return "", errors.New("lyric not compatible")
|
|
}
|
|
|
|
// getLyricOptionsCnByProvider do the query by provider
|
|
func getLyricOptionsCnByProvider(search string, serviceProvider string) (resultTags []*SongTag, err error) {
|
|
|
|
urlSearch := "http://api.sunyj.xyz"
|
|
|
|
params := url.Values{}
|
|
params.Add("site", serviceProvider)
|
|
params.Add("search", search)
|
|
resp, err := http.Get(urlSearch + "?" + params.Encode())
|
|
if err != nil {
|
|
return nil, tracerr.Wrap(err)
|
|
}
|
|
defer resp.Body.Close()
|
|
|
|
if resp.StatusCode != 200 {
|
|
return nil, fmt.Errorf("http response error: %d", resp.StatusCode)
|
|
}
|
|
|
|
switch serviceProvider {
|
|
case "kugou":
|
|
var tagKugou []tagKugou
|
|
err = json.NewDecoder(resp.Body).Decode(&tagKugou)
|
|
if err != nil {
|
|
return nil, tracerr.Wrap(err)
|
|
}
|
|
|
|
for _, v := range tagKugou {
|
|
resultArtist := strings.Join(v.Artist, " ")
|
|
songName := v.Name
|
|
resultAlbum := v.Album
|
|
songTitleForPopup := fmt.Sprintf("%s - %s : %s", resultArtist, songName, resultAlbum)
|
|
songTag := &SongTag{
|
|
Artist: resultArtist,
|
|
Title: v.Name,
|
|
Album: v.Album,
|
|
TitleForPopup: songTitleForPopup,
|
|
LangExt: "zh-CN",
|
|
ServiceProvider: serviceProvider,
|
|
SongID: v.ID,
|
|
LyricID: v.LyricID,
|
|
}
|
|
resultTags = append(resultTags, songTag)
|
|
}
|
|
|
|
case "netease":
|
|
var tagNetease []tagNetease
|
|
err = json.NewDecoder(resp.Body).Decode(&tagNetease)
|
|
if err != nil {
|
|
return nil, tracerr.Wrap(err)
|
|
}
|
|
|
|
for _, v := range tagNetease {
|
|
resultArtist := strings.Join(v.Artist, " ")
|
|
songName := v.Name
|
|
resultAlbum := v.Album
|
|
songTitleForPopup := fmt.Sprintf("%s - %s : %s", resultArtist, songName, resultAlbum)
|
|
songTag := &SongTag{
|
|
Artist: resultArtist,
|
|
Title: v.Name,
|
|
Album: v.Album,
|
|
URL: "",
|
|
TitleForPopup: songTitleForPopup,
|
|
LangExt: "zh-CN",
|
|
ServiceProvider: serviceProvider,
|
|
SongID: strconv.FormatInt(v.ID, 10),
|
|
LyricID: strconv.FormatInt(v.LyricID, 10),
|
|
}
|
|
resultTags = append(resultTags, songTag)
|
|
}
|
|
|
|
}
|
|
|
|
return resultTags, nil
|
|
}
|