Nuxt.js — Error Handling and Plugins

John Au-Yeung - Jan 19 '21 - - Dev Community

Check out my books on Amazon at https://www.amazon.com/John-Au-Yeung/e/B08FT5NT62

Subscribe to my email list now at http://jauyeung.net/subscribe/

Nuxt.js is an app framework that’s based on Vue.js.

We can use it to create server-side rendered apps and static sites.

In this article, we’ll look at how to handle async data errors and plugins with Nuxt.js.

Handling Errors

We can handle errors in our pages when we get async data.

To do that, we write:

<template>
  <div>{{ title }}</div>
</template>

<script>
import axios from "axios";

export default {
  async asyncData({ params, error }) {
    try {
      const { data } = await axios.get(
        `https://jsonplaceholder.typicode.com/posts/${params.id}`
      );
      return { title: data.title };
    } catch {
      error({ statusCode: 404, message: "Post not found" });
    }
  },
};
</script>
Enter fullscreen mode Exit fullscreen mode

We have an asyncData method with an object that has the error property.

error is a function that we can to render the error.

Assets

Nuxt uses vue-loader, file-loader, and url-loader Webpack loaders for asset serving.

Also, we can use the static folder for static assets.

To add assets, we can write:

<template>
  <div class="container">
    <img src="~/assets/kitten.jpg" />
  </div>
</template>

<script>
export default {};
</script>
Enter fullscreen mode Exit fullscreen mode

The ~ is a shorthand for the Nuxt root folder.

Static

We can also serve assets from the static folder.

For example, we can move our file to the static folder and write:

<template>
  <div class="container">
    <img src="/kitten.jpg" />
  </div>
</template>

<script>
export default {};
</script>
Enter fullscreen mode Exit fullscreen mode

The / is the static folder’s shorthand.

Plugins

We can add plugins into our app.

They may come as external packages like Axios.

Or we can use Vue plugins.

To use Vue plugins, we have to add them manually.

For example, if we want to add a tooltip to our app, we install the v-tooltip package by running:

npm install --save v-tooltip
Enter fullscreen mode Exit fullscreen mode

Then we create the plugins/vue-tooltip.js and add:

import Vue from 'vue'
import VTooltip from 'v-tooltip'

Vue.use(VTooltip)
Enter fullscreen mode Exit fullscreen mode

Then in nuxt.config.js , we add:

plugins: [
  '@/plugins/vue-tooltip.js'
],
Enter fullscreen mode Exit fullscreen mode

Then we can use it as usual by writing:

<template>
  <div class="container">
    <button v-tooltip="'hello world'">hello</button>
  </div>
</template>

<script>
export default {};
</script>
Enter fullscreen mode Exit fullscreen mode

Inject in $root & context

We can also make functions available across all of our app.

To do that, we can call the inject function.

We can create our own plugin by adding plugins/hello.js :

export default (context, inject) => {
  const hello = msg => console.log(`hello ${msg}!`)
  inject('hello', hello)
}
Enter fullscreen mode Exit fullscreen mode

Then we can add our plugin in nuxt.config.js :

plugins: [
  '@/plugins/hello.js'
],
Enter fullscreen mode Exit fullscreen mode

Then we can call our hello function by writing:

<template>
  <div class="container"></div>
</template>

<script>
export default {
  mounted() {
    this.$hello("james");
  },
};
</script>
Enter fullscreen mode Exit fullscreen mode

We also need:

context.$hello = hello
Enter fullscreen mode Exit fullscreen mode

in the function we exported if we use Nuxt 2.12 or earlier.

We can also use the $hello function with the asyncData function by writing:

<template>
  <div class="container"></div>
</template>

<script>
export default {
  mounted() {
    this.$hello("james");
  },
  asyncData({ $hello }) {
    $hello("asyncData");
  },
};
</script>
Enter fullscreen mode Exit fullscreen mode

The $hello is part of the context parameter of asyncData .

Conclusion

We can handle errors when we get data.

Also, we can create our own plugins and functions and inject them to our app.

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .