116 lines
3.6 KiB
TypeScript
116 lines
3.6 KiB
TypeScript
/**
|
|
* 管理员业务服务
|
|
*
|
|
* 功能描述:
|
|
* - 调用核心服务完成管理员登录
|
|
* - 提供用户列表查询
|
|
* - 提供用户密码重置能力
|
|
*
|
|
* @author jianuo
|
|
* @version 1.0.0
|
|
* @since 2025-12-19
|
|
*/
|
|
|
|
import { Inject, Injectable, Logger, NotFoundException } from '@nestjs/common';
|
|
import { AdminCoreService } from '../../core/admin_core/admin_core.service';
|
|
import { Users } from '../../core/db/users/users.entity';
|
|
import { UsersService } from '../../core/db/users/users.service';
|
|
import { UsersMemoryService } from '../../core/db/users/users_memory.service';
|
|
import { LogManagementService } from '../../core/utils/logger/log_management.service';
|
|
|
|
export interface AdminApiResponse<T = any> {
|
|
success: boolean;
|
|
data?: T;
|
|
message: string;
|
|
error_code?: string;
|
|
}
|
|
|
|
@Injectable()
|
|
export class AdminService {
|
|
private readonly logger = new Logger(AdminService.name);
|
|
|
|
constructor(
|
|
private readonly adminCoreService: AdminCoreService,
|
|
@Inject('UsersService') private readonly usersService: UsersService | UsersMemoryService,
|
|
private readonly logManagementService: LogManagementService,
|
|
) {}
|
|
|
|
getLogDirAbsolutePath(): string {
|
|
return this.logManagementService.getLogDirAbsolutePath();
|
|
}
|
|
|
|
async login(identifier: string, password: string): Promise<AdminApiResponse> {
|
|
try {
|
|
const result = await this.adminCoreService.login({ identifier, password });
|
|
return { success: true, data: result, message: '管理员登录成功' };
|
|
} catch (error) {
|
|
this.logger.error(`管理员登录失败: ${identifier}`, error instanceof Error ? error.stack : String(error));
|
|
return {
|
|
success: false,
|
|
message: error instanceof Error ? error.message : '管理员登录失败',
|
|
error_code: 'ADMIN_LOGIN_FAILED',
|
|
};
|
|
}
|
|
}
|
|
|
|
async listUsers(limit: number, offset: number): Promise<AdminApiResponse<{ users: any[]; limit: number; offset: number }>> {
|
|
const users = await this.usersService.findAll(limit, offset);
|
|
return {
|
|
success: true,
|
|
data: {
|
|
users: users.map((u: Users) => this.formatUser(u)),
|
|
limit,
|
|
offset,
|
|
},
|
|
message: '用户列表获取成功',
|
|
};
|
|
}
|
|
|
|
async getUser(id: bigint): Promise<AdminApiResponse<{ user: any }>> {
|
|
const user = await this.usersService.findOne(id);
|
|
return {
|
|
success: true,
|
|
data: { user: this.formatUser(user) },
|
|
message: '用户信息获取成功',
|
|
};
|
|
}
|
|
|
|
async resetPassword(id: bigint, newPassword: string): Promise<AdminApiResponse> {
|
|
// 确认用户存在
|
|
const user = await this.usersService.findOne(id).catch((): null => null);
|
|
if (!user) {
|
|
throw new NotFoundException('用户不存在');
|
|
}
|
|
|
|
await this.adminCoreService.resetUserPassword(id, newPassword);
|
|
|
|
this.logger.log(`管理员重置密码成功: userId=${id.toString()}`);
|
|
|
|
return { success: true, message: '密码重置成功' };
|
|
}
|
|
|
|
async getRuntimeLogs(lines?: number): Promise<AdminApiResponse<{ file: string; updated_at: string; lines: string[] }>> {
|
|
const result = await this.logManagementService.getRuntimeLogTail({ lines });
|
|
return {
|
|
success: true,
|
|
data: result,
|
|
message: '运行日志获取成功',
|
|
};
|
|
}
|
|
|
|
private formatUser(user: Users) {
|
|
return {
|
|
id: user.id.toString(),
|
|
username: user.username,
|
|
nickname: user.nickname,
|
|
email: user.email,
|
|
email_verified: user.email_verified,
|
|
phone: user.phone,
|
|
avatar_url: user.avatar_url,
|
|
role: user.role,
|
|
created_at: user.created_at,
|
|
updated_at: user.updated_at,
|
|
};
|
|
}
|
|
}
|