-
Notifications
You must be signed in to change notification settings - Fork 11
5. Async Data
You may want to fetch data and render it on the server-side. Nuxt.js adds an asyncData
method to let you handle async operations before setting the component data.
In our page index.vue
we will add the script
where we will work all our javascript code:
<script>
const gistsLocal = [
{
'url': 'https://api.github.com/gists/51891107b240fbd61c3c3fd725a6bf4a',
'commits_url': 'https://api.github.com/gists/51891107b240fbd61c3c3fd725a6bf4a/commits',
'id': '51891107b240fbd61c3c3fd725a6bf4a',
'git_pull_url': 'https://gist.github.com/51891107b240fbd61c3c3fd725a6bf4a.git',
'git_push_url': 'https://gist.github.com/51891107b240fbd61c3c3fd725a6bf4a.git',
'html_url': 'https://gist.github.com/51891107b240fbd61c3c3fd725a6bf4a',
'files': {
'talk-nodeJS-medellin.md': {
'filename': 'talk-nodeJS-medellin.md',
'type': 'text/plain',
'language': 'Markdown',
'raw_url': 'https://gist.githubusercontent.com/khriztianmoreno/51891107b240fbd61c3c3fd725a6bf4a/raw/fd1420ae3a3e352c23fd84090a891f9b84cdee09/talk-nodeJS-medellin.md',
'size': 9082
}
},
'public': true,
'created_at': '2017-09-28T03:16:39Z',
'updated_at': '2017-10-26T03:53:24Z',
'description': 'Talk: Estructurando la base de nuestro proyecto',
'comments': 0,
'user': null,
'comments_url': 'https://api.github.com/gists/51891107b240fbd61c3c3fd725a6bf4a/comments',
'owner': {
'login': 'khriztianmoreno',
'id': 1481964,
'avatar_url': 'https://avatars1.githubusercontent.com/u/1481964?v=4',
'gravatar_id': '',
'url': 'https://api.github.com/users/khriztianmoreno',
'html_url': 'https://github.com/khriztianmoreno',
'followers_url': 'https://api.github.com/users/khriztianmoreno/followers',
'following_url': 'https://api.github.com/users/khriztianmoreno/following{/other_user}',
'gists_url': 'https://api.github.com/users/khriztianmoreno/gists{/gist_id}',
'starred_url': 'https://api.github.com/users/khriztianmoreno/starred{/owner}{/repo}',
'subscriptions_url': 'https://api.github.com/users/khriztianmoreno/subscriptions',
'organizations_url': 'https://api.github.com/users/khriztianmoreno/orgs',
'repos_url': 'https://api.github.com/users/khriztianmoreno/repos',
'events_url': 'https://api.github.com/users/khriztianmoreno/events{/privacy}',
'received_events_url': 'https://api.github.com/users/khriztianmoreno/received_events',
'type': 'User',
'site_admin': false
},
'truncated': false
},
{
'url': 'https://api.github.com/gists/08b5102c533d489d25db8e467b207648',
'forks_url': 'https://api.github.com/gists/08b5102c533d489d25db8e467b207648/forks',
'commits_url': 'https://api.github.com/gists/08b5102c533d489d25db8e467b207648/commits',
'id': '08b5102c533d489d25db8e467b207648',
'git_pull_url': 'https://gist.github.com/08b5102c533d489d25db8e467b207648.git',
'git_push_url': 'https://gist.github.com/08b5102c533d489d25db8e467b207648.git',
'html_url': 'https://gist.github.com/08b5102c533d489d25db8e467b207648',
'files': {
'GIF-Screencast-OSX.md': {
'filename': 'GIF-Screencast-OSX.md',
'type': 'text/plain',
'language': 'Markdown',
'raw_url': 'https://gist.githubusercontent.com/khriztianmoreno/08b5102c533d489d25db8e467b207648/raw/fa006ed2e0f785f778b58545861583bd0c4393c8/GIF-Screencast-OSX.md',
'size': 2817
},
'Performance-vs-quality.md': {
'filename': 'Performance-vs-quality.md',
'type': 'text/plain',
'language': 'Markdown',
'raw_url': 'https://gist.githubusercontent.com/khriztianmoreno/08b5102c533d489d25db8e467b207648/raw/9868405d0b45a6e78774c7b2cab704464ddaeef7/Performance-vs-quality.md',
'size': 3703
}
},
'public': true,
'created_at': '2017-09-08T17:00:06Z',
'updated_at': '2017-09-08T17:00:06Z',
'description': 'OS X Screencast to animated GIF',
'comments': 0,
'user': null,
'comments_url': 'https://api.github.com/gists/08b5102c533d489d25db8e467b207648/comments',
'owner': {
'login': 'khriztianmoreno',
'id': 1481964,
'avatar_url': 'https://avatars1.githubusercontent.com/u/1481964?v=4',
'gravatar_id': '',
'url': 'https://api.github.com/users/khriztianmoreno',
'html_url': 'https://github.com/khriztianmoreno',
'followers_url': 'https://api.github.com/users/khriztianmoreno/followers',
'following_url': 'https://api.github.com/users/khriztianmoreno/following{/other_user}',
'gists_url': 'https://api.github.com/users/khriztianmoreno/gists{/gist_id}',
'starred_url': 'https://api.github.com/users/khriztianmoreno/starred{/owner}{/repo}',
'subscriptions_url': 'https://api.github.com/users/khriztianmoreno/subscriptions',
'organizations_url': 'https://api.github.com/users/khriztianmoreno/orgs',
'repos_url': 'https://api.github.com/users/khriztianmoreno/repos',
'events_url': 'https://api.github.com/users/khriztianmoreno/events{/privacy}',
'received_events_url': 'https://api.github.com/users/khriztianmoreno/received_events',
'type': 'User',
'site_admin': false
},
'truncated': false
}
]
</script>
Nuxt.js offers you different ways to use asyncData. Choose the one you're the most familiar with: Promise
, async/await
o callback
<script>
// ... const gistsLocal
export default {
data () {
return { gists: gistsLocal }
},
asyncData () {
return gistsLocal
}
}
</script>
We are going to make an improvement to our current main page to use a component that we can reuse later, that's why in the components
folder we created the file GistArticle.vue
with the following content:
<template>
<article class="post post-large">
<div v-if="gist">
<div class="post-date">
<span class="day">{{ gist.created_at | date('D') }}</span>
<span class="month">{{ gist.created_at | date('MMM') }}</span>
</div>
<div class="post-content">
<h2>
<nuxt-link :to="{ path: '/post/'+ gist.id }">{{gist.description}}</nuxt-link>
</h2>
<!-- Content Raw -->
<p>{{gist.description}}</p>
<!-- /Content Raw -->
<div class="post-meta">
<span>
<i class="fa fa-user"></i>
By <a :href="gist.owner.html_url" target="_blank">{{ gist.owner.login }}</a>
</span>
<span>
<i class="fa fa-comments"></i>
<a :href="gist.comments_url" target="_blank">{{ gist.comments }} Comments</a>
</span>
<a :href="'/post/'+ gist.id +''" class="btn btn-xs btn-primary pull-right">Read more...</a>
</div>
</div>
</div>
</article>
</template>
<script>
export default {
props: ['gist']
}
</script>
<style lang="scss" scoped>
$primary-color: #41b883;
$secundary-color: #35495f;
$hover-color: #3c8070;
.pagination {
margin: -10px 0 20px;
}
.btn-primary {
background-color: $primary-color;
border-color: $primary-color;
&:hover {
background-color: $hover-color;
border-color: $hover-color;
}
}
article {
border-bottom: 1px solid #DDD;
margin-bottom: 50px;
padding-bottom: 10px;
&.post {
h2 a {
text-decoration: none;
}
.post-meta {
font-size: 0.9em;
margin-bottom: 7px;
>span {
display: inline-block;
padding-right: 8px;
}
i {
margin-right: 3px;
}
}
.post-date {
box-shadow: 0 1px 2px 0 rgba(0, 0, 0, 0.1);
float: left;
margin-right: 10px;
text-align: center;
.month {
background-color: $primary-color;
border-radius: 0 0 2px 2px;
box-shadow: 0 -1px 0 0 rgba(0, 0, 0, 0.07) inset;
color: #FFF;
font-size: 0.9em;
padding: 0 10px 2px;
}
.day {
background: #F4F4F4;
border-radius: 2px 2px 0 0;
color: $primary-color;
display: block;
font-size: 16px;
font-weight: 500;
font-weight: bold;
padding: 10px;
}
}
}
&.post-large {
margin-left: 60px;
h2 {
margin-bottom: 5px;
}
.post-date {
margin-left: -60px;
}
}
}
</style>
And now our main page index.vue
should be as follows:
<template>
<section>
<div class="main-container">
<div class="blog-posts">
<gist-article :key="item.id" v-for="(item, index) in gists" :gist="item" />
</div>
</div>
</section>
</template>
<script>
import GistArticle from '~/components/GistArticle.vue'
const gistsLocal = [
{
'url': 'https://api.github.com/gists/51891107b240fbd61c3c3fd725a6bf4a',
'commits_url': 'https://api.github.com/gists/51891107b240fbd61c3c3fd725a6bf4a/commits',
'id': '51891107b240fbd61c3c3fd725a6bf4a',
'git_pull_url': 'https://gist.github.com/51891107b240fbd61c3c3fd725a6bf4a.git',
'git_push_url': 'https://gist.github.com/51891107b240fbd61c3c3fd725a6bf4a.git',
'html_url': 'https://gist.github.com/51891107b240fbd61c3c3fd725a6bf4a',
'files': {
'talk-nodeJS-medellin.md': {
'filename': 'talk-nodeJS-medellin.md',
'type': 'text/plain',
'language': 'Markdown',
'raw_url': 'https://gist.githubusercontent.com/khriztianmoreno/51891107b240fbd61c3c3fd725a6bf4a/raw/fd1420ae3a3e352c23fd84090a891f9b84cdee09/talk-nodeJS-medellin.md',
'size': 9082
}
},
'public': true,
'created_at': '2017-09-28T03:16:39Z',
'updated_at': '2017-10-26T03:53:24Z',
'description': 'Talk: Estructurando la base de nuestro proyecto',
'comments': 0,
'user': null,
'comments_url': 'https://api.github.com/gists/51891107b240fbd61c3c3fd725a6bf4a/comments',
'owner': {
'login': 'khriztianmoreno',
'id': 1481964,
'avatar_url': 'https://avatars1.githubusercontent.com/u/1481964?v=4',
'gravatar_id': '',
'url': 'https://api.github.com/users/khriztianmoreno',
'html_url': 'https://github.com/khriztianmoreno',
'followers_url': 'https://api.github.com/users/khriztianmoreno/followers',
'following_url': 'https://api.github.com/users/khriztianmoreno/following{/other_user}',
'gists_url': 'https://api.github.com/users/khriztianmoreno/gists{/gist_id}',
'starred_url': 'https://api.github.com/users/khriztianmoreno/starred{/owner}{/repo}',
'subscriptions_url': 'https://api.github.com/users/khriztianmoreno/subscriptions',
'organizations_url': 'https://api.github.com/users/khriztianmoreno/orgs',
'repos_url': 'https://api.github.com/users/khriztianmoreno/repos',
'events_url': 'https://api.github.com/users/khriztianmoreno/events{/privacy}',
'received_events_url': 'https://api.github.com/users/khriztianmoreno/received_events',
'type': 'User',
'site_admin': false
},
'truncated': false
},
{
'url': 'https://api.github.com/gists/08b5102c533d489d25db8e467b207648',
'forks_url': 'https://api.github.com/gists/08b5102c533d489d25db8e467b207648/forks',
'commits_url': 'https://api.github.com/gists/08b5102c533d489d25db8e467b207648/commits',
'id': '08b5102c533d489d25db8e467b207648',
'git_pull_url': 'https://gist.github.com/08b5102c533d489d25db8e467b207648.git',
'git_push_url': 'https://gist.github.com/08b5102c533d489d25db8e467b207648.git',
'html_url': 'https://gist.github.com/08b5102c533d489d25db8e467b207648',
'files': {
'GIF-Screencast-OSX.md': {
'filename': 'GIF-Screencast-OSX.md',
'type': 'text/plain',
'language': 'Markdown',
'raw_url': 'https://gist.githubusercontent.com/khriztianmoreno/08b5102c533d489d25db8e467b207648/raw/fa006ed2e0f785f778b58545861583bd0c4393c8/GIF-Screencast-OSX.md',
'size': 2817
},
'Performance-vs-quality.md': {
'filename': 'Performance-vs-quality.md',
'type': 'text/plain',
'language': 'Markdown',
'raw_url': 'https://gist.githubusercontent.com/khriztianmoreno/08b5102c533d489d25db8e467b207648/raw/9868405d0b45a6e78774c7b2cab704464ddaeef7/Performance-vs-quality.md',
'size': 3703
}
},
'public': true,
'created_at': '2017-09-08T17:00:06Z',
'updated_at': '2017-09-08T17:00:06Z',
'description': 'OS X Screencast to animated GIF',
'comments': 0,
'user': null,
'comments_url': 'https://api.github.com/gists/08b5102c533d489d25db8e467b207648/comments',
'owner': {
'login': 'khriztianmoreno',
'id': 1481964,
'avatar_url': 'https://avatars1.githubusercontent.com/u/1481964?v=4',
'gravatar_id': '',
'url': 'https://api.github.com/users/khriztianmoreno',
'html_url': 'https://github.com/khriztianmoreno',
'followers_url': 'https://api.github.com/users/khriztianmoreno/followers',
'following_url': 'https://api.github.com/users/khriztianmoreno/following{/other_user}',
'gists_url': 'https://api.github.com/users/khriztianmoreno/gists{/gist_id}',
'starred_url': 'https://api.github.com/users/khriztianmoreno/starred{/owner}{/repo}',
'subscriptions_url': 'https://api.github.com/users/khriztianmoreno/subscriptions',
'organizations_url': 'https://api.github.com/users/khriztianmoreno/orgs',
'repos_url': 'https://api.github.com/users/khriztianmoreno/repos',
'events_url': 'https://api.github.com/users/khriztianmoreno/events{/privacy}',
'received_events_url': 'https://api.github.com/users/khriztianmoreno/received_events',
'type': 'User',
'site_admin': false
},
'truncated': false
}
]
export default {
data () {
return { gists: gistsLocal }
},
asyncData () {
return gistsLocal
},
components: {
GistArticle
}
}
</script>
<style>
.main-container {
align-items: center;
display: flex;
flex-direction: column;
justify-content: flex-start;
min-height: 30vh;
}
</style>
To see these steps complete, you can change to the 5-async-data
branch in this repository.
Hello, my name is Cristian Moreno.
I'm a community leader and altruistic speaker, JavaScript/Node.js evangelist and FullStack Javascript Developer. Currently co-organize Medellin.js (Biggest JavaScript user group in Colombia), Avanet and Azure Cloud Medellin communities.
I love developing things, especially ideas, giving them a new perspective and making them shine! products and applications come after I transform ideas into code; I'm passionate about software development and related stuff.