import { AuthenticationPage, AuthenticationRules } from "../pages/auth/auth"; import { NewsData, NewsFeed } from "../pages/feed/news"; import { NewsItem } from "../pages/feed/news-item"; type EndpointURL = "/api" | `http${'s' | ''}://${string}`; interface ErrorDetails { code: string, message: string, } interface APIResponse { response ?: T; error ?: ErrorDetails; } let newsFeed : NewsFeed | null = null; let authPage : AuthenticationPage | null = null; class ErrorAPI extends Error {} export class ControllerAPI { protected endpoint: EndpointURL; constructor(endpoint: EndpointURL = "/api") { this.endpoint = endpoint; } protected async request(path: string, options: RequestInit = {}): Promise { let url : string; if (this.endpoint === "/api") { url = new URL("/api", window.location.origin).href + path; } else if (/\/$/i.test(this.endpoint)) { url = this.endpoint + path.slice(1); } else { url = this.endpoint + path; } const response = await fetch(url, options); const result: APIResponse = await response.json(); if (result.error) throw new ErrorAPI(result.error.message); if (result.response === undefined) throw new ErrorAPI("Missing response from API"); return result.response; } protected checkFirstAuth(): boolean { // Implement your authentication logic here, e.g., check for a valid token in localStorage //const token = localStorage.getItem('authToken'); //return !!token; // Returns true if token exists and is not empty return true; } protected throwIfUnauthed(): void { // Let's redirect to /auth if not authed if (!this.checkFirstAuth()) { window.location.href = '/auth'; } } async isAuthenticated(): Promise { if (!this.checkFirstAuth()) return false; const result = await this.request('/isAuthenticated', { method: 'GET', credentials: 'include' // Include cookies for authentication }); return result; } async getNews(returnPage: boolean = false) : Promise { this.throwIfUnauthed(); const result = await this.request('/news', { method: 'GET', credentials: 'include' // Include cookies for authentication }); if (!returnPage) return result; if (!newsFeed) newsFeed = new NewsFeed(result.map(x => new NewsItem( x.id, x.title, new Date(x.publishedAt), x.content, x.source ))); return newsFeed; } async getAuthRules(returnPage: boolean = false) : Promise { const result = await this.request('/authenticationRules', { method: 'GET', credentials: 'include' // Include cookies for authentication }); if (!returnPage) return result; if (!authPage) authPage = new AuthenticationPage(result); return authPage; } }