目錄
- 安裝nuxt3的pinia包
- 修改nuxt.config.ts的配置
- 在專案中建立pinia倉庫
- 建立本地的測試伺服器用於測試ssr
- 在nuxt專案中建立伺服器端請求介面
- 在
/article/[id]
路由頁面中實現伺服器端渲染 - 使用postman向
http://localhost:3000/article/95
傳送請求 - 修改路由配置實現頁面資料快取
安裝nuxt3的pinia包
pnpm i pinia @pinia/nuxt
yarn add pinia @pinia/nuxt
npm i pinia @pinia/nuxt
修改nuxt.config.ts的配置
// nuxt.config.ts
export default defineNuxtConfig({
// ... 其他配置
modules: [
// ...
'@pinia/nuxt',
],
})
在專案中建立pinia倉庫
// /stores/index.js
import { defineStore } from 'pinia'
export const useRootStore = defineStore('root', {
state: () => ({
msg: '測試msg資料',
articleData: {
id: undefined,
title: undefined,
content: undefined,
},
}),
getters: {},
})
建立本地的測試伺服器用於測試ssr
import express from 'express'
import cors from 'cors'
const article = {
title: 'hello world',
content:
'Eu pariatur aliquip enim enim officia laboris proident adipisicing duis aute ex labore nisi excepteur.',
}
const app = express()
app.use(cors())
app.use(express.json())
app.get('/article', cors(), (req, res) => {
const { id } = req.query
console.log('訪問/article ' + new Date().toString())
setTimeout(() => {
res.send({ code: 200, data: { id:Number(id), ...article } })
}, 1500)
})
app.listen(4520, err => {
console.log('server is running at port 4520')
})
在nuxt專案中建立伺服器端請求介面
// /server/article.get.js
export default defineEventHandler(async event => {
// console.log(event)
const { id } = getQuery(event)
return new Promise(async (resolve, reject) => {
const res = await $fetch(`http://127.0.0.1:4520/article?id=${id}`).catch(err => err)
if (res.code === 200) {
resolve(res)
} else {
reject(res)
}
})
})
在/article/[id]
路由頁面中實現伺服器端渲染
// /pages/article/[id].vue
<template>
<div id="articleContainer">
<p>{{ $rootStore?.msg }}</p>
<p>id:{{ $rootStore?.articleData?.id }}</p>
<p>標題:{{ $rootStore?.articleData?.title }}</p>
<p>內容:{{ $rootStore?.articleData?.content }}</p>
</div>
</template>
<script setup>
import { useRootStore } from '~/stores/index'
const articleStore = useArticleStore()
const $route = useRoute()
const $rootStore = useRootStore()
//#region 初始化資料
initData()
async function initData() {
const res = await useFetch(`/api/article?id=${$route.params.id}`)
const res_ = res.data.value
if (res_.code === 200) {
$rootStore.$patch({
articleData: { ...res_.data },
})
}
}
//#endregion
</script>
<style scoped lang="scss"></style>
使用postman向http://localhost:3000/article/95
傳送請求
- 註釋: localhost:3000是nuxt3專案的預設啟動地址
- 得到如下的html結構, 代表服務端渲染成功
<p data-v-inspector="pages/article/[id].vue:3:5">測試msg資料</p>
<p data-v-inspector="pages/article/[id].vue:4:5">id:95</p>
<p data-v-inspector="pages/article/[id].vue:5:5">標題:hello world</p>
<p data-v-inspector="pages/article/[id].vue:6:5">內容:Eu pariatur aliquip enim enim officia laboris proident adipisicing duis aute ex labore nisi excepteur.</p>
修改路由配置實現頁面資料快取
// nuxt.config.ts
routeRules: {
'/article/**': { ssr:true },
},
- 當路由設定為上面所示時, 每次向
/article/[id]
路由發起請求都會重新向伺服器呼叫介面,
// 每次重新整理頁面伺服器介面都會列印請求
訪問/article Tue Apr 16 2024 13:21:37 GMT+0800 (中國標準時間)
訪問/article Tue Apr 16 2024 13:23:28 GMT+0800 (中國標準時間)
訪問/article Tue Apr 16 2024 13:23:30 GMT+0800 (中國標準時間)
- 修改路由配置為
'/article/**': { swr: 60 }, // 頁面資料快取60s, 在快取資料有效期間不向伺服器發起新的請求
- 修改後, 在60s內無論重新整理多少次頁面, 伺服器介面只會列印一條請求
訪問/article Tue Apr 16 2024 13:28:53 GMT+0800 (中國標準時間)