Home

Issue: 3040

Can't reliably detect currently rendered page

[issue link]

I would like to reliably know which layout and page is currently being rendered outside the page component itself. I would like to make adjustments to various layout components, such as styling the body tag and tweaking the state of a header component and so on.

Right now I’m using a mixin called currentPage with rudimentary detection that looks like this:

currentPage () {
  if (this.$nuxt && this.$nuxt.$route) {

    // Home page
    if (!this.$nuxt.$route.path || this.$nuxt.$route.path === '/') {
      return 'home'

    // Current page (or current route)
    } else if (this.$nuxt.$route.name) {
      return this.$nuxt.$route.name
    }

  }

  // Assume the user is on error page
  return 'error'
}

This works in most cases, however it breaks when I’m triggering the error using error() in asyncData. In my example, I’m triggering an error from asyncData if I can’t find a resource from my CMS, but my currentPage computed thinks the user is on the original page.

Something like this:

asyncData ({ error }) {
  return Promises.all([ /* fetch data from Contentful*/ ]).then((contentfulData) => {
    if (!contentfulData.items.length) {
      error({
        statusCode: 404,
        message: 'Not found'
      })
    }
  })
}

In this case, the user will see an error page, but I can’t find any way of actually detecting that this is happening outside of my error.vue code. The router still thinks the user is on the original page (which is half true, since the URL did not change). I would imagine there are other scenarios where the current route does not match the rendered page as well.

I can think of a few hacky workarounds to some of the things I’m trying to use this for, but it feels a little bit weird that the name of the page component that is being rendered is not available anywhere. I also tried getting the error data from under this.$nuxt.nuxt.err, but this does not seem to be reactive.

This question is available on Nuxt.js community (#c2635)