Files
u-desktop/horoscope.go

173 lines
4.2 KiB
Go

package main
import (
"encoding/json"
"fmt"
"log"
"os"
"path/filepath"
"strings"
"time"
)
const tianapiStarURL = "https://apis.tianapi.com/star/index"
var zodiacToSign = map[string]string{
"白羊座": "aries", "金牛座": "taurus", "双子座": "gemini", "巨蟹座": "cancer",
"狮子座": "leo", "处女座": "virgo", "天秤座": "libra", "天蝎座": "scorpio",
"射手座": "sagittarius", "摩羯座": "capricorn", "水瓶座": "aquarius", "双鱼座": "pisces",
}
type tianapiStarResp struct {
Code int `json:"code"`
Result struct {
List []struct {
Type string `json:"type"`
Content string `json:"content"`
} `json:"list"`
} `json:"result"`
}
type horoscopeInfo struct {
Zodiac string `json:"zodiac"`
Date string `json:"date"`
All string `json:"all"`
Love string `json:"love"`
Work string `json:"work"`
Money string `json:"money"`
Health string `json:"health"`
LuckyColor string `json:"luckyColor"`
LuckyNum string `json:"luckyNum"`
Noble string `json:"noble"`
Summary string `json:"summary"`
}
func horoscopeCachePath() string {
return filepath.Join(configDir(), "horoscope_cache.json")
}
func saveHoroscopeCache(info *horoscopeInfo) {
info.Date = time.Now().Format("2006-01-02")
data, _ := json.Marshal(info)
os.WriteFile(horoscopeCachePath(), data, 0644)
}
func loadHoroscopeCache() *horoscopeInfo {
data, err := os.ReadFile(horoscopeCachePath())
if err != nil {
return nil
}
var info horoscopeInfo
if json.Unmarshal(data, &info) != nil {
return nil
}
return &info
}
func fetchHoroscope(zodiac string) *horoscopeInfo {
sign := zodiacToSign[zodiac]
if sign == "" {
sign = "sagittarius"
}
key := loadConfig().tianapiKey()
if key == "" {
log.Println("未配置天聚数行 API Key")
return nil
}
url := fmt.Sprintf("%s?key=%s&astro=%s", tianapiStarURL, key, sign)
data, err := httpGet(url)
if err != nil {
log.Println("星座运势请求失败:", err)
return nil
}
var resp tianapiStarResp
if json.Unmarshal(data, &resp) != nil || resp.Code != 200 {
log.Println("星座运势解析失败:", string(data))
return nil
}
info := &horoscopeInfo{Zodiac: zodiac}
for _, item := range resp.Result.List {
switch item.Type {
case "综合指数":
info.All = strings.TrimSuffix(item.Content, "%")
case "爱情指数":
info.Love = strings.TrimSuffix(item.Content, "%")
case "工作指数":
info.Work = strings.TrimSuffix(item.Content, "%")
case "财运指数":
info.Money = strings.TrimSuffix(item.Content, "%")
case "健康指数":
info.Health = strings.TrimSuffix(item.Content, "%")
case "幸运颜色":
info.LuckyColor = item.Content
case "幸运数字":
info.LuckyNum = item.Content
case "贵人星座":
info.Noble = item.Content
case "今日概述":
info.Summary = strings.TrimSpace(item.Content)
}
}
log.Printf("星座运势已获取: %s", zodiac)
return info
}
func pushHoroscopeInfo(info *horoscopeInfo) {
jsonData, _ := json.Marshal(info)
log.Printf("星座运势JS: %s", string(jsonData[:min(len(jsonData), 120)]))
js := fmt.Sprintf(`if(window.updateHoroscopeFromGo) window.updateHoroscopeFromGo(%s)`, string(jsonData))
evalJS(js)
}
func pushHoroscope(zodiac string) {
info := fetchHoroscope(zodiac)
if info == nil {
log.Println("星座运势: fetchHoroscope返回nil")
return
}
saveHoroscopeCache(info)
pushHoroscopeInfo(info)
}
func horoscopeLoop() {
cfg := loadConfig()
cached := loadHoroscopeCache()
if cached != nil && !cfg.HideZodiac {
pushHoroscopeInfo(cached)
}
time.Sleep(5 * time.Second)
cfg = loadConfig()
today := time.Now().Format("2006-01-02")
if !cfg.HideZodiac && !(cached != nil && cached.Date == today && cached.Zodiac == cfg.Zodiac) {
for i := 0; i < 3; i++ {
pushHoroscope(cfg.Zodiac)
cached := loadHoroscopeCache()
if cached != nil && cached.Date == time.Now().Format("2006-01-02") && cached.Zodiac == cfg.Zodiac {
break
}
time.Sleep(30 * time.Second)
}
}
ticker := time.NewTicker(24 * time.Hour)
for range ticker.C {
cfg := loadConfig()
if !cfg.HideZodiac {
pushHoroscope(cfg.Zodiac)
}
}
}
func triggerHoroscopeRefresh(zodiac string) {
go func() {
pushHoroscope(zodiac)
}()
}