/// <reference lib="dom" />
/// <reference path="./lib/type.d.ts" />

import type { LogArguments } from './lib/logger';
import type { ErrorCode, HighResolutionTime } from './lib/node';

import type { BinaryLike, BinaryToTextEncoding, CipherGCMTypes, Encoding } from 'node:crypto';

// @ts-ignore
import type { BytesOptions } from 'bytes';

declare namespace types {
    interface LOG_TYPE {
        UNKNOWN: 0;
        SYSTEM: 1;
        NODE: 2;
        PROCESS: 4;
        COMPRESS: 8;
        WATCH: 16;
        FILE: 32;
        CLOUD: 64;
        TIME_ELAPSED: 128;
        TIME_PROCESS: 256;
        FAIL: 512;
        HTTP: 1024;
        IMAGE: 2048;
        EXEC: 4096;
        PERMISSION: 8192;
        TIMEOUT: 16384;
        STDOUT: 32768;
        DB: 65536;
    }

    const LOG_TYPE: {
        UNKNOWN: 0;
        SYSTEM: 1;
        NODE: 2;
        PROCESS: 4;
        COMPRESS: 8;
        WATCH: 16;
        FILE: 32;
        CLOUD: 64;
        TIME_ELAPSED: 128;
        TIME_PROCESS: 256;
        FAIL: 512;
        HTTP: 1024;
        IMAGE: 2048;
        EXEC: 4096;
        PERMISSION: 8192;
        TIMEOUT: 16384;
        STDOUT: 32768;
        DB: 65536;
    };

    interface LOG_STATE {
        STDIN: 0;
        STDOUT: 1;
        STDERR: 2;
    }

    const LOG_STATE: {
        STDIN: 0;
        STDOUT: 1;
        STDERR: 2;
    };

    interface STATUS_TYPE {
        UNKNOWN: 0;
        FATAL: 1;
        ERROR: 2;
        WARN: 3;
        INFO: 4;
        DEBUG: 5;
        ASSERT: 6;
        TRACE: 7;
    }

    const STATUS_TYPE: {
        UNKNOWN: 0;
        FATAL: 1;
        ERROR: 2;
        WARN: 3;
        INFO: 4;
        DEBUG: 5;
        ASSERT: 6;
        TRACE: 7;
    };

    interface ASSET_FLAG {
        NONE: 0;
        IGNORE: 1;
        CLONE: 2;
        USING: 4;
        WATCH: 8;
        MODIFIED: 16;
        PROCESS: 32;
        MAIN: 64;
        EXISTS: 128;
    }

    const ASSET_FLAG: {
        NONE: 0;
        IGNORE: 1;
        CLONE: 2;
        USING: 4;
        WATCH: 8;
        MODIFIED: 16;
        PROCESS: 32;
        MAIN: 64;
        EXISTS: 128;
    };

    interface FILE_TYPE {
        UNKNOWN: 0;
        ASSET: 1;
        TRANSFORM: 2;
        COMPRESSED: 4;
        SOURCEMAP: 8;
        TORRENT: 16;
    }

    const FILE_TYPE: {
        UNKNOWN: 0;
        ASSET: 1;
        TRANSFORM: 2;
        COMPRESSED: 4;
        SOURCEMAP: 8;
        TORRENT: 16;
    };

    interface ACTION_FLAG {
        NONE: 0;
        IGNORE: 1;
    }

    const ACTION_FLAG: {
        NONE: 0;
        IGNORE: 1;
    };

    interface ERR_CODE {
        MODULE_NOT_FOUND: "MODULE_NOT_FOUND";
        ERR_MODULE_NOT_FOUND: "ERR_MODULE_NOT_FOUND";
    }

    const ERR_CODE: {
        MODULE_NOT_FOUND: string;
        ERR_MODULE_NOT_FOUND: string;
    };

    interface DOWNLOAD_TYPE {
        HTTP: 0;
        DISK: 1;
        CACHE: 2;
    }

    const DOWNLOAD_TYPE: {
        HTTP: 0;
        DISK: 1;
        CACHE: 2;
    };

    interface FETCH_TYPE {
        UNKNOWN: 0;
        HTTP: 1;
        TORRENT: 2;
        FTP: 3;
        UNIX_SOCKET: 4;
    }

    const FETCH_TYPE: {
        UNKNOWN: 0;
        HTTP: 1;
        TORRENT: 2;
        FTP: 3;
        UNIX_SOCKET: 4;
    };

    interface DB_TYPE {
        SQL: 1;
        NOSQL: 2;
        DOCUMENT: 4;
        KEYVALUE: 8;
    }

    const DB_TYPE: {
        SQL: 1;
        NOSQL: 2;
        DOCUMENT: 4;
        KEYVALUE: 8;
    };

    interface DB_TRANSACTION {
        ACTIVE: 1;
        PARTIAL: 2;
        COMMIT: 4;
        TERMINATE: 8;
        ABORT: 16;
        FAIL: 32;
        AUTH: 64;
        CACHE: 128;
    }

    const DB_TRANSACTION: {
        ACTIVE: 1;
        PARTIAL: 2;
        COMMIT: 4;
        TERMINATE: 8;
        ABORT: 16;
        FAIL: 32;
        AUTH: 64;
        CACHE: 128;
    };

    interface TRANSFER_TYPE {
        DISK: 1;
        STREAM: 2;
        CHUNK: 4;
    }

    const TRANSFER_TYPE: {
        DISK: 1;
        STREAM: 2;
        CHUNK: 4;
    };

    interface WATCH_EVENT {
        MODIFIED: "modified";
        BROADCAST: "broadcast";
        CLOSE: "close";
        ERROR: "error";
    }

    const WATCH_EVENT: {
        MODIFIED: "modified";
        BROADCAST: "broadcast";
        CLOSE: "close";
        ERROR: "error";
    };

    interface READDIR_SORT {
        FILE: number;
        DIRECTORY: number;
        DESCENDING: number;
    }

    const READDIR_SORT: {
        FILE: 0;
        DIRECTORY: 1;
        DESCENDING: 2;
    };

    interface THRESHOLD {
        FILEMANAGER_INTERVAL: number;
        WATCH_INTERVAL: number;
        WATCH_CHANGE: number;
        LOGGER_METER_INCREMENT: number;
    }

    const THRESHOLD: {
        FILEMANAGER_INTERVAL: number;
        WATCH_INTERVAL: number;
        WATCH_CHANGE: number;
        LOGGER_METER_INCREMENT: number;
    };

    const IMPORT_MAP: StringMap;

    interface CloneObjectOptions<T = unknown> {
        target?: T;
        deep?: boolean;
        /** @deprecated WeakSet<object> */
        deepIgnore?: WeakSet<object> | WeakMap<object, object>;
        freezeDepth?: number | boolean;
        mergeArray?: MergeArrayMethod;
        mergeDepth?: number;
        typedArray?: boolean;
        structured?: boolean;
        shared?: boolean;
        symbol?: boolean;
        inherited?: boolean;
        nonenumerable?: boolean;
        preserve?: boolean;
    }

    type ImportAttributes = { with: { type: "json" } };
    type MergeArrayMethod = "concat" | "concat-pre" | "includes" | "unshift" | "push" | "flat" | "join" | "slice" | "reverse" | ["flat", number] | ["join", string] | ["slice", number, number?];
    type WatchEventValue = WATCH_EVENT[keyof WATCH_EVENT];

    function createAbortError(reject: true): Promise<never>;
    function createAbortError(): DOMException;
    function hasBit(value: unknown, flags: number): boolean;
    function ignoreFlag(value: unknown): boolean;
    function cloneFlag(value: unknown): boolean;
    function usingFlag(value: unknown): boolean;
    function watchFlag(value: unknown): boolean;
    function modifiedFlag(value: unknown): boolean;
    function processFlag(value: unknown): boolean;
    function mainFlag(value: unknown): boolean;
    function existsFlag(value: unknown): boolean;
    function getLogCurrent(): LogArguments | null;
    function setLogCurrent(value: LogArguments | null): void;
    function setTempDir(value: string): boolean;
    function getTempDir(create: true, prefix?: string): string;
    function getTempDir(...values: string[]): string;
    function isArray<T>(value: unknown): value is T[];
    function isObject<T extends object>(value: unknown): value is T;
    function isPlainObject<T = PlainObject>(value: unknown): value is T;
    function isString<T extends string>(value: unknown): value is T;
    function isEmpty(value: unknown): boolean;
    function isFunction<T extends Function>(value: unknown, cjs?: boolean): value is T;
    function isErrorCode<T extends unknown[]>(err: unknown, ...code: T): err is Required<ErrorCode<T[number]>>;
    function asFunction<U = unknown, V = unknown>(value: unknown, sync?: boolean): FunctionType<U, V> | null;
    function parseTime(value: number | string, epoch: true): number;
    function parseTime(value: number | string, negative: false): number;
    function parseTime(value: number | string, start?: number): number;
    function parseExpires(value: number | string, epoch: true): number;
    function parseExpires(value: number | string, start?: number | boolean): number;
    function formatTime(value: number, char: string): string;
    function formatTime(value: number, elapsed?: boolean, char?: string): string;
    function convertTime(value: number | string): number;
    function convertTime(value: HighResolutionTime, format: true): string;
    function convertTime(value: HighResolutionTime, format?: boolean): number;
    function hasGlob(value: string): boolean;
    function escapePattern(value: unknown, symbols?: boolean): string;
    function renameExt(value: string, ext: string, when?: string): string;
    function formatSize(value: string): number;
    function formatSize(value: number, options?: BytesOptions): string;
    function alignSize(value: unknown, kb?: number, factor?: number): number;
    function cascadeObject<T = unknown>(data: object, query: string, fallback?: unknown): T;
    function cloneObject<T>(data: T, deep: boolean): T;
    /** @deprecated WeakMap<object> */
    function cloneObject<T>(data: T, deepIgnore: WeakSet<object> | WeakMap<object, object>): T;
    function cloneObject<T, U>(data: T, options?: CloneObjectOptions<U>): T;
    function coerceObject<T = unknown>(data: T, cache: boolean): T;
    function coerceObject<T = unknown>(data: T, parseString?: FunctionArgs<[string]>, cache?: boolean): T;
    function getEncoding(value: unknown, fallback?: BufferEncoding): BufferEncoding;
    function encryptUTF8(algorithm: CipherGCMTypes, key: BinaryLike, iv: BinaryLike, data: string, encoding?: Encoding): string | undefined;
    function decryptUTF8(algorithm: CipherGCMTypes, key: BinaryLike, iv: BinaryLike, data: string, encoding?: Encoding): string | undefined;
    function hashKey(data: BinaryLike, algorithm?: string, encoding?: BinaryToTextEncoding): string;
    function incrementUUID(restart?: boolean): string;
    function validateUUID(value: unknown): boolean;
    function randomString(format: string, dictionary?: string): string;
    function sanitizeCmd(value: string, ...args: unknown[]): string;
    function sanitizeArgs(value: string, doubleQuote?: boolean): string;
    function sanitizeArgs(values: string[], doubleQuote?: boolean): string[];
    function errorValue(value: string, cause: unknown): Error;
    function errorValue(value: string, hint?: string, cause?: unknown): Error;
    function errorMessage(title: number | string, value: string, cause: unknown): Error;
    function errorMessage(title: number | string, value: string, hint?: string, cause?: unknown): Error;
    function supported(major: number, minor: number, lts: boolean): boolean;
    function supported(major: number, minor?: number, patch?: number, lts?: boolean): boolean;
    function importESM<T = unknown>(name: string | URL, isDefault: boolean, fromPath?: boolean): Promise<T>;
    function importESM<T = unknown>(name: string | URL, options?: ImportAttributes, fromPath?: boolean): Promise<T>;
    function requireESM<T = unknown>(name: string, url?: string | URL, expect?: string): T;
    function purgeMemory(percent?: number): number;
}

export = types;