fix(client/web): 语言跟随系统 + SSO 落地补 basePath + 移除账户页续费按钮
- 语言(#1):LocaleNotifier 首启无用户选择时读设备 locale(zh/ja/ko/ru/es 命中 对应语种,余回退英文),原来恒为固定默认 en、从不看系统语言。用户显式切换仍持久 化优先。 - 用户中心 SSO(#3):usercenter 运行在 basePath=/user,但 /sso 落地页用原生 window.location.replace('/') 跳转(Next 不补 basePath)→ 落到站点根=官网主页, 且换票已建立的会话看起来像未登录。改为 withBase() 统一补 /user 前缀,兑票成功 直达 /user/ 且保持登录态。(服务端 issue/exchange 流程实测均 200,非后端问题) - 账户页(#4):移除"续费/升级"按钮(免费卡片 + PRO 横幅两处)及其未用组件;购买入口 仍由"购买套餐"行保留,不影响下单路径。 Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01FEVUXAbFT6bF1Qw27RHWoD
This commit is contained in:
@@ -25,6 +25,17 @@ import { makeT } from '../../lib/i18n';
|
||||
import { getClient } from '../../lib/api/client';
|
||||
import { bilingual } from '../../lib/api/errors';
|
||||
|
||||
/** 站点 basePath(与 next.config.js 一致)。本页用的是 window.location 原生跳转,
|
||||
* Next 不会自动补 basePath,故绝对路径必须手动加前缀,否则会落到站点根(官网主页)
|
||||
* 而不是用户中心 —— 这正是「点用户中心却跳到主页、还要求重新登录」的根因。 */
|
||||
const BASE_PATH = process.env.NEXT_PUBLIC_BASE_PATH ?? '/user';
|
||||
|
||||
/** 把本站相对路径补上 basePath(供 window.location 原生跳转用)。 */
|
||||
function withBase(path: string): string {
|
||||
const p = path.startsWith('/') ? path : `/${path}`;
|
||||
return `${BASE_PATH}${p}`;
|
||||
}
|
||||
|
||||
/** redirect 白名单:仅本站相对路径(单个 '/' 开头),其余一律回 '/'。 */
|
||||
function safeRedirect(raw: string | null): string {
|
||||
if (!raw) return '/';
|
||||
@@ -45,14 +56,15 @@ export default function SsoPage() {
|
||||
const redirect = safeRedirect(params.get('redirect'));
|
||||
|
||||
// 票据只用一次,立刻从地址栏抹掉,不留浏览器历史(与 jiu 一致)。
|
||||
// 原生 history/location 不吃 Next 的 basePath,须手动补,否则地址与跳转都会漂到站点根。
|
||||
try {
|
||||
window.history.replaceState(null, '', '/sso/');
|
||||
window.history.replaceState(null, '', withBase('/sso/'));
|
||||
} catch {
|
||||
/* ignore */
|
||||
}
|
||||
|
||||
if (!ticket) {
|
||||
window.location.replace('/');
|
||||
window.location.replace(withBase('/'));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -61,14 +73,14 @@ export default function SsoPage() {
|
||||
.exchangeWebTicket(ticket)
|
||||
.then(() => {
|
||||
if (!alive) return;
|
||||
window.location.replace(redirect);
|
||||
window.location.replace(withBase(redirect));
|
||||
})
|
||||
.catch((e) => {
|
||||
if (!alive) return;
|
||||
setMsg(bilingual(e, lang));
|
||||
setFailed(true);
|
||||
setTimeout(() => {
|
||||
window.location.replace('/');
|
||||
window.location.replace(withBase('/'));
|
||||
}, 1500);
|
||||
});
|
||||
|
||||
|
||||
Reference in New Issue
Block a user