refactor(data): replace schema classes with readonly models
This commit is contained in:
@@ -2,32 +2,37 @@
|
||||
* Auth API
|
||||
*
|
||||
* 认证相关接口
|
||||
*
|
||||
*
|
||||
*/
|
||||
import { z } from "zod";
|
||||
|
||||
import { httpClient } from "./http_client";
|
||||
import { ApiPath } from "./api_path";
|
||||
import { ApiEnvelope, unwrap } from "./response_helper";
|
||||
import {
|
||||
FacebookIdentityRequest,
|
||||
FacebookIdentityResponse,
|
||||
FacebookIdentityResponseSchema,
|
||||
FacebookLoginRequest,
|
||||
FacebookPsidLoginRequest,
|
||||
FacebookPsidLoginResponse,
|
||||
FacebookPsidLoginResponseSchema,
|
||||
FbIdLoginRequest,
|
||||
GoogleLoginRequest,
|
||||
GuestLoginRequest,
|
||||
GuestLoginResponse,
|
||||
GuestLoginResponseSchema,
|
||||
LoginRequest,
|
||||
LoginResponse,
|
||||
LoginResponseSchema,
|
||||
RefreshTokenRequest,
|
||||
RefreshTokenResponse,
|
||||
RefreshTokenResponseSchema,
|
||||
RegisterRequest,
|
||||
} from "@/data/schemas/auth";
|
||||
import { User } from "@/data/schemas/user";
|
||||
import { User, UserSchema } from "@/data/schemas/user";
|
||||
import type { UserData } from "@/data/schemas/user/user";
|
||||
import { Logger } from "@/utils/logger";
|
||||
import { ApiPath } from "./api_path";
|
||||
import { httpClient } from "./http_client";
|
||||
import { ApiEnvelope, unwrap } from "./response_helper";
|
||||
|
||||
const log = new Logger("DataServicesApiAuthApi");
|
||||
|
||||
@@ -36,11 +41,11 @@ export class AuthApi {
|
||||
* 邮箱密码登录
|
||||
*/
|
||||
async emailLogin(body: LoginRequest): Promise<LoginResponse> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(
|
||||
ApiPath.emailLogin,
|
||||
{ method: "POST", body: body.toJson() }
|
||||
);
|
||||
return LoginResponse.fromJson(unwrap(env) as Record<string, unknown>);
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(ApiPath.emailLogin, {
|
||||
method: "POST",
|
||||
body,
|
||||
});
|
||||
return LoginResponseSchema.parse(unwrap(env) as Record<string, unknown>);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -49,7 +54,7 @@ export class AuthApi {
|
||||
async register(body: RegisterRequest): Promise<void> {
|
||||
await httpClient<ApiEnvelope<unknown>>(ApiPath.register, {
|
||||
method: "POST",
|
||||
body: body.toJson(),
|
||||
body,
|
||||
});
|
||||
}
|
||||
|
||||
@@ -59,20 +64,20 @@ export class AuthApi {
|
||||
async googleLogin(body: GoogleLoginRequest): Promise<LoginResponse> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(ApiPath.googleLogin, {
|
||||
method: "POST",
|
||||
body: body.toJson(),
|
||||
body,
|
||||
});
|
||||
return LoginResponse.fromJson(unwrap(env) as Record<string, unknown>);
|
||||
return LoginResponseSchema.parse(unwrap(env) as Record<string, unknown>);
|
||||
}
|
||||
|
||||
/**
|
||||
* Facebook 登录
|
||||
*/
|
||||
async facebookLogin(body: FacebookLoginRequest): Promise<LoginResponse> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(
|
||||
ApiPath.facebookLogin,
|
||||
{ method: "POST", body: body.toJson() }
|
||||
);
|
||||
return LoginResponse.fromJson(unwrap(env) as Record<string, unknown>);
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(ApiPath.facebookLogin, {
|
||||
method: "POST",
|
||||
body,
|
||||
});
|
||||
return LoginResponseSchema.parse(unwrap(env) as Record<string, unknown>);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -81,9 +86,9 @@ export class AuthApi {
|
||||
async facebookIdLogin(body: FbIdLoginRequest): Promise<LoginResponse> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(
|
||||
ApiPath.facebookIdLogin,
|
||||
{ method: "POST", body: body.toJson() }
|
||||
{ method: "POST", body },
|
||||
);
|
||||
return LoginResponse.fromJson(unwrap(env) as Record<string, unknown>);
|
||||
return LoginResponseSchema.parse(unwrap(env) as Record<string, unknown>);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -94,9 +99,9 @@ export class AuthApi {
|
||||
): Promise<FacebookPsidLoginResponse> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(
|
||||
ApiPath.facebookPsidLogin,
|
||||
{ method: "POST", body: body.toJson() },
|
||||
{ method: "POST", body },
|
||||
);
|
||||
return FacebookPsidLoginResponse.fromJson(
|
||||
return FacebookPsidLoginResponseSchema.parse(
|
||||
unwrap(env) as Record<string, unknown>,
|
||||
);
|
||||
}
|
||||
@@ -109,9 +114,9 @@ export class AuthApi {
|
||||
): Promise<FacebookIdentityResponse> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(
|
||||
ApiPath.userFacebookIdentity,
|
||||
{ method: "POST", body: body.toJson() },
|
||||
{ method: "POST", body },
|
||||
);
|
||||
return FacebookIdentityResponse.fromJson(
|
||||
return FacebookIdentityResponseSchema.parse(
|
||||
unwrap(env) as Record<string, unknown>,
|
||||
);
|
||||
}
|
||||
@@ -120,7 +125,7 @@ export class AuthApi {
|
||||
* 退出登录(fire-and-forget)
|
||||
*
|
||||
* 后端 logout 端点的 envelope `data` 字段常为 `null`(登出端点没有业务数据),
|
||||
* 不要再用 `unwrap` + `LogoutResponse.fromJson` 解析 —— Zod schema 是 z.object,
|
||||
* 不要再用 `unwrap` + `LogoutResponseSchema.parse` 解析 —— Zod schema 是 z.object,
|
||||
* 对 null 会抛 ZodError "Invalid input: expected object, received null"。
|
||||
*
|
||||
* 对齐 `register` 的写法:调通就完事,不解析响应体。
|
||||
@@ -137,19 +142,20 @@ export class AuthApi {
|
||||
async guestLogin(body: GuestLoginRequest): Promise<GuestLoginResponse> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(ApiPath.guestLogin, {
|
||||
method: "POST",
|
||||
body: body.toJson(),
|
||||
body,
|
||||
});
|
||||
log.debug("[AuthApi.guestLogin] raw envelope from backend", env);
|
||||
const unwrapped = unwrap(env) as Record<string, unknown>;
|
||||
const userObj = unwrapped.user as { lastMessageAt?: unknown } | undefined;
|
||||
log.debug("[AuthApi.guestLogin] unwrapped data (pre-parse)", {
|
||||
hasUser: "user" in unwrapped,
|
||||
userKeys: userObj && typeof userObj === "object" ? Object.keys(userObj) : null,
|
||||
userKeys:
|
||||
userObj && typeof userObj === "object" ? Object.keys(userObj) : null,
|
||||
lastMessageAt: userObj?.lastMessageAt,
|
||||
lastMessageAtType: typeof userObj?.lastMessageAt,
|
||||
});
|
||||
try {
|
||||
return GuestLoginResponse.fromJson(unwrapped);
|
||||
return GuestLoginResponseSchema.parse(unwrapped);
|
||||
} catch (e) {
|
||||
if (e instanceof z.ZodError) {
|
||||
log.error("[AuthApi.guestLogin] ZodError parsing response", {
|
||||
@@ -167,15 +173,13 @@ export class AuthApi {
|
||||
/**
|
||||
* 刷新 Token
|
||||
*/
|
||||
async refreshToken(
|
||||
body: RefreshTokenRequest
|
||||
): Promise<RefreshTokenResponse> {
|
||||
async refreshToken(body: RefreshTokenRequest): Promise<RefreshTokenResponse> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(ApiPath.refresh, {
|
||||
method: "POST",
|
||||
body: body.toJson(),
|
||||
body,
|
||||
});
|
||||
return RefreshTokenResponse.fromJson(
|
||||
unwrap(env) as Record<string, unknown>
|
||||
return RefreshTokenResponseSchema.parse(
|
||||
unwrap(env) as Record<string, unknown>,
|
||||
);
|
||||
}
|
||||
|
||||
@@ -183,10 +187,8 @@ export class AuthApi {
|
||||
* 获取当前用户信息
|
||||
*/
|
||||
async getCurrentUser(): Promise<User> {
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(
|
||||
ApiPath.getCurrentUser
|
||||
);
|
||||
return User.fromJson(unwrap(env) as UserData);
|
||||
const env = await httpClient<ApiEnvelope<unknown>>(ApiPath.getCurrentUser);
|
||||
return UserSchema.parse(unwrap(env) as UserData);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user