Laravel+Nuxt快速上手

前言 :

因為前一篇laravel 7 + VueJs開發紀錄

完成了一個網站前後台開發作業,但VueJs的SEO問題卻有點難處理,下個專案必須考慮SEO狀況因此單純用VueJs處理前端就已經不敷使用

研究了一下SSR的處理方式,決定透過Nuxt來處理Vue的SSR讓SEO更友善,本篇將紀錄初期開發踩坑全記錄

如何整合Laravel?

Nuxt是不是可以像Vue一樣,將前後端兩個project整合成單一網站來開發?

一開始是這麼想到,畢竟開發者只有我一個人如果還有拆兩塊寫有點麻煩,因此找到gitHub上已經有人整合好的plugin可以使用

https://github.com/m2sd/nuxt-laravel

https://github.com/m2sd/laravel-nuxt

先說結論 : 目前無法使用Nuxt universal模式,也就是無法處理SSR的部分,因此我放棄了

最終我只有在laravel資料夾底下的resources/nuxt 來建立Nuxt專案,整合git repo到同一個專案底下方便管理

建立Nuxt專案

依照Nuxt官網提示很容易只要一個指令就可以將Nuxt初始化安裝起來

切換到laravel/resources資料夾底下下指令

當然踩坑了npx丟了錯誤出來,還好gitHub上也不少人遇到一樣的錯誤

https://github.com/nuxt/create-nuxt-app/issues/383

https://github.com/serverless/serverless/issues/6989

先把create-nuxt-app裝起來就可以了

接著系統會提示使用的專案資料夾名稱以及其他需要的相依套件

這次我只有裝axios且server使用NodeJs,有需要其他套件就自行選擇

安裝好之後且換到laravel/resources/nuxt資料夾

應該就可以透過 http://localhost:3000 看到Nuxt網站已經建立完成

Docker環境也會踩坑嗎?

當然不缺席,如果你跟我一樣開發環境是架構在docker-compose(php7 + nginx)的話需要注意幾個地方

1. 為了避免每次重開docker都需要安裝一次create-nuxt-app 所以我將指令加入php的Dockerfile

2. 因為Nuxt測試與正式環境都架構在3000 port底下所以記得要把php的Dockerfile expose 3000 port

3. docker-compose記得將3000 port加入對應的php container

4. 最後,因為Nuxt 並非扔回3000 port而已,而是http://localhost:3000/,所以要將php的Dockerfile加入

這樣應該就可以透過http://localhost:3000連線了,雖然Nuxt在build的時候會顯示的是container的IP位置

Nuxt的Router怎麼處理

基本上Nuxt不必像Vue一樣需要手動建立每一個連結的Route設定,他會按照page資料夾底下的文件結構自己長出來,基本上如果沒有特殊需求依照官網的指示來設定page資料夾底下的vue檔案就可以了

https://nuxtjs.org/guide/routing/

But! 我個人習慣依照Route的結構來設定全站的使用權限,因此我還是走自行建立Route的方式

https://github.com/nuxt-community/router-module

首先,安裝需要的package

接著到resources/nuxt也就是nuxt的根目錄找到nuxt.conf.js,在buildModules 陣列中加入以下

接著就可以在nuxt根目錄建立router.js 建立自己需要的路由資訊了Example

Nuxt如何處裡.env檔

.env可以用來記錄後端API的位置以及其他環境資訊,使用.env可以分開正式上線後跟開發階段的不同參數,vue整合到laravel後,可以直接讀取laravel的.env檔案,那Nuxt怎麼處理?

https://github.com/nuxt-community/dotenv-module

安裝套件

接著到nuxt.conf.js的buildModules加入以下

最後,就可以在nuxt跟目錄底下建立.env檔案,如果有個變數名稱為MIX_API_NAME的話個可已透過process.env.MIX_API_NAME來取得參數值

Nuxt的localStorage

在vue中,可以將需要存在瀏覽器內的資料(ex:登入資訊)存放到localstorage中,但Nuxt是沒有的,如果需要儲存資料可以使用server side的session 或cookie,畢竟Nuxt是Server與Client並存的,所幸也有人已經完成package可以存取localstorage,但是有些需要注意的地方

https://github.com/rubystarashe/nuxt-vuex-localstorage

首先,安裝套件

接著編輯nuxt.conf.js中的models,加入以下資訊

其中,’adminUser’是我會用來存取localstorage的vuex module,可以把所有有用上的module都填在這個陣列中

以這個範例來看,adminUser中的state資料就會被存放到localstorage中不會揮發

但是,需要注意的是如果Nuxt跑在usiversal模式底下,網頁載入的時候是從server端將資料渲染好再傳回瀏覽器,這時候因為localstorage屬於client端的資料就會無法取得

如果component需要取得localsotrage資料我會在mounted()中將存在localstorage中的資訊取出存回到component的data中,方便頁面渲染資料時直接使用data中的資料

Nuxt使用vue的套件

https://zh.nuxtjs.org/guide/plugins/

根據官網描述,Nuxt是可以直接使用vue的npm套件的,舉例來說如果我們需要用到vue-simple-alert

https://github.com/constkhi/vue-simple-alert

首先,一樣先安裝套件

接著在nuxt/plugin資料夾中建立一個檔案命名為vue-simple-alert.js,內容為

接著編輯跟目錄底下的nuxt.conf.js,在plugins中加入

在component中就可以依照vue套件的原生方式使用了,但我偶爾會遇到錯誤,目前還不知道發生什麼事情

Nuxt中的Server / Client 取得API資料

Nuxt中asyncData與fetch可以說是精華所在,Server端會先跑過這兩個function,換句話說可以在這邊先呼叫api取得資料這樣就可以正確在server端渲染完成了

詳細可以參考這篇文章

https://medium.com/@jackercleaninglab/ssr-nuxt-js-%E8%B6%85%E5%85%A5%E9%96%80-84a0823b45ed

舉例來說,我會這樣子取得資料

其中,有幾個地方說明一下

params : 是指route中設定好的參數,舉例來說route中如果設定了/:id

就可以透過params.id 來取得網址中帶入的id資料

query: 網址中的_GET參數,如果網址中有?page=2

就可以透過query.page來取得

但是,這次遇到一個狀況是取得資料後我想放回component中的data而不是渲染到網頁中

這部分做法就回到跟vue相同,在mounted中透過dispatch取得資料後watch變數變更的時候再寫回data中即可

如果還有更好的做法會再更新上來

 

以上幾點,紀錄一下初次開發

下一步將會是在docker中獨立建立container處理Nuxt 伺服器,並且做到docker-compose up後可以自動build 並start Nuxt