import { installQuasarPlugin } from '@quasar/quasar-app-extension-testing-unit-vitest';
import { mount, flushPromises } from '@vue/test-utils';
import { createTestingPinia } from '@pinia/testing';
import { vi } from 'vitest';
import { i18n } from 'src/boot/i18n';
import { Notify, Dialog } from 'quasar';
import axios from 'axios';
import * as useValidator from 'src/composables/useValidator';

installQuasarPlugin({
    plugins: {
        Notify,
        Dialog,
    },
});
const pinia = createTestingPinia({ createSpy: vi.fn, stubActions: false });
const mockPush = vi.fn();
const mockReplace = vi.fn();

vi.mock('vue-router', () => ({
    useRouter: () => ({
        push: mockPush,
        replace: mockReplace,
        currentRoute: {
            value: {
                params: {
                    id: 1,
                },
                meta: { moduleName: 'mockName' },
                matched: [{ path: 'mockName/list' }],
            },
        },
    }),
    useRoute: () => ({
        matched: [],
        query: {},
        params: {},
        meta: { moduleName: 'mockName' },
        path: 'mockSection/list',
    }),
    onBeforeRouteLeave: () => {},
}));

vi.mock('axios');

vi.spyOn(useValidator, 'useValidator').mockImplementation(() => {
    return { validate: vi.fn() };
});

class FormDataMock {
    append() {
        vi.fn();
    }
    delete() {
        vi.fn();
    }
    get() {
        vi.fn();
    }
    getAll() {
        vi.fn();
    }
    has() {
        vi.fn();
    }
    set() {
        vi.fn();
    }
    forEach() {
        vi.fn();
    }
}
global.FormData = FormDataMock;
global.URL = class URL {};

export function createWrapper(component, options) {
    const defaultOptions = {
        global: {
            plugins: [i18n, pinia],
        },
        mocks: {
            t: (tKey) => tKey,
            $t: (tKey) => tKey,
        },
    };

    const mountOptions = Object.assign({}, defaultOptions);

    if (options instanceof Object) {
        Object.assign(mountOptions, options);

        if (options.global) {
            mountOptions.global.plugins = defaultOptions.global.plugins;
        }
    }

    const wrapper = mount(component, mountOptions);
    const vm = wrapper.vm;

    return { vm, wrapper };
}

export { axios, flushPromises };