feat: 添加工具函数和自定义Hooks

- 新增heritageTransform.ts实现数据转换
- 新增inheritorTransform.ts实现传承人数据转换
- 新增useAuth自定义Hook封装认证逻辑
- 提高代码复用性和可维护性
This commit is contained in:
Leo 2025-10-13 21:40:55 +08:00
parent 093cb7c1fd
commit 668864a736
3 changed files with 225 additions and 0 deletions

19
src/hooks/useAuth.ts Normal file
View File

@ -0,0 +1,19 @@
/**
* Hook
*/
import { useMemo } from 'react'
export const useAuth = () => {
// 检查本地存储中是否有 token
const token = localStorage.getItem('hrt-token')
const isAuthenticated = useMemo(() => {
return !!token
}, [token])
return {
isAuthenticated,
token,
}
}

View File

@ -0,0 +1,81 @@
/**
*
* 使
*/
import type { HeritageListItem, HeritageDetail, HeritageItem } from '@/types'
/**
* HeritageItem格式
*/
export const transformHeritageListItem = (item: HeritageListItem): HeritageItem => {
// 解析tags字符串为数组
const tagsArray = item.tags ? item.tags.split(',').map(t => t.trim()).filter(Boolean) : []
return {
id: String(item.id),
name: item.name,
category: item.category as any, // 后端返回的category格式应该与前端一致
province: item.province,
city: item.city,
level: item.level as any,
coverImage: item.coverImage,
description: item.description,
// 以下字段列表接口没有,使用默认值
history: '',
skills: '',
significance: '',
inheritors: [],
videoUrl: '',
virtualTourUrl: '',
status: item.status as 'active' | 'endangered' | 'revived',
tags: tagsArray,
viewCount: item.viewCount || 0,
likeCount: item.likeCount || 0,
createdAt: item.createTime,
updatedAt: item.createTime,
}
}
/**
* HeritageItem格式
*/
export const transformHeritageDetail = (detail: HeritageDetail): HeritageItem => {
// 解析tags字符串为数组
const tagsArray = detail.tags ? detail.tags.split(',').map(t => t.trim()).filter(Boolean) : []
// 解析images JSON字符串为数组
let imagesArray: string[] = []
try {
if (detail.images) {
imagesArray = JSON.parse(detail.images)
}
} catch (error) {
console.error('Failed to parse images JSON:', error)
imagesArray = []
}
return {
id: String(detail.id),
name: detail.name,
category: detail.category as any,
province: detail.province,
city: detail.city,
level: detail.level as any,
coverImage: detail.coverImage,
images: imagesArray,
description: detail.description,
history: detail.history || '',
skills: detail.skills || '',
significance: detail.significance || '',
inheritors: [], // 传承人信息需要另外接口获取
videoUrl: detail.videoUrl,
virtualTourUrl: '',
status: detail.status as 'active' | 'endangered' | 'revived',
tags: tagsArray,
viewCount: detail.viewCount || 0,
likeCount: detail.likeCount || 0,
createdAt: detail.createTime,
updatedAt: detail.updateTime,
}
}

View File

@ -0,0 +1,125 @@
/**
*
* 使
*/
import type { InheritorListItem, InheritorDetail, Inheritor } from '@/types'
/**
* Inheritor格式
*/
export const transformInheritorListItem = (item: InheritorListItem): Inheritor => {
// 计算年龄
const currentYear = new Date().getFullYear()
const age = currentYear - item.birthYear
return {
id: String(item.id),
name: item.name,
avatar: item.avatar,
coverImage: item.avatar, // 使用头像作为封面
gender: item.gender === 1 ? 'male' : 'female',
birthYear: item.birthYear,
province: item.province,
city: item.city,
level: item.level as any,
heritageItems: [String(item.heritageId)],
title: `${getLevelLabel(item.level)}代表性传承人`,
bio: item.introduction || '',
masterSkills: item.heritageName || '',
achievements: [],
awards: [],
works: [],
videos: [],
followers: item.likeCount || 0,
viewCount: item.viewCount || 0,
createdAt: item.createTime,
updatedAt: item.createTime,
}
}
/**
* Inheritor格式
*/
export const transformInheritorDetail = (detail: InheritorDetail): Inheritor => {
// 计算年龄
const currentYear = new Date().getFullYear()
const age = currentYear - detail.birthYear
// 解析works JSON字符串为数组
let worksArray: any[] = []
try {
if (detail.works) {
worksArray = JSON.parse(detail.works)
}
} catch (error) {
console.error('Failed to parse works JSON:', error)
}
// 解析images JSON字符串为数组
let imagesArray: string[] = []
try {
if (detail.images) {
imagesArray = JSON.parse(detail.images)
}
} catch (error) {
console.error('Failed to parse images JSON:', error)
}
return {
id: String(detail.id),
name: detail.name,
avatar: detail.avatar,
coverImage: imagesArray[0] || detail.avatar,
gender: detail.gender === 1 ? 'male' : 'female',
birthYear: detail.birthYear,
province: detail.province,
city: detail.city,
level: detail.level as any,
heritageItems: [String(detail.heritageId)],
title: `${getLevelLabel(detail.level)}代表性传承人`,
bio: detail.introduction || '',
masterSkills: detail.heritageName || '',
achievements: detail.achievements ? parseAchievements(detail.achievements) : [],
awards: [],
works: worksArray,
videos: detail.videoUrl ? [{
id: 'video-1',
title: `${detail.name}的传承故事`,
cover: detail.avatar,
url: detail.videoUrl,
duration: 0,
viewCount: 0,
publishDate: detail.createTime,
}] : [],
followers: detail.likeCount || 0,
viewCount: detail.viewCount || 0,
createdAt: detail.createTime,
updatedAt: detail.updateTime,
}
}
/**
*
*/
function getLevelLabel(level: string): string {
const levelMap: Record<string, string> = {
national: '国家级',
provincial: '省级',
municipal: '市级',
}
return levelMap[level] || level
}
/**
*
*/
function parseAchievements(achievements: string): any[] {
// 简单按换行分割
return achievements.split('\n').filter(Boolean).map((text, index) => ({
id: `achievement-${index}`,
title: text.trim(),
description: '',
date: '',
}))
}