nuxt icon indicating copy to clipboard operation
nuxt copied to clipboard

Why do I get `error.value.statusCode` does not exists and how to solve?

Open Barbapapazes opened this issue 1 year ago • 6 comments

Environment


  • Operating System: Linux
  • Node Version: v18.18.0
  • Nuxt Version: 3.8.2
  • CLI Version: 3.10.0
  • Nitro Version: 2.8.1
  • Package Manager: [email protected]
  • Builder: -
  • User Config: ssr, modules, ui, runtimeConfig, css, site, linkChecker, sitemap, colorMode, ogImage, vite, devtools
  • Runtime Modules: @nuxt/[email protected], @nuxtseo/[email protected]
  • Build Modules: -

Reproduction

  • Create a nuxt project
  • Create a composable like this one
export async function fetchRepoBySlug(slug: string) {
  const config = useRuntimeConfig()

  const data = await $fetch(`/repositories/${slug}`, {
    baseURL: config.public.apiBase,
  })

  const validatedData = myzod.object({
    data: myzod.object({
      name: myzod.string(),
      npmName: myzod.string().or(myzod.null()),
      stars: myzod.object({
        current: myzod.object({
          value: myzod.number(),
          fetchedAt: myzod.string(),
        }),
        previous: myzod.object({
          value: myzod.number(),
          fetchedAt: myzod.string(),
        }),
      }),
      downloads: myzod.object({
        current: myzod.object({
          value: myzod.number(),
          start: myzod.string(),
          end: myzod.string(),
        }),
        previous: myzod.object({
          value: myzod.number(),
          start: myzod.string(),
          end: myzod.string(),
        }),
      }),
      starsMetrics: myzod.array(myzod.object({
        value: myzod.number(),
        fetchedAt: myzod.string(),
      })),
      downloadsMetrics: myzod.array(myzod.object({
        value: myzod.number(),
        fetchedAt: myzod.string(),
      })),
    }),
  }).parse(data)

  return validatedData
}

And use it in a page

const route = useRoute()
const slug = route.params.slug as string
const { data: repo, error } = await useAsyncData(slug, () => fetchRepoBySlug(slug))

if (error.value) {
  // TODO: it's strange, why this happens?
  if (error.value.statusCode === 404) {
    throw createError({
      statusCode: 404,
      statusMessage: 'Repository not found',
      fatal: true,
    })
  }
}

Describe the bug

Hello,

When using the useAsyncData, the type for the error is not a FetchError, which seems logic, but how to solve this since the value statusCode exists?

Additional context

Full error

Property 'statusCode' does not exist on type 'Error'.ts(2339)

Logs

No response

Barbapapazes avatar Dec 27 '23 18:12 Barbapapazes

Can you provide a running reproduction please?

Something tells me that error.value is a union of various types and you have to narrow it down (because indeed, Error has no statusCode but H3Error has (checking e.g. via isNuxtError)

TheAlexLichter avatar Dec 28 '23 11:12 TheAlexLichter

I'm trying to reproduce but I don't know why it's seems a little bit tricky.

Why the error could be an H3Error? How could it be related to H3?

Barbapapazes avatar Dec 28 '23 17:12 Barbapapazes

Sometimes, it's a NuxtError, sometime a H3Error. Could I have some explanation on how TypeScript choose which type?

Barbapapazes avatar Dec 28 '23 17:12 Barbapapazes

Types when everything if fine (.nuxt/types/imports.d.ts) ([email protected])

image

When I got the error (same file) ([email protected])

image

Barbapapazes avatar Dec 28 '23 17:12 Barbapapazes

With [email protected]

image

Barbapapazes avatar Dec 28 '23 17:12 Barbapapazes

Okk, after retrying with [email protected], seems related to this version since it's working fine with [email protected].

I don't know why this happens and if it could happen again so I do not close this issue. Feel free to close it.

Barbapapazes avatar Dec 28 '23 18:12 Barbapapazes

Yes, we fixed the types in Nuxt v3.9.0 in https://github.com/nuxt/nuxt/pull/24396.

danielroe avatar Dec 29 '23 08:12 danielroe