feat: 接入内容服务端真实接口并优化页面交互

- 迁移内容数据到服务端接口,移除本地模拟数据
- 首页新增推荐课程加载与未读消息检查
- 资讯、课程、搜索页面支持分页加载与错误重试
- 登录页新增恢复课程、消息、帮助页的路由逻辑
- 评估分析页新增处理中状态动效与阶段提示
- API 环境切换到正式域名 airz.hqling.cloud
This commit is contained in:
hujun
2026-10-01 20:26:41 +08:00
parent 3b2a0139e4
commit 2a9ff403c4
41 changed files with 21742 additions and 427 deletions
+23 -17
View File
@@ -2,7 +2,9 @@
<view class="page page-white" :style="pageStyle()">
<AppHeader title="新闻详情" />
<scroll-view scroll-y :style="contentStyle(96, false)">
<view v-if="available" class="detail-content">
<view v-if="loading" class="empty-content"><text class="empty-copy">正在加载资讯…</text></view>
<view v-else-if="error.length > 0" class="empty-content"><text class="empty-title">{{ error }}</text><button class="primary-button empty-button" @click="reload">重新加载</button></view>
<view v-else-if="available" class="detail-content">
<text class="detail-category">{{ article.category }}</text><text class="detail-title">{{ article.title }}</text>
<text class="detail-source">{{ article.source }}</text><text class="detail-meta">{{ article.date }} · {{ article.readingTime }}阅读</text>
<image class="detail-image" :src="article.image" mode="aspectFill"></image>
@@ -16,22 +18,26 @@
</template>
<script setup lang="uts">
import { usePageLayout } from '@/services/layout.uts'
import { newsArticles, findNewsArticle, NewsArticle } from '@/packages/content/services/content.uts'
import AppHeader from '@/components/AppHeader.uvue'
const { contentStyle, pageStyle } = usePageLayout()
const article = ref<NewsArticle>(newsArticles[0])
const available = ref(true)
onLoad((options) => {
if (options == null) return
const id = options['id'] == null ? '' : options['id'] as string
const legacyTitle = options['title'] == null ? '' : options['title'] as string
if (id == '' && legacyTitle == '') return
const selected = findNewsArticle(id, legacyTitle)
available.value = selected != null
if (selected != null) article.value = selected
})
const goNews = (): void => { uni.redirectTo({ url: '/packages/content/news/news' }) }
import { usePageLayout } from '@/services/layout.uts'
import { fetchArticle, emptyArticle, NewsArticle } from '@/services/content.uts'
import AppHeader from '@/components/AppHeader.uvue'
const { contentStyle, pageStyle } = usePageLayout()
const article = ref<NewsArticle>(emptyArticle()); const available = ref(false); const loading = ref(false); const error = ref('')
let id = ''; let visible = false; let generation = 0
async function reload() {
const request = ++generation; loading.value = true; available.value = false; error.value = ''
try {
const result = await fetchArticle(id)
if (!visible || request != generation) return
article.value = result; available.value = true
} catch (err) { if (visible && request == generation) error.value = err instanceof Error ? err.message : '资讯加载失败,请重试' }
finally { if (request == generation) loading.value = false }
}
onLoad((options) => { id = options?.['id'] ?? '' })
onShow(() => { visible = true; reload() })
onHide(() => { visible = false; generation++ })
onUnload(() => { visible = false; generation++ })
const goNews = () => { uni.redirectTo({ url: '/packages/content/news/news' }) }
</script>
<style>