1.最近在做一个前端项目,之前是用vue做的单页面应用程序,现在项目是需要做seo的,所以选择了nuxt,但是nuxt由于新增了服务器端,所以导致在写代码的时候不知道到底什么时候是在服务端运行,什么时候又在客户端运行
2.接来下是我利用实践得出的一些结论和理解,我先将生命周期放在这里:
2.1: 整个页面流程通俗来讲就是,当页面第一次加载或者重新reload页面时,会从上向下一次执行,但是你之后的路由跳转其实都是在client端中执行,和server端就没什么关系了,包括页面中的asyncData,其实我一开始以为asyncData是一直在server端运行,其实并不是,除了第一次加载,其他的通过路由跳转的asyncData都是在client端运行
2.2:如果你写的是一个插件,那么如果你设置了该插件的属性为sse:false,表示只会在客户端运行该插件,如果你设置为了true,则表示既会在客户端运行,也会在服务器端运行。
举个例子:在nuxt中使用axios,有两种方式:
1.写两个req 的api作为两个插件,一个在服务器请求名字为server-api.js,(服务端请求+asyncData中的请求)ssr设为true,一个在客户端请求 名为client-api.js,ssr设为false
2.只写一个request的qpi,将其ssr设为true即可
我个人是用的第一种,看着更清晰,哪个是客户端的请求,哪个是服务端的请求。那么在server-api.js中的代码其实会运行两次,由于我是将$aRep注入了context,所以不管是在server端还是client端的app中你都能找到这个app.$aReq,但是client-api.js中由于是ssr为false,导致其中的代码只会在client端运行一次,所以就只注入在了client端的app中
2.3 如果你想做一个初始化的操作,那么可以使用vuex中的nuxtServerInit ,该方法是完全运行在server端的,其实从生命周期可以看出来在render之前的都是在server端。
2.4 中间件:第一次进入页面或者刷新页面是在server端运行,之后的路由跳转是在client端运行
2.5 在一个页面中 ,当你第一次加载页面,或者重新加载页面时,即使用浏览器的reload功能,这时候由于页面完全刷新,该页面的.vue文件中的asyncData的环境是server端环境,并不会在客户端运行,但是你之后的路由跳转,页面中的asyncData的环境都是client端环境
2.6 当你在.vue的page页面中引入第三方vue插件时,即直接使用Import xxx from 'xxx',这种引入方式时,要注意,在第一次刷新页面时也会在服务端进行import,所以会导致大部分vue插件直接报错,解决办法就是:1.要么按照官方文档加载插件的方式进行操作,要么就在mounted钩子中使用动态加载,即llet a = require('xxx')
2.7 其实从2.5那点可以看出一个问题,由于在项目中我使用了axios进行请求,并且在需要请求时自动传递cookie,涉及到跨域问题。看了@nuxtjs/axios的文档后可以很简单就解决这个问题,使用proxy和credentials就能解决,其实这是针对client端的,我们都知道服务器和服务器之间的交互是不存在跨域问题的。所以可以使用proxy,我先将请求发送给nuxt服务器(这个过程不存在跨域),然后由nuxt服务器帮我转发就行了,当你设置了credentials后,nuxt服务器会同时将cookie传过去。那在写server-api.js插件时就要特别注意了,由于该插件同时运行在server和client端,那么在client端的时候,我们需要使用代理发送请求,在server端的时候我们就不能使用代理发送请求了,否则cookie传不过去的,所以需要通过process.client和process.server判断并使用不同的url