/** * 404 错误 * @return {[type]} */ const headerModel = require('../models/header'); const logger = global.yoho.logger; const cache = global.yoho.cache.master; const helpers = global.yoho.helpers; const sender = global.yoho.apmSender; const config = global.yoho.config; const hostname = require('os').hostname(); const routeEncode = require('./route-encode'); const _ = require('lodash'); const forceNoCache = (res) => { if (res && !res.finished) { res.set({ 'Cache-Control': 'no-cache', Pragma: 'no-cache', Expires: (new Date(1900, 0, 1, 0, 0, 0, 0)).toUTCString() }); } }; const _err510 = (req, res, code, err) => { res.status(code); if (req.xhr) { return res.json({ code: err.code, message: '服务器繁忙请稍后重试!' }); } return res.render('error/510', { err: err, module: 'common', page: 'error', title: '服务器繁忙 | Yoho!Buy有货 | 潮流购物逛不停', pageHeader: headerModel.setNav({ navTitle: '服务器繁忙请稍后重试!' }), pageFooter: true, isErr: true }); }; const _err500 = (req, res, code, err) => { res.status(code); if (req.xhr) { return res.json({ code: err.code, message: '服务器错误!' }); } return res.render('error/500', { err: err, module: 'common', page: 'error', title: '服务器错误 | Yoho!Buy有货 | 潮流购物逛不停', pageHeader: headerModel.setNav({ navTitle: '服务器错误!' }), pageFooter: true, isErr: true }); }; exports.notFound = () => { return (req, res) => { forceNoCache(res); res.status(404); if (req.xhr) { return res.json({ code: 404, message: '抱歉,页面不存在!' }); } return res.render('error/404', { module: 'common', page: 'error', title: '页面不存在 | Yoho!Buy有货 | 潮流购物逛不停', pageHeader: headerModel.setNav({ navTitle: '抱歉,页面不存在!' }), pageFooter: true, isErr: true }); }; }; /** * 服务器错误 * @return {[type]} */ exports.serverError = () => { return async(err, req, res, next) => { const uid = req.user ? req.user.uid : 0; const udid = _.get(req, 'cookies.udid', 'yoho'); forceNoCache(res); err.code = err.code || err.statusCode || 500; if (!err.type === 'entity.parse.failed') { // json 解析失败不上报错误 logger.error(`error at path: ${req.url}`); logger.error(err); } if (req.isApmReport && err.code !== 401) { // 上报服务端错误 sender.addMessage({ measurement: 'error-report', tags: { app: config.appName, // 应用名称 hostname, type: 'server', route: `[${req.method}]${_.get(req, 'route.path', '')}`, // 请求路由 reqID: req.reqID, uid, udid, code: err.code || 500, path: `[${req.method}]${routeEncode.getRouter(req)}` }, fields: { message: err.message, stack: err.stack } }); } if (err && err.code === 401) { logger.warn(`401 warn info:client_type=${req.query.client_type},req.user=${JSON.stringify(req.user)},req.query=${JSON.stringify(req.query)},cookies=${JSON.stringify(req.cookies)}`); // eslint-disable-line if (req.xhr) { return res.status(401).json(err); } else if (req.yoho.isApp) { if (err.lowVersion) { return res.render('error/app-auth', { module: 'common', page: 'app-update', localCss: true, message: err.message }); } return res.render('error/app-auth', { module: 'common', page: 'app-redirect-login', message: '请登录', localCss: true, refer: err.refer }); } else { return res.redirect(helpers.urlFormat('/signin.html', { refer: req.originalUrl })); } } else if (err.code === 9999991 || err.code === 9999992) { let remoteIp = req.yoho.clientIp; const isHuman = await cache.getAsync(`${config.app}:limiter:api:ishuman:${remoteIp}`); if (!isHuman) { if (remoteIp.indexOf(',') > 0) { let arr = remoteIp.split(','); remoteIp = arr[0]; } cache.setAsync(`${config.app}:limiter:${remoteIp}`, 1, config.LIMITER_IP_TIME); let limitAPI = helpers.urlFormat('/3party/check', {refer: req.get('Referer') || ''}); let limitPage = helpers.urlFormat('/3party/check', { refer: req.protocol + '://' + req.get('host') + req.originalUrl }); req.session.apiLimitValidate = true; if (req.xhr) { return res.status(510).json({ code: err.code, data: {refer: limitAPI} }); } return res.redirect(limitPage); } return _err510(req, res, 510, err); } if (!res.headersSent) { return _err500(req, res, err.code, err); } return next(err); }; };