import { Cache } from "react-native-cache"; import { LIBRETRANSLATE_BASE_URL } from "@/constants/api"; import AsyncStorage from '@react-native-async-storage/async-storage'; type language_t = string; const cache = new Cache({ namespace: "translation_terrace", policy: { maxEntries: 50000, // if unspecified, it can have unlimited entries stdTTL: 0 // the standard ttl as number in seconds, default: 0 (unlimited) }, backend: AsyncStorage }); export type language_matrix_entry = { code: string, name: string, targets: string [] } export type language_matrix = { [key:string] : language_matrix_entry } export class Translator { constructor(public source : language_t, public defaultTarget : string = "en", private baseUrl = LIBRETRANSLATE_BASE_URL) { } async fetchLanguages() : Promise { const res = await fetch(this.baseUrl + "/languages", { headers: { "Content-Type": "application/json" } }); const data = await res.json(); return Object.fromEntries( Object.values(data as language_matrix_entry []).map((obj : language_matrix_entry) => { return [ obj["code"], obj, ] }) ) } async translate(text : string, target : string|undefined = undefined) { const url = LIBRETRANSLATE_BASE_URL + `/translate`; const res = await fetch(url, { method: "POST", body: JSON.stringify({ q: text, source: this.source, target: target || this.defaultTarget, format: "text", alternatives: 3, api_key: "" }), headers: { "Content-Type": "application/json" } }); const data = await res.json(); console.log(data) return data.translatedText } } export class CachedTranslator extends Translator { async translate (text : string, target : string|undefined = undefined) { const targetKey = target || this.defaultTarget; // console.debug(`Translating from ${this.source} -> ${targetKey}`) const key1 = `${this.source}::${targetKey}::${text}` const tr1 = await cache.get(key1); if (tr1) return tr1; const tr2 = await super.translate(text, target); const key2 = `${this.source}::${targetKey}::${text}` await cache.set(key2, tr2); return tr2; } }