typescriptvue.jsvuetifyjs3

Where can I find the types of Vuetify components’ events and props?


I'm using v-data-table-server component, but can't find some types for events or props. For instance, I need the type of object that @update:options returns. In the relevant section of Vuetify docs, there is no specific type (it's just any):

screenshot from docs

template

<VCard title="">
  <v-data-table-server
    :headers="headers"
    :items="serverItems"
    :items-length="totalItems"
    v-model:items-per-page="itemsPerPage"
    :loading="loading"
    :search="search"
    @update:options="loadItems"
    item-value="name"
    :items-per-page-text="t('table.items-per-page-text')"
    :loading-text="t('table.loading-text')"
    :no-data-text="t('common.no-data')"
  >
    <template v-slot:loading>
      <v-skeleton-loader type="table-row@10"></v-skeleton-loader>
    </template>
    <template #top> </template>
  </v-data-table-server>
</VCard>

Script

<script setup lang="ts">
import { useI18n } from 'vue-i18n'
import type { DataTableHeader } from 'vuetify'
const { t } = useI18n()

const desserts = [
  {
    name: 'Frozen Yogurt',
    calories: 159,
    fat: 6,
    carbs: 24,
    protein: 4,
    iron: '1',
  },
  {
    name: 'Jelly bean',
    calories: 375,
    fat: 0,
    carbs: 94,
    protein: 0,
    iron: '0',
  },
  ...
]
const FakeAPI = {
  async fetch({ page, itemsPerPage }) {
    return new Promise(resolve => {
      setTimeout(() => {
        const start = (page - 1) * itemsPerPage
        const end = start + itemsPerPage
        const items = desserts.slice()
        const paginated = items.slice(start, end === -1 ? undefined : end)
        resolve({ items: paginated, total: items.length })
      }, 500)
    })
  },
}
const itemsPerPage = ref(5)
const headers: Ref<DataTableHeader[]> = ref([
  {
    title: 'Dessert (100g serving)',
    align: 'start',
    key: 'name',
    sortable: false,
  },
  { title: 'Calories', key: 'calories', align: 'end', sortable: false },
  { title: 'Fat (g)', key: 'fat', align: 'end', sortable: false },
  { title: 'Carbs (g)', key: 'carbs', align: 'end', sortable: false },
  { title: 'Protein (g)', key: 'protein', align: 'end', sortable: false },
  { title: 'Iron (%)', key: 'iron', align: 'end', sortable: false },
])
const search = ref('')
const serverItems = ref([])
const loading = ref(true)
const totalItems = ref(0)
function loadItems({ page, itemsPerPage }) {
  loading.value = true
  FakeAPI.fetch({ page, itemsPerPage }).then(({ items, total }) => {
    serverItems.value = items
    totalItems.value = total
    loading.value = false
  })
}
</script>

I searched the documentation and existing questions but couldn’t find a solution. If there’s another approach, I’d be happy to learn it.


Solution

  • The type of @update:options is just (options: any) => true in the codebase. Tracking down where this event is emitted from, it seems like the options parameter actually has a runtime shape like this:

    {
      page: number
      itemsPerPage: number
      sortBy: readonly SortItem[]
      groupBy: readonly SortItem[]
      search: string | undefined
    }
    

    Don't ask me why they didn't type that properly nor document it. Browsing around, it seems Vuetify's usage of TypeScript is lackadaisical at best, so perhaps this shouldn't be surprising.