Files
bidding_watcher/src/common/auth/auth.guard.ts

61 lines
1.6 KiB
TypeScript
Raw Normal View History

import {
CanActivate,
ExecutionContext,
Injectable,
UnauthorizedException,
} from '@nestjs/common';
import { ConfigService } from '@nestjs/config';
import { Request } from 'express';
import { UsersService } from '../../users/users.service';
@Injectable()
export class AuthGuard implements CanActivate {
constructor(
private configService: ConfigService,
private usersService: UsersService,
) {}
async canActivate(context: ExecutionContext): Promise<boolean> {
const request = context.switchToHttp().getRequest<Request>();
// 检查是否启用 Basic Auth
const enableBasicAuth =
this.configService.get<string>('ENABLE_BASIC_AUTH') === 'true';
if (!enableBasicAuth) {
// 如果未启用 Basic Auth允许所有访问
return true;
}
// 解析 Authorization header
const authHeader = request.headers['authorization'] as string;
if (!authHeader || !authHeader.startsWith('Basic ')) {
throw new UnauthorizedException('Missing or invalid Authorization header');
}
// 解码 Basic Auth
const base64Credentials = authHeader.split(' ')[1];
const credentials = Buffer.from(base64Credentials, 'base64').toString(
'utf-8',
);
const [username, password] = credentials.split(':');
if (!username || !password) {
throw new UnauthorizedException('Invalid credentials format');
}
// 验证用户
const user = await this.usersService.validateUser(username, password);
if (!user) {
throw new UnauthorizedException('Invalid username or password');
}
// 将用户信息附加到请求对象
(request as any).user = user;
return true;
}
}