Files
2026-09-15 21:56:10 +02:00

92 lines
3.3 KiB
TypeScript

import { ISource, SearchResult, ContentLinks, MediaType, SelectionData } from '../../src/types/source.js';
import { sourceRegistry } from '../../src/core/registry.js';
import { FS24API } from './api.js';
import { FS24Auth } from './auth.js';
import { parseListingHTML, extractNewsId, parseReleasesJSON } from './parser.js';
export class FS24Source implements ISource {
public readonly name = 'fs24';
public readonly displayName = 'FS24';
public async healthCheck(): Promise<boolean> {
try {
await FS24Auth.getCookie(true);
return true;
} catch (e: any) {
console.error(`[FS24] HealthCheck échoué: ${e.message}`);
return false;
}
}
public async search(query: string, mediaType?: MediaType): Promise<SearchResult[]> {
if (!query || query.length < 3) return [];
try {
const html = await FS24API.fetchSearch(query);
const results = parseListingHTML(html, mediaType || 'movie');
return results;
} catch (e: any) {
console.error(`[FS24] Erreur search: ${e.message}`);
return [];
}
}
public async getTrending(mediaType: MediaType): Promise<SearchResult[]> {
try {
const html = await FS24API.fetchTrending(mediaType === 'series' ? 'series' : 'movie');
const results = parseListingHTML(html, mediaType);
return results.slice(0, 20); // Keep top 20
} catch (e: any) {
console.error(`[FS24] Erreur trending: ${e.message}`);
return [];
}
}
public async getRecent(): Promise<SearchResult[]> {
try {
const html = await FS24API.fetchRecent();
const results = parseListingHTML(html, 'movie'); // Default to movie for recents, TMDB will fix it if needed
return results.slice(0, 20);
} catch (e: any) {
console.error(`[FS24] Erreur recent: ${e.message}`);
return [];
}
}
public async getContentLinks(identifier: string, season?: number): Promise<ContentLinks> {
try {
// Step 1: Fetch the page HTML to extract the news_id
const html = await FS24API.fetchPage(identifier);
const newsId = extractNewsId(html);
if (!newsId) {
console.warn(`[FS24] Impossible d'extraire le news_id depuis: ${identifier}`);
return { links: [] };
}
// Step 2: Call the release JSON API to get the actual download links
const releaseData = await FS24API.fetchReleases(newsId);
const links = parseReleasesJSON(releaseData);
console.log(`[FS24] ${links.length} lien(s) trouvé(s) pour post_id=${newsId}`);
return { links };
} catch (e: any) {
console.error(`[FS24] Erreur getContentLinks: ${e.message}`);
return { links: [] };
}
}
public async getSelection(identifier: string, type?: string, seasonValue?: string | number): Promise<SelectionData> {
const content = await this.getContentLinks(identifier);
return {
links: content.links,
seasons: [],
isSeries: type === 'series'
};
}
}
// ── Auto-registration ──
sourceRegistry.register(new FS24Source());