import { FaviconOptions } from 'favicons';
import { ReadonlyDeep, Writable, ValueOf } from 'type-fest';

/**
 * List of valid platform names / icon types accepted by favicons. Should be
 * identical to `favicons` `PlatformName` type, which was made a private type in
 * version 7.0.0.
 */
type FaviconsIconTypes = keyof NonNullable<FaviconOptions["icons"]>;

/**
 * This should be similar to the `IconOptions` type from `favicons`, which was
 * made private in version 7.0.0. All options here are optional and writable.
 */
type FaviconsIconOptions = Writable<Partial<Exclude<ValueOf<NonNullable<FaviconOptions["icons"]>>, string[] | boolean>>>;

type FaviconsIconsOptions = {
    [K in FaviconsIconTypes]?: FaviconsIconOptions & {
        /**
         * Source image to use for this icon type.
         */
        source: string;
    };
};

interface BaseFaviconsPluginOptions {
    /**
     * Whether to cache generated assets for faster subsequent builds.
     *
     * @default `true`
     */
    cache?: boolean;
    /**
     * Inject html links/metadata -- set to `false` to generate a webapp.html` file.
     * @default true
     */
    inject?: boolean;
    /**
     * Output Path for the favicon images & files, relative to the Vite assets directory
     */
    outputPath?: string;
    /**
     * The root of the project from which you want to load metadata
     * @default process.cwd()
     */
    projectRoot?: string;
}

type FaviconsConfig = Partial<FaviconOptions>;

interface FaviconsLogoPluginOptions extends BaseFaviconsPluginOptions {
    /**
     * `Favicons` configuration options
     *  - [See `favicons` documentation](https://github.com/itgalaxy/favicons)
     */
    favicons?: FaviconsConfig;
    /**
     * Your source logo (Will default to )
     * @default "assets/logo.png"
     */
    logo?: string;
}

interface FaviconsIconsPluginOptions extends BaseFaviconsPluginOptions, ReadonlyDeep<FaviconOptions> {
    /**
     * `Favicons` configuration options
     *  - [See `favicons` documentation](https://github.com/itgalaxy/favicons)
     */
    favicons?: Omit<FaviconsConfig, "icons">;
    /**
     * Options for rendering supported icon types. Keys should be supported icon
     * types from `favicons` and values should be an object containing a `source`
     * and any other properties from `favicons` IconOptions type.
     */
    icons: FaviconsIconsOptions;
}

/**
 * Object used to describe a file emitted to a Vite compilation.
 */
interface EmittedFile {
    /**
     * Original file name.
     */
    name: string;

    /**
     * Name that will be used for the file in the compilation.
     */
    resolvedName: string;
}

interface Runtime {
    files: EmittedFile[];
    images: EmittedFile[];
    metadata: string;
}

export type { FaviconsIconsPluginOptions as F, Runtime as R, FaviconsLogoPluginOptions as a };
