A social knowledge tool for researchers built on ATProto
1import { UseCase } from 'src/shared/core/UseCase';
2import { Result, err, ok } from 'src/shared/core/Result';
3import { AppError } from 'src/shared/core/AppError';
4import { ITokenService } from '../services/ITokenService';
5import { TokenPair } from '@semble/types';
6import { RefreshAccessTokenErrors } from './errors/RefreshAccessTokenErrors';
7
8const ENABLE_REFRESH_LOGGING = true;
9
10export interface RefreshAccessTokenDTO {
11 refreshToken: string;
12}
13
14export type RefreshAccessTokenResponse = Result<
15 TokenPair,
16 RefreshAccessTokenErrors.InvalidRefreshTokenError | AppError.UnexpectedError
17>;
18
19export class RefreshAccessTokenUseCase
20 implements UseCase<RefreshAccessTokenDTO, Promise<RefreshAccessTokenResponse>>
21{
22 constructor(private tokenService: ITokenService) {}
23
24 async execute(
25 request: RefreshAccessTokenDTO,
26 ): Promise<RefreshAccessTokenResponse> {
27 try {
28 if (ENABLE_REFRESH_LOGGING) {
29 const tokenPreview = '...' + request.refreshToken.slice(-8);
30 console.log(
31 `[RefreshAccessTokenUseCase] Attempting token refresh with token: ${tokenPreview}`,
32 );
33 }
34
35 const tokenResult = await this.tokenService.refreshToken(
36 request.refreshToken,
37 );
38
39 if (tokenResult.isErr()) {
40 if (ENABLE_REFRESH_LOGGING) {
41 console.log(
42 `[RefreshAccessTokenUseCase] Token refresh failed: ${tokenResult.error.message}`,
43 );
44 }
45 return err(new AppError.UnexpectedError(tokenResult.error));
46 }
47
48 if (!tokenResult.value) {
49 if (ENABLE_REFRESH_LOGGING) {
50 console.log(
51 `[RefreshAccessTokenUseCase] Token refresh returned null - invalid refresh token`,
52 );
53 }
54 return err(new RefreshAccessTokenErrors.InvalidRefreshTokenError());
55 }
56
57 if (ENABLE_REFRESH_LOGGING) {
58 console.log(`[RefreshAccessTokenUseCase] Token refresh successful`);
59 }
60
61 return ok(tokenResult.value);
62 } catch (error: any) {
63 if (ENABLE_REFRESH_LOGGING) {
64 console.log(
65 `[RefreshAccessTokenUseCase] Token refresh error: ${error.message}`,
66 );
67 }
68 return err(new AppError.UnexpectedError(error));
69 }
70 }
71}