feat: 支持游客免登录浏览核心页面

未登录用户可先浏览衣橱、穿搭、运势、分享等内容,登录改为用户主动选择,并在登录页增加协议勾选确认与暂不登录入口。
This commit is contained in:
2026-09-16 21:44:04 +08:00
parent c07a969642
commit 45222317af
47 changed files with 996 additions and 12150 deletions
+59 -4
View File
@@ -1,4 +1,4 @@
import { request, redirectToLogin } from '../../utils/request'
import { request } from '../../utils/request'
import * as auth from '../../utils/auth'
import { PagedResult, ClothesItem, QuotaItem } from '../../types/models'
import { QuotaType } from '../../utils/config'
@@ -7,6 +7,7 @@ import { clothesStatusFlag } from '../../utils/clothes-status'
import { resolvePendingClothes } from '../../utils/pending-clothes'
import { setTabBarSelected } from '../../utils/tabbar'
import { navScroll } from '../../utils/nav'
import { GUEST_WARDROBE, GuestClothes, goLogin } from '../../utils/guest'
import { logger } from '../../utils/logger'
// 日志模块名
@@ -22,6 +23,12 @@ const CATEGORIES = [
{ name: '配饰', value: '配饰' },
]
// 游客态分类筛选:与分类条 value 对齐,「全部」返回完整示例
function filterGuestClothes(index: number): GuestClothes[] {
const cat = CATEGORIES[index] ? CATEGORIES[index].value : ''
return cat ? GUEST_WARDROBE.filter((it) => it.category === cat) : GUEST_WARDROBE
}
Page({
data: {
categories: CATEGORIES,
@@ -45,16 +52,37 @@ Page({
{ text: '知道了', value: '' },
{ text: '查看衣物', value: 'ok', type: 'main' },
],
// 游客态(未登录):展示本地示例内容,不发任何需要授权的请求
guest: false,
guestList: GUEST_WARDROBE,
},
// scroll-view 滚动 → 导航收缩为玻璃小标题
onNavScroll: navScroll,
onLoad() {
// 首帧渲染前判定游客态:未登录直接渲染本地示例,避免首帧 setData 冲突
if (!auth.isLoggedIn()) {
this.setData({ guest: true, loading: false })
logger.info(LOG, '未登录进入首页,渲染游客态示例内容')
}
},
onShow() {
this.syncTabBar()
// 未登录直接回登录页(幂等跳转),不再发出必然 401 的请求
// 未登录:游客态浏览,零请求,不再强制跳登录(微信审核合规要求:
// 用户可先浏览体验功能服务,登录与否由用户自行选择)
if (!auth.isLoggedIn()) {
redirectToLogin()
if (!this.data.guest) this.setData({ guest: true, list: [], loading: false })
return
}
// 登录成功回到首页:清空示例数据,切回真实衣橱
if (this.data.guest) {
logger.info(LOG, '检测到登录态,从游客态切换为真实衣橱')
;(this as any).firstShown = true
this.setData({ guest: false, guestList: [], list: [], total: 0, uploadRemain: 0, loading: true })
this.resolvePending()
this.refresh()
return
}
// 核对「上传后退出小程序」的衣物最终处理结果(pending 为空时零请求)
@@ -82,6 +110,11 @@ Page({
},
onRefresh() {
// 游客态没有服务端数据可刷新,直接收起下拉动画
if (this.data.guest) {
this.setData({ refreshing: false })
return
}
this.setData({ refreshing: true })
Promise.all([this.fetchList(1), this.fetchQuota()]).finally(() => {
this.setData({ refreshing: false })
@@ -89,6 +122,7 @@ Page({
},
onReachBottom() {
if (this.data.guest) return
if (!this.data.hasMore || this.data.loading || this.data.loadingMore) return
this.fetchList(this.data.page + 1)
},
@@ -186,11 +220,27 @@ Page({
onCategoryTap(e: WechatMiniprogram.TouchEvent) {
const index = Number(e.currentTarget.dataset.index)
if (index === this.data.activeCategory) return
this.setData({ activeCategory: index, list: [], loading: true })
this.setData({ activeCategory: index })
// 游客态:本地示例数据即时筛选,提供可操作的浏览体验,不发请求
if (this.data.guest) {
this.setData({ guestList: filterGuestClothes(index) })
return
}
this.setData({ list: [], loading: true })
this.refresh()
},
// 游客态点击示例内容 / 受限入口:统一进入登录页,由用户自行选择是否登录
onGuestLogin() {
logger.debug(LOG, '游客态点击受限入口,引导登录')
goLogin()
},
onClothesTap(e: WechatMiniprogram.CustomEvent) {
if (this.data.guest) {
this.onGuestLogin()
return
}
const item = e.detail.item as ClothesItem
logger.debug(LOG, '点击衣物, uuid=', item && item.clothes_uuid)
wx.navigateTo({
@@ -200,6 +250,11 @@ Page({
},
onUpload() {
// 上传需登录:游客态先引导登录,不直接进入上传页
if (!auth.isLoggedIn()) {
this.onGuestLogin()
return
}
wx.navigateTo({
url: '/pages/upload/upload',
fail: (e) => logger.warn(LOG, 'navigateTo 上传页失败, err=', e && e.errMsg),