Nuxt middleware中间件
Nuxt执行顺序:
1、配置 nuxt.config.js (plugins)
2、中间件 middleware
3、匹配布局 layout(layout-created)
4、匹配页面 pages(page-created、mounted)
5、匹配布局 layout (layout-mounted)
1、middleware中间件
中间件允许定义一个自定义函数运行在一个页面或一组页面渲染之前。
每一个中间件应放置在 middleware/
目录。文件名的名称将成为中间件名称 (middleware/auth.js
将成为 auth
中间件)。
2、middleware中间件执行流程顺序:
nuxt.config.js
- 匹配布局
- 匹配页面
中间件可以异步执行,只需要返回一个 Promise
或使用第 2 个 callback
作为第一个参数:
3、middleware中间件可以做什么
1)、登录校验:在页面加载前校验是否登录,未登录跳转登录页
2)、按需提前请求接口:在所有接口请求前,先请求相应的接口(如:获取用户ip接口)
3)、重置请求头:在页面加载前重置 headers
4)、自定义参数:自定义参数供文件/页面使用
4、使用中间件
1)、新建文件 middleware/stats.js
2)、引用中间件
2-1)、layout/default :
2-2)、pages页面使用
5、示例
1)、登录校验(/middleware/stats.js)
export default function ({route, req, res, redirect}) { if (未登录) { redirect('/login') } }
2)、按需提前请求接口(/middleware/stats.js)
export default function (context) { const c = context.$cookies.getAll() || {} // 获取当前地区ip if(c.country?.id) return return context.$api.common.getCountryIp().then(response => { const res = response.result || {}; const country = { id: res.id, countryCode: res.countryCode, englishName: res.englishName, } context.$cookies.set('country', country) }) }
3)、重置请求头(/middleware/stats.js)
export default function (context) { context.headers.countrycode = 'US' }
4)、自定义参数(/middleware/stats.js)
6、中间件在服务层通信
1)、在 store 文件夹下新建 national.js
/* * @description 通用数据 国家、货币、语言 */ export const state = () => ({ country: {}, currency: {}, language: {} }) export const mutations = { setCountry(state, data) { state.country = data || {} }, setCurrency(state, data) { state.currency = data || {} }, setLanguage(state, data) { state.language = data || {} } } export const actions = {} export const getters = {}
2)、middleware中间件 stats.js 设置 store
/** * @description 基础设置 **/ export default function ({route, req, redirect, store, ...context}) { const c = context.$cookies.getAll() || {} const query = route.query; const domain = req?.headers?.domain; const pageIp = req?.headers['X-Forwarded-For'] || req?.headers['x-forwarded-for']; const mainName = ['m.yfn.com', 'mmall.preview.selleroa.com']; const toType = Object.prototype.toString; // 协议 const agreement = process.env.NODE_ENV == 'pre' ? 'http://' : 'https://'; // 入参 let params = {}; if(query.country_code && toType.call(query.country_code) == '[object Array]') { const countryCodeLength = query.country_code.length; const lastCountryCode = query.country_code[countryCodeLength - 1] || ''; lastCountryCode && (params = {countryCode: lastCountryCode}) } else { params = query.country_code ? {countryCode: query.country_code} : {}; } if(process.env.NODE_ENV != 'development' && domain) { params.origin = `${agreement}${domain}` params.getByIp = true } // nginx域名 domain && context.$cookies.set('page/domain', `${domain}`) params.origin && context.$cookies.set('page/origin', params.origin) // nginx ip let headers = {}; if(pageIp) { context.$cookies.set('page/ip', `${pageIp}`) headers['X-Forwarded-For'] = pageIp } // 获取当前地区ip if(!query.country_code && c?.country?.id && c?.currency?.code && c?.language?.identify) return return context.$api.common.getCountryIp(params, headers).then(response => { const res = response.result || {}; const ipInfo = response.ipResult || {}; const country = res; // 重定向 if(mainName.includes(domain) && params.origin && country.mRealmName != params.origin && !query.country_code) { const redirectUrl = `${country.mRealmName}${route.fullPath}`; return redirect(redirectUrl) } // 缓存 const currency = { code: res.currencyCode, symbol: res.currencySymbol }; const language = { identify: res.language, langCode: res.langCode, language: res.languageName }; context.$cookies.set('country', country); context.$cookies.set('currency', currency); context.$cookies.set('language', language); context.$cookies.set('page/ipName', ipInfo.mRealmName || ''); context.$cookies.set('page/countryParams', params || ''); // 通用数据设置 store.commit('national/setCountry', country) store.commit('national/setCurrency', currency) store.commit('national/setLanguage', language) }) }
3)、plugins插件内使用
4)、axios插件内使用