Convert eslintrc in package.json to flat config

- I hate this. I hate that they forced this.
- But hey, at least it works again.
This commit is contained in:
adroslice 2024-05-18 21:35:09 +02:00
parent fc18e9e8ac
commit 2c050ae61d
32 changed files with 111 additions and 113 deletions

47
client/eslint.config.js Normal file
View file

@ -0,0 +1,47 @@
import vuePlugin from 'eslint-plugin-vue';
import vueParser from 'vue-eslint-parser';
import tsParser from '@typescript-eslint/parser';
export default [
...vuePlugin.configs['flat/recommended'],
{
languageOptions: {
parser: vueParser,
parserOptions: {
parser: tsParser,
sourceType: 'module',
},
},
plugins: { vueParser },
rules: {
'semi': [
'error',
'always',
],
'comma-dangle': [
'error',
'always-multiline',
],
'no-trailing-spaces': 'error',
'quotes': [
'warn',
'single',
],
'prefer-template': 'warn',
'vue/multi-word-component-names': 'off',
'vue/html-closing-bracket-spacing': 'off',
'vue/html-self-closing': 'off',
'vue/first-attribute-linebreak': 'off',
'vue/max-attributes-per-line': 'off',
'vue/html-closing-bracket-newline': 'off',
'vue/no-dupe-keys': 'off',
'vue/no-template-shadow': 'off',
'vue/v-on-event-hyphenation': 'off',
'vue/singleline-html-element-content-newline': 'off',
'indent': [
'error',
2,
],
},
},
];

View file

@ -50,53 +50,5 @@
"vite-plugin-pages": "^0.32.1",
"vite-tsconfig-paths": "^4.3.2",
"vue-tsc": "^2.0.19"
},
"eslintConfig": {
"root": true,
"parser": "vue-eslint-parser",
"parserOptions": {
"parser": "@typescript-eslint/parser",
"sourceType": "module"
},
"overrides": [
{
"files": "**/*.+(ts|vue)"
}
],
"extends": [
"plugin:vue/vue3-strongly-recommended"
],
"plugins": [
"eslint-plugin-vue"
],
"rules": {
"semi": [
"error",
"always"
],
"comma-dangle": [
"error",
"always-multiline"
],
"no-trailing-spaces": "error",
"quotes": [
"warn",
"single"
],
"prefer-template": "warn",
"vue/multi-word-component-names": "off",
"vue/html-closing-bracket-spacing": "off",
"vue/html-self-closing": "off",
"vue/first-attribute-linebreak": "off",
"vue/max-attributes-per-line": "off",
"vue/html-closing-bracket-newline": "off",
"vue/no-dupe-keys": "off",
"vue/no-template-shadow": "off",
"vue/singleline-html-element-content-newline": "off",
"indent": [
"error",
2
]
}
}
}

View file

@ -161,7 +161,7 @@ onMounted(async() => {
</div>
</div>
<router-view v-slot="{ Component, route }" v-if="authState === AuthState.Authenticated">
<router-view v-if="authState === AuthState.Authenticated" v-slot="{ Component, route }">
<Transition name="fade">
<component :is="Component" :key="{route}" class="page-content pad gap"/>
</Transition>
@ -169,15 +169,15 @@ onMounted(async() => {
</div>
<Transition name="fade">
<div class="login" v-if="authState === AuthState.Unauthenticated">
<div v-if="authState === AuthState.Unauthenticated" class="login">
<FocusTrap>
<form @submit="$event => $event.preventDefault()" :disabled="loginDisabled" class="cl-secondary">
<form :disabled="loginDisabled" class="cl-secondary" @submit="$event => $event.preventDefault()">
<h1>nfSense Login</h1>
<h2 :hidden="!loginDisabled">Logging in...</h2>
<label for="username" v-text="'Username'" :hidden="loginDisabled" />
<input name="username" v-model="username" :hidden="loginDisabled" :disabled="loginDisabled"/>
<label for="password" v-text="'Password'" :hidden="loginDisabled"/>
<input name="password" type="password" v-model="password" :hidden="loginDisabled" :disabled="loginDisabled"/>
<label for="username" :hidden="loginDisabled" v-text="'Username'" />
<input v-model="username" name="username" :hidden="loginDisabled" :disabled="loginDisabled"/>
<label for="password" :hidden="loginDisabled" v-text="'Password'"/>
<input v-model="password" name="password" type="password" :hidden="loginDisabled" :disabled="loginDisabled"/>
<button @click="tryLogin">Login</button>
</form>
</FocusTrap>

View file

@ -31,6 +31,6 @@ async function draggedRow(draggedRow: number, draggedOverRow: number) {
<slot/>
</PageHeader>
<div v-if="loading" >Loading...</div>
<NiceTable v-else :columns="columns" v-model:selection="selection" @dragged-row="draggedRow" v-bind="tableProps" :data="data"/>
<NiceTable v-else v-model:selection="selection" :columns="columns" v-bind="tableProps" :data="data" @dragged-row="draggedRow"/>
</div>
</template>

View file

@ -8,11 +8,11 @@ watch($$(modelValue), (val) => emit('update:modelValue', val));
</script>
<template>
<div @click="() => modelValue = !modelValue" @keypress="() => modelValue = !modelValue" tabindex="0">
<div tabindex="0" @click="() => modelValue = !modelValue" @keypress="() => modelValue = !modelValue">
<i-material-symbols-check-box-outline v-if="modelValue"/>
<i-material-symbols-check-box-outline-blank v-else/>
</div>
</template>
</template>
<style scoped>
div { cursor: pointer; }

View file

@ -184,26 +184,26 @@ function handleKeydown(e: KeyboardEvent) {
}
</script>
<template>
<div :class="{'multiselect': 1, 'cl-secondary': 1, expanded}" ref="inputDiv"
<div ref="inputDiv" :class="{'multiselect': 1, 'cl-secondary': 1, expanded}"
@keydown="handleKeydown"
@focusin="$event => { if (!inputDiv?.contains($event.relatedTarget as HTMLElement)) focusIn(); }"
@focusout="$event => expanded = inputDiv?.contains($event.relatedTarget as HTMLElement) ?? false">
<div class="head">
<div class="selection" v-if="multiple">
<div v-for="(key, index) of modelValue as Index[]" :key="key" v-text="options[key].display" :class="{navigated: selCount + navigated === index}"
@click="() => toggle(key)"/>
<div v-if="multiple" class="selection">
<div v-for="(key, index) of modelValue as Index[]" :key="key" :class="{navigated: selCount + navigated === index}" @click="() => toggle(key)"
v-text="options[key].display"/>
</div>
<div class="searchbar">
<div class="expand button" :tabindex="expanded ? undefined : -1">
<i-material-symbols-expand-circle-down-outline width="1em" height="1em"/>
</div>
<input v-if="multiple || modelValue === null" @click="expand" :placeholder="placeholder" v-model="search" ref="input"/>
<button v-else v-text="options[modelValue]?.display" ref="valueButton"
@click="() => toggle(modelValue)"/>
<input v-if="multiple || modelValue === null" ref="input" v-model="search" :placeholder="placeholder" @click="expand"/>
<button v-else ref="valueButton" @click="() => toggle(modelValue)"
v-text="options[modelValue]?.display"/>
</div>
</div>
<Transition name="fade-fast">
<div tabindex="-1" class="dropdown" v-if="expanded">
<div v-if="expanded" tabindex="-1" class="dropdown">
<div v-for="([key, option], index) in Object.entries(options)" :key="key"
:class="{selected: multiple ? modelValue?.some((x: Index) => x == key) : key == modelValue, navigated: navigated === index + 1}"
@click="() => toggle(key)">

View file

@ -70,11 +70,11 @@ watchEffect(() => {
<label v-text="label"/>
<div class="pillbar">
<button v-for="[index, variant] of Object.entries(variants)" :key="index" :class="{selected: currentVariant === index}" @click="() => currentVariant = index">
<component v-if="variant.icon" :is="variant.icon"/>
<component :is="variant.icon" v-if="variant.icon"/>
<template v-else>{{ variant.display }}</template>
</button>
</div>
<NicerForm v-if="currentVariant && variants[currentVariant]?.fields" :fields="variants[currentVariant].fields" v-model="formValue" :key="currentVariant"/>
<NicerForm v-if="currentVariant && variants[currentVariant]?.fields" :key="currentVariant" v-model="formValue" :fields="variants[currentVariant].fields"/>
</div>
</template>
<style scoped>

View file

@ -38,5 +38,5 @@ watch($$(options), (val) => { if(!equals(val, props.options)) emit('update:optio
</script>
<template>
<DropdownInput :multiple="true" :options="options" :search-provider="searchProvider" v-model="modelValue"/>
<DropdownInput v-model="modelValue" :multiple="true" :options="options" :search-provider="searchProvider"/>
</template>

View file

@ -50,7 +50,7 @@ watch($$(modelValue), (val) => {
<template>
<div class="form">
<component v-if="heading" :is="`h${headingLevel}`">{{ heading }}</component>
<component :is="`h${headingLevel}`" v-if="heading">{{ heading }}</component>
<div class="form inner-form">
<template v-for="[index, field] of Object.entries(fields)" :key="index">
<label v-if="field.label && field.is !== 'EnumInput'" v-text="field.label"/>

View file

@ -10,7 +10,7 @@ let { modelValue, min, max } = $(props);
</script>
<template>
<input type="number" v-model.number="modelValue" :min="min" :max="max">
<input v-model.number="modelValue" type="number" :min="min" :max="max">
</template>
<style scoped>

View file

@ -23,7 +23,7 @@ watch($$(modelValue), (val) => emit('update:modelValue', val));
</script>
<template>
<div>
<button class="option" v-for="[index, option] of Object.entries(options)" :key="index" :class="{selected: modelValue === index}" @click="() => modelValue = index">
<button v-for="[index, option] of Object.entries(options)" :key="index" class="option" :class="{selected: modelValue === index}" @click="() => modelValue = index">
<component :is="option.icon"/>
{{ option.display }}
</button>

View file

@ -38,5 +38,5 @@ watch($$(options), (val) => { if(!equals(val, props.options)) emit('update:optio
</script>
<template>
<DropdownInput :multiple="false" :options="options" :search-provider="searchProvider" v-model="modelValue"/>
<DropdownInput v-model="modelValue" :multiple="false" :options="options" :search-provider="searchProvider"/>
</template>

View file

@ -42,7 +42,7 @@ function tallyChildren(routes: NavRoute[]) {
<template>
<div :class="{'nav-dropdown': 1, 'nav-dropdown-expanded': expanded}" :style="`--predicted-height: ${2.5 * tallyChildren(children)}rem;`">
<div class="button" @click="expanded = !expanded">
<component v-if="(typeof icon !== 'string')" :is="icon"/>
<component :is="icon" v-if="(typeof icon !== 'string')"/>
<template v-else>{{ icon }}</template>
<span>
{{ caption }}

View file

@ -25,11 +25,11 @@ watch($$(lowerDepths), () => emit('update:expandedDepth', Math.max(...Object.ent
<template>
<template v-if="routes">
<template v-for="[index, route] of routes.entries()" :key="route.href">
<router-link v-if="route.href" :to="route.href" class="button" @click="clickHandler" :title="route.caption">
<router-link v-if="route.href" :to="route.href" class="button" :title="route.caption" @click="clickHandler">
<component :is="route.icon"/>
{{ route.caption }}
</router-link>
<NavDropdown v-else v-bind="route" @update:expanded-depth="(val) => lowerDepths[index] = val" :click-handler="clickHandler"/>
<NavDropdown v-else v-bind="route" :click-handler="clickHandler" @update:expanded-depth="(val) => lowerDepths[index] = val"/>
</template>
</template>
</template>

View file

@ -11,7 +11,7 @@ watchEffect(() => useTitle(`${title} - nfSense`));
</script>
<template>
<Portal to="page-header">
<h1 v-if="title !== ''" v-text="title" :class="{'flex-grow': !noSpacer}"/>
<h1 v-if="title !== ''" :class="{'flex-grow': !noSpacer}" v-text="title"/>
<slot/>
</Portal>
</template>

View file

@ -65,7 +65,7 @@ onMounted(async() => {
<div v-else-if="editTypes[subsystem][entity]">
<PageHeader :title="'Update ' + editTypes[subsystem][entity].name">
</PageHeader>
<NicerForm class="scroll cl-secondary" :fields="editTypes[subsystem][entity].fields" v-model="vm"/>
<NicerForm v-model="vm" class="scroll cl-secondary" :fields="editTypes[subsystem][entity].fields"/>
<div class="actions">
<div class="flex-grow"/>
<button @click="update">Submit</button>

View file

@ -27,7 +27,7 @@ async function create() {
<div v-if="editTypes[subsystem][entity]">
<PageHeader :title="'Create ' + editTypes[subsystem][entity].name">
</PageHeader>
<NicerForm class="scroll cl-secondary" :fields="editTypes[subsystem][entity].fields" v-model="vm"/>
<NicerForm v-model="vm" class="scroll cl-secondary" :fields="editTypes[subsystem][entity].fields"/>
<div class="actions">
<div class="flex-grow"/>
<button @click="create">Submit</button>

View file

@ -67,7 +67,7 @@ onMounted(async() => {
</script>
<template>
<TableView title="Pending Changes" :columns="columns" :loading="loading" v-model:data="displayData" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:data="displayData" title="Pending Changes" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<button @click="apply">Apply</button>
<button @click="discard">Discard</button>

View file

@ -59,11 +59,11 @@ onMounted(async() => {
<template>
<div>
<TableView title="DNAT Rules" :columns="columns" :loading="loading" @dragged-row="draggedRow" v-model:selection="selection" v-model:data="rules" :table-props="{sort:true, sortSelf: true, draggable: true}">
<TableView v-model:selection="selection" v-model:data="rules" title="DNAT Rules" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true, draggable: true}" @dragged-row="draggedRow">
<button @click="load">Refresh</button>
<router-link class="button" to="/firewall/destination_nat_rules/edit">Create</router-link>
<router-link class="button" :class="{ disabled: selection.length != 1 }" :to="'/firewall/destination_nat_rules/edit/' + selection[0]">Edit</router-link>
<button @click="deleteRule" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="deleteRule">Delete</button>
</TableView>
</div>
</template>

View file

@ -59,11 +59,11 @@ onMounted(async() => {
<template>
<div>
<TableView title="SNAT Rules" :columns="columns" :loading="loading" @dragged-row="draggedRow" v-model:selection="selection" v-model:data="rules" :table-props="{sort:true, sortSelf: true, draggable: true}">
<TableView v-model:selection="selection" v-model:data="rules" title="SNAT Rules" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true, draggable: true}" @dragged-row="draggedRow">
<button @click="load">Refresh</button>
<router-link class="button" to="/firewall/source_nat_rules/edit">Create</router-link>
<router-link class="button" :class="{ disabled: selection.length != 1 }" :to="'/firewall/source_nat_rules/edit/' + selection[0]">Edit</router-link>
<button @click="deleteRule" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="deleteRule">Delete</button>
</TableView>
</div>
</template>

View file

@ -63,10 +63,10 @@ onMounted(async() => {
</script>
<template>
<TableView title="Interfaces" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="displayData" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="displayData" title="Interfaces" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/network/interfaces/edit">Create</router-link>
<button @click="editInterface" :disabled="selection.length != 1">Edit</button>
<button @click="deleteInterface" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="editInterface">Edit</button>
<button :disabled="selection.length != 1" @click="deleteInterface">Delete</button>
</TableView>
</template>

View file

@ -42,10 +42,10 @@ onMounted(async() => {
</script>
<template>
<TableView title="Static Routes" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="staticRoutes" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="staticRoutes" title="Static Routes" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/network/static_routes/edit">Create</router-link>
<router-link class="button" :class="{ disabled: selection.length != 1 }" :to="'/network/static_routes/edit/' + selection[0]">Edit</router-link>
<button @click="deleteStaticRoutes" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="deleteStaticRoutes">Delete</button>
</TableView>
</template>

View file

@ -82,10 +82,10 @@ onMounted(async() => {
</script>
<template>
<TableView title="Addresses" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="displayData" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="displayData" title="Addresses" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/object/addresses/edit">Create</router-link>
<button @click="editAddress" :disabled="selection.length != 1">Edit</button>
<button @click="deleteAddress" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="editAddress">Edit</button>
<button :disabled="selection.length != 1" @click="deleteAddress">Delete</button>
</TableView>
</template>

View file

@ -85,10 +85,10 @@ onMounted(async() => {
</script>
<template>
<TableView title="Services" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="displayData" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="displayData" title="Services" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/object/services/edit">Create</router-link>
<button @click="editService" :disabled="selection.length != 1">Edit</button>
<button @click="deleteService" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="editService">Edit</button>
<button :disabled="selection.length != 1" @click="deleteService">Delete</button>
</TableView>
</template>

View file

@ -41,11 +41,11 @@ onMounted(async() => {
<template>
<div>
<TableView title="DHCP Servers" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="servers" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="servers" title="DHCP Servers" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/service/dhcp_servers/edit">Create</router-link>
<router-link class="button" :class="{ disabled: selection.length != 1 }" :to="'/service/dhcp_servers/edit/' + selection[0]">Edit</router-link>
<button @click="deleteRule" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="deleteRule">Delete</button>
</TableView>
</div>
</template>

View file

@ -41,11 +41,11 @@ onMounted(async() => {
<template>
<div>
<TableView title="DNS Servers" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="servers" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="servers" title="DNS Servers" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/service/dns_servers/edit">Create</router-link>
<router-link class="button" :class="{ disabled: selection.length != 1 }" :to="'/service/dns_servers/edit/' + selection[0]">Edit</router-link>
<button @click="deleteRule" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="deleteRule">Delete</button>
</TableView>
</div>
</template>

View file

@ -41,11 +41,11 @@ onMounted(async() => {
<template>
<div>
<TableView title="NTP Servers" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="servers" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="servers" title="NTP Servers" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/service/ntp_servers/edit">Create</router-link>
<router-link class="button" :class="{ disabled: selection.length != 1 }" :to="'/service/ntp_servers/edit/' + selection[0]">Edit</router-link>
<button @click="deleteRule" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="deleteRule">Delete</button>
</TableView>
</div>
</template>

View file

@ -45,10 +45,10 @@ onMounted(async() => {
</script>
<template>
<TableView title="Users" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="users" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="users" title="Users" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/system/users/edit">Create</router-link>
<button @click="editUser" :disabled="selection.length != 1">Edit</button>
<button @click="deleteUser" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="editUser">Edit</button>
<button :disabled="selection.length != 1" @click="deleteUser">Delete</button>
</TableView>
</template>

View file

@ -22,7 +22,7 @@ function genSP(indexIsChar: boolean): SearchProvider {
<template>
<div>
<PageHeader title="Test Page"/>
<NicerForm :fields="{
<NicerForm v-model="vm" :fields="{
Single: { is: 'SingleSelect', label: 'SingleSelect', props: { options: testValues, searchProvider: genSP(true) } },
Multiple: { is: 'MultiSelect', label: 'Multiselect', props: { options: testValues, searchProvider: genSP(false) } },
adv: { is: 'Heading', props: { caption: 'Subsection' } },
@ -42,7 +42,7 @@ function genSP(indexIsChar: boolean): SearchProvider {
Text: { is: 'TextBox', label: 'Text' },
} } },
} } },
}" v-model="vm"/>
}"/>
{{ vm }}
<button @click="() => { vm.Multiple = [1]; }">Click me</button>
<button @click="() => { vm.Multiple = [42]; }">Click me but EEEEVIL</button>

View file

@ -62,10 +62,10 @@ onMounted(async() => {
</script>
<template>
<TableView title="Wireguard Interfaces" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="displayData" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="displayData" title="Wireguard Interfaces" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/vpn/wireguard.interfaces/edit">Create</router-link>
<button @click="editInterface" :disabled="selection.length != 1">Edit</button>
<button @click="deleteInterface" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="editInterface">Edit</button>
<button :disabled="selection.length != 1" @click="deleteInterface">Delete</button>
</TableView>
</template>

View file

@ -63,10 +63,10 @@ onMounted(async() => {
</script>
<template>
<TableView title="Peers" :columns="columns" :loading="loading" v-model:selection="selection" v-model:data="displayData" :table-props="{sort:true, sortSelf: true}">
<TableView v-model:selection="selection" v-model:data="displayData" title="Peers" :columns="columns" :loading="loading" :table-props="{sort:true, sortSelf: true}">
<button @click="load">Refresh</button>
<router-link class="button" to="/vpn/wireguard.peers/edit">Create</router-link>
<button @click="editPeer" :disabled="selection.length != 1">Edit</button>
<button @click="deletePeer" :disabled="selection.length != 1">Delete</button>
<button :disabled="selection.length != 1" @click="editPeer">Edit</button>
<button :disabled="selection.length != 1" @click="deletePeer">Delete</button>
</TableView>
</template>

View file

@ -15,7 +15,6 @@
"forceConsistentCasingInFileNames": true,
"types": [
"vite/client",
"vue/ref-macros",
"vite-plugin-pages/client",
"unplugin-vue-macros/macros-global"
],