import { computed, ref, readonly } from 'vue' const defaultSubmissionGuidelines = `1. 投稿时无需加入书名号 2. 除DJ外,其他类型歌曲均接收(包括小语种) 3. 禁止投递含有违规内容的歌曲 4. 点播的歌曲将由管理员进行审核 5. 审核通过后将安排在播放时段播出 6. 提交即表明我已阅读投稿须知并已知该歌曲有概率无法播出 7. 本系统仅提供音乐搜索和播放管理功能,不存储任何音乐文件。所有音乐内容均来自第三方音乐平台,版权归原平台及版权方所有。用户点歌时请确保遵守相关音乐平台的服务条款,尊重音乐作品版权。我们鼓励用户支持正版音乐,在官方平台购买和收听喜爱的音乐作品。 8. 最终解释权归广播站所有` // 站点配置状态 const siteConfig = ref({ siteTitle: '', siteLogoUrl: '', schoolLogoHomeUrl: '', schoolLogoPrintUrl: '', siteDescription: '', siteVersion: '', submissionGuidelines: '', icpNumber: '', gonganNumber: '', defaultTheme: null, enabledThemes: null, statisticsCode: '', statisticsCodeEnabled: false }) const isLoaded = ref(false) const isLoading = ref(false) export const useSiteConfig = () => { // 获取站点配置 const fetchSiteConfig = async () => { if (isLoading.value) return try { isLoading.value = true const response = await fetch('/api/site-config') if (!response.ok) { throw new Error('获取站点配置失败') } const data = await response.json() siteConfig.value = data isLoaded.value = true } catch (error) { console.error('获取站点配置失败:', error) // 使用默认配置 siteConfig.value = { siteTitle: '校园广播站点歌系统', siteLogoUrl: '/images/site-logo.png', schoolLogoHomeUrl: '/images/school-logo-black.png', schoolLogoPrintUrl: '/images/school-logo-transparent.png', siteDescription: '校园广播站点歌系统 - 让你的声音被听见', siteVersion: '', submissionGuidelines: defaultSubmissionGuidelines, icpNumber: '', gonganNumber: '', enableReplayRequests: false, enableCollaborativeSubmission: true, enableSubmissionRemarks: false, defaultTheme: 'ClassicDark', enabledThemes: '["System","ClassicDark","ClassicLight","ModernLight"]', statisticsCode: '', statisticsCodeEnabled: false } isLoaded.value = true } finally { isLoading.value = false } } // 计算属性 const siteTitle = computed(() => siteConfig.value.siteTitle || '校园广播站点歌系统') const logoUrl = computed(() => { const url = siteConfig.value.siteLogoUrl return (!url || url === '/favicon.ico') ? '/images/site-logo.png' : url }) const schoolLogoHomeUrl = computed(() => { const raw = (siteConfig.value.schoolLogoHomeUrl || '').trim() const fallback = '/images/school-logo-black.png' if (!raw) return fallback if (raw === '/images/school-logo-white.png' || raw === '/images/school-logo-black.png') return fallback return raw }) const schoolLogoPrintUrl = computed(() => siteConfig.value.schoolLogoPrintUrl || '/images/school-logo.png') const description = computed( () => siteConfig.value.siteDescription || '校园广播站点歌系统 - 让你的声音被听见' ) const siteVersion = computed(() => (siteConfig.value.siteVersion || '').trim()) const guidelines = computed( () => siteConfig.value.submissionGuidelines || defaultSubmissionGuidelines ) const icp = computed(() => siteConfig.value.icpNumber || '') const gonganNumber = computed(() => siteConfig.value.gonganNumber || '') const enableReplayRequests = computed(() => siteConfig.value.enableReplayRequests || false) const enableCollaborativeSubmission = computed( () => siteConfig.value.enableCollaborativeSubmission !== false ) const enableSubmissionRemarks = computed(() => siteConfig.value.enableSubmissionRemarks === true) const smtpEnabled = computed(() => !!siteConfig.value.smtpEnabled) const statisticsCode = computed(() => siteConfig.value.statisticsCode || '') const statisticsCodeEnabled = computed(() => !!siteConfig.value.statisticsCodeEnabled) function parseEnabledThemes(raw) { if (Array.isArray(raw)) return raw.filter(Boolean) if (typeof raw === 'string') { const s = raw.trim() if (!s) return [] if (s.startsWith('[') || s.startsWith('{')) { try { const parsed = JSON.parse(s) if (Array.isArray(parsed)) return parsed.filter(Boolean) if (parsed && Array.isArray(parsed.items)) return parsed.items.filter(Boolean) } catch (_) { // fallback to comma split } } return s.split(',').map((x) => x.trim()).filter(Boolean) } return [] } const defaultTheme = computed(() => typeof siteConfig.value.defaultTheme === 'string' && siteConfig.value.defaultTheme ? siteConfig.value.defaultTheme : null ) const enabledThemes = computed(() => parseEnabledThemes(siteConfig.value.enabledThemes)) // 初始化配置(仅在客户端执行) const initSiteConfig = async () => { if (typeof window !== 'undefined' && !isLoaded.value) { await fetchSiteConfig() } } // 刷新配置 const refreshSiteConfig = async () => { isLoaded.value = false await fetchSiteConfig() } return { siteConfig: readonly(siteConfig), isLoaded: readonly(isLoaded), isLoading: readonly(isLoading), siteTitle, logoUrl, schoolLogoHomeUrl, schoolLogoPrintUrl, description, siteVersion, guidelines, icp, gonganNumber, enableReplayRequests, enableCollaborativeSubmission, enableSubmissionRemarks, smtpEnabled, defaultTheme, enabledThemes, statisticsCode, statisticsCodeEnabled, fetchSiteConfig, initSiteConfig, refreshSiteConfig } }