/** * 秒杀页面 * @author: 陈峰<feng.chen@yoho.cn> * @date: 2016/09/08 */ 'use strict'; const Promise = require('bluebird'); const logger = global.yoho.logger; const moment = require('moment'); const mRoot = '../models'; const headerModel = require('../../../doraemon/models/header'); const seckillModel = require(`${mRoot}/seckill`); let headerData = headerModel.setNav({ navTitle: '秒杀活动', navBtn: true, }); /** * [时间缺0补0] */ const _timeFormat = (tick) => { return tick < 10 ? `0${tick}` : tick; }; /** * 秒杀商品 添加 自定义属性 * ---------------------------------------- * 已开抢 * product.over [APP,H5: 1.已抢光 2.过了endTime] * product.isSeckill [APP,H5 秒杀中, 与over互斥] * 抢购中: * product.over * product.isSeckill * 即将开抢: * product.wait = true * product.remindFlag = true [APP: 已添加提醒] * product.remindFalg = false [APP: 默认提醒状态] * Product.hideRemind = true [APP: queryRemindList接口失败的情况下] */ function _productAddFlag(productList, remindList) { let now = Date.now(); productList .sort((a, b) => b.orderBy - a.orderBy) .forEach(product => { let startTime = product.startTime * 1000; // s to ms let endTime = product.endTime * 1000; product.remindFlag = false; product.readableTime = moment.unix(product.startTime).format('MM月DD日 HH:mm'); if (now < startTime) { // 未开抢 product.wait = true; product.isSeckill = true; if (!remindList) { product.hideRemind = true; } else if (remindList.length) { for (let i = 0, j = remindList.length; i < j; i++) { if (remindList[i].productSkn === product.productSkn) { // remind on; product.remindFlag = true; remindList.splice(i, 1); break; } } } } else if (product.secKillStatus === 0 || (now > endTime)) { // 确实已抢光, 过了秒杀时间 product.over = true; } }); return productList; } /** * 获取 秒杀产品列表 */ function fetchProductList(activityInfo, uid) { let activityId = activityInfo.activityId; let hasRemindAttr = activityInfo.isApp && uid && (Date.now() < activityInfo.startTime); let productList = seckillModel.queryProductList(activityId); let remindList = hasRemindAttr ? seckillModel.queryRemindList(activityId, uid) : { code: 200, data: [] }; return Promise.all([productList, remindList]) .then(res => { let r1 = res[0]; let r2 = res[1]; let result = []; if (r1.code !== 200) { return result; } result = r2.data ? _productAddFlag(r1.data, r2.data) : _productAddFlag(r1.data); return result; }); } /** * [秒杀列表页面] */ const index = (req, res) => { return res.render('seckill', { title: '秒杀活动', pageHeader: headerData, pageStyle: 'seckill-page', pageFooter: true, width750: true, }); }; /** * [秒杀列表 页面 初始数据] */ const indexData = (req, res, next) => { let focusTime = Number.parseInt(req.query.time, 10) || 0; let result = {}; let uid = req.yoho.isApp && req.query.uid; return seckillModel.queryActivity().then((resultActivity) => { // console.log(resultActivity) let focusIndex = false; // let nowTime = Date.now(); if (!resultActivity.data) { return next(); } result.currentTime = resultActivity.data.currentTime * 1000; if (resultActivity.code !== 200) { return next(); } if (!( resultActivity.data && resultActivity.data.secKillProductVoList && resultActivity.data.secKillProductVoList.length )) { return res.json({ title: '秒杀活动', pageHeader: headerData, error: '来晚啦~秒杀已结束' }); } result.activitys = resultActivity.data.secKillProductVoList.sort((a, b) => a.startTime - b.startTime); // orderBy startTime ASC if (focusTime) { focusTime = moment(focusTime, 'YYYYMMDDHHmmss').unix(); focusIndex = result.activitys.findIndex(activity=> activity.startTime === focusTime); if (focusIndex !== -1) { result.activitys[focusIndex].focus = true; focusIndex = true; } else { focusIndex = false; } } result.activitys.forEach((activity, i) => { let date, hour = 0, minute = 0; activity.startTime *= 1000; date = new Date(activity.startTime); hour = date.getHours(); minute = date.getMinutes(); activity.time = `${_timeFormat(hour)}:${_timeFormat(minute)}`; if (result.currentTime > activity.startTime) { // 当前时间大于这个时间段,已经开始和即将开始两种情况 if (i < result.activitys.length - 1) { let nextTime = result.activitys[i + 1].startTime * 1000; if (result.currentTime < nextTime) { // 下一个时间段与当前时间来区别是否正在抢购 activity.now = true; focusIndex || (activity.focus = focusIndex = true); } else { activity.over = true; } } else { // 大于这个时间段但是后面没有秒抢时间端了,则依然显示抢购中 activity.now = true; focusIndex || (activity.focus = focusIndex = true); } } else { activity.wait = true; } }); if (result.activitys.length && result.activitys.findIndex(activity => activity.focus) < 0) { let i = result.activitys.length; // 没有focus的活动,则focus 最后一个 over 的活动 while (i) { let activity = result.activitys[i - 1]; if (activity.over) { activity.focus = true; break; } i = i - 1; } // 没有over,全部都是未开抢,则focus第一个 if (!i) { result.activitys[0].focus = true; } } let focusActivity = result.activitys.find(activity => activity.focus); let activityInfo = { activityId: focusActivity.activityId, startTime: focusActivity.startTime * 1000, isApp: req.yoho.isApp }; return fetchProductList(activityInfo, uid).then((resultProducts) => { result.products = resultProducts; res.json(result); }); }); }; /** * [xhr根据活动id获取商品列表] */ const getProductList = (req, res, next) => { if (!req.xhr) { return next(); } let activityId = Number(req.query.activityId); let startTime = Number(req.query.startTime); let uid = req.yoho.isApp && req.query.uid; if (!activityId) { return next(); } let activityInfo = { isApp: req.yoho.isApp, activityId, startTime }; return fetchProductList(activityInfo, uid).then(resultProducts => { res.json({products: resultProducts}); }).catch(error => { logger.error(error); }); }; // only app const remind = (req, res, next) => { if (!(req.yoho.isApp && req.xhr)) { return res.status(404).json({ msg: '请求不合法' }); } return seckillModel.remind({ on_off: req.body.on_off === 'true' ? true : false, activity_id: Number.parseInt(req.body.activity_id, 10), product_skn: Number.parseInt(req.body.product_skn, 10), uid: Number.parseInt(req.body.uid, 10), sec_kill_id: Number.parseInt(req.body.sec_kill_id, 10), app_type: 0 }) .then(result => { return res.json(result); }); }; // Middleware:检测 app_version 是否正确 // @param okVersion string "5.1.0" [master_version, minor_version, patch_version] // TODO: 可以移到 middleware; const checkAppVer = function(okVersion) { return (req, res, next) => { /** * [比较app版本] * @param okVersion string '5.1.0' * @param curVersion string * @returns -1: 小于, 0 等于, 1大于 */ let compareVersion = (okVersion, curVersion) => { //eslint-disable-line let result = 0; // -1: 小于, 0 等于, 1 大于 if (okVersion === curVersion) { return result; } okVersion = okVersion.split('.'); curVersion = curVersion.split('.'); for (var i = 0; i < 3; i++) { let standard = Number.parseInt(okVersion[i], 10) || 0; let cur = Number.parseInt(curVersion[i], 10) || 0; if (cur < standard) { result = -1; break; } else if (cur > standard) { result = 1; break; } } return result; }; if (req.yoho.isApp) { let curVersion = req.query.app_version; let isOld = compareVersion(okVersion, curVersion) === -1; if (isOld) { return res.redirect('/passport/update'); } } next(); }; }; module.exports = { index, indexData, getProductList, remind, checkAppVer };