import { Assets } from 'pixi.js';
import Locales from './Locales';

/** Developer-friendly locales service that loads every available language. */
export default class DevLocales extends Locales
{
    public override name = 'DevLocales';
    public readonly backPanelControlsName = 'LanguageControls';

    constructor(lang: string, defaultLocale: string)
    {
        super(lang, defaultLocale);
        window.locales = this;
    }

    public get languagesList(): string[]
    {
        const resourceStore = this._i18n.services.resourceStore.data;
        const config = Assets.get<string[]>('translations_config') ?? [];

        return Object.keys(resourceStore).map((key) =>
            config.find((entry) => entry.toLowerCase() === key.toLowerCase()) ?? key);
    }

    public override async load(): Promise<void>
    {
        this._resultLocale = this.getResultLocale();
        const resources = await this.loadLocale(this._resultLocale);

        await this.applyI18n(resources);
    }

    protected override async loadLocale(_lang?: string): Promise<Record<string, { translation: Record<string, unknown> }>>
    {
        const config = Assets.get<string[]>('translations_config') ?? [];
        const resources: Record<string, { translation: Record<string, unknown> }> = {};

        for (const lang of config)
        {
            const path = lang === 'en' ? 'translations.json' : `locales/${lang}.json`;
            const gamePath = `translations/${path}`;
            const sdkPath = `shared-translations/${path}`;

            const [gameExists, sdkExists] = await Promise.all([
                this.checkFileExists(gamePath),
                this.checkFileExists(sdkPath),
            ]);

            if (!gameExists && !sdkExists)
            {
                continue;
            }

            const [gameTranslations, sdkTranslations] = await Promise.all([
                gameExists ? Assets.load<Record<string, unknown>>(gamePath) : Promise.resolve({}),
                sdkExists ? Assets.load<Record<string, unknown>>(sdkPath) : Promise.resolve({}),
            ]);

            resources[lang.toLowerCase()] = {
                translation: {
                    ...(sdkTranslations ?? {}),
                    ...(gameTranslations ?? {}),
                },
            };
        }

        return resources;
    }

    private async checkFileExists(path: string): Promise<boolean>
    {
        try
        {
            const response = await fetch(path, { method: 'HEAD' });

            return response.ok;
        }
        catch
        {
            return false;
        }
    }

    public async changeLanguage(lang: string): Promise<void>
    {
        await this._i18n.changeLanguage(lang);
    }

    public override dispose(): void
    {
        super.dispose();
        window.locales = undefined;
    }
}
