Authored by 郭成尧

merge-master

@@ -73,7 +73,6 @@ app.use(global.yoho.hbs({ @@ -73,7 +73,6 @@ app.use(global.yoho.hbs({
73 helpers: _.assign(global.yoho.helpers, require('./utils/helpers')) 73 helpers: _.assign(global.yoho.helpers, require('./utils/helpers'))
74 })); 74 }));
75 75
76 -app.use(global.yoho.middleware());  
77 76
78 app.use(bodyParser.json()); 77 app.use(bodyParser.json());
79 app.use(bodyParser.urlencoded({ 78 app.use(bodyParser.urlencoded({
@@ -31,4 +31,4 @@ exports.sidebar = function(req, res, next) { @@ -31,4 +31,4 @@ exports.sidebar = function(req, res, next) {
31 layout: false 31 layout: false
32 }); 32 });
33 }).catch(next); 33 }).catch(next);
34 -}  
  34 +};
@@ -373,7 +373,7 @@ const order = (params) => { @@ -373,7 +373,7 @@ const order = (params) => {
373 code: 200 373 code: 200
374 }).then((result) => { 374 }).then((result) => {
375 375
376 - if (result.data) { 376 + if (result && result.data) {
377 Object.assign(finalResult, {cancelReason: result.data}); 377 Object.assign(finalResult, {cancelReason: result.data});
378 } 378 }
379 return finalResult; 379 return finalResult;
@@ -385,7 +385,7 @@ const order = (params) => { @@ -385,7 +385,7 @@ const order = (params) => {
385 * @param params 385 * @param params
386 */ 386 */
387 const getOrders = (params) => { 387 const getOrders = (params) => {
388 - let finalResult = Promise.resolve([]); 388 + let finalResult = [];
389 389
390 if (!params.uid) { 390 if (!params.uid) {
391 return Promise.resolve([]); 391 return Promise.resolve([]);
@@ -182,7 +182,6 @@ exports.orderSub = (req, res, next) => { @@ -182,7 +182,6 @@ exports.orderSub = (req, res, next) => {
182 let yohoCoin = req.body.yohoCoin || 0; 182 let yohoCoin = req.body.yohoCoin || 0;
183 let skuList = req.body.skuList || ''; 183 let skuList = req.body.skuList || '';
184 let orderInfo; 184 let orderInfo;
185 - let isWechat = req.yoho.isWechat;  
186 185
187 try { 186 try {
188 orderInfo = JSON.parse(req.cookies['order-info']); 187 orderInfo = JSON.parse(req.cookies['order-info']);
@@ -254,7 +253,15 @@ exports.orderSub = (req, res, next) => { @@ -254,7 +253,15 @@ exports.orderSub = (req, res, next) => {
254 253
255 return co(function* () { 254 return co(function* () {
256 let result; 255 let result;
257 - let ip = req.ip || ''; 256 +
  257 + // 接口需要的其他参数
  258 + let otherParams = {
  259 + unionKey: unionKey, // 友盟数据
  260 + userAgent: userAgent,
  261 + isWechat: req.yoho.isWechat,
  262 + ip: req.ip || '',
  263 + udid: req.cookies._yasvd || 'yoho'
  264 + };
258 265
259 /* tar modified 161206 套餐 */ 266 /* tar modified 161206 套餐 */
260 if (req.body.cartType === 'bundle') { 267 if (req.body.cartType === 'bundle') {
@@ -262,11 +269,11 @@ exports.orderSub = (req, res, next) => { @@ -262,11 +269,11 @@ exports.orderSub = (req, res, next) => {
262 269
263 result = yield cartModel.orderSub(uid, addressId, 'bundle', deliveryTimeId, 270 result = yield cartModel.orderSub(uid, addressId, 'bundle', deliveryTimeId,
264 deliveryId, invoices, paymentTypeId, paymentType, msg, couponCode, 271 deliveryId, invoices, paymentTypeId, paymentType, msg, couponCode,
265 - yohoCoin, null, unionKey, userAgent, times, activityInfo, ip, isWechat); 272 + yohoCoin, null, times, activityInfo, otherParams);
266 } else { 273 } else {
267 result = yield cartModel.orderSub(uid, addressId, cartType, deliveryTimeId, 274 result = yield cartModel.orderSub(uid, addressId, cartType, deliveryTimeId,
268 deliveryId, invoices, paymentTypeId, paymentType, msg, couponCode, 275 deliveryId, invoices, paymentTypeId, paymentType, msg, couponCode,
269 - yohoCoin, skuList, unionKey, userAgent, null, null, ip, isWechat); 276 + yohoCoin, skuList, null, null, otherParams);
270 } 277 }
271 278
272 // 提交成功清除Cookie 279 // 提交成功清除Cookie
@@ -180,23 +180,21 @@ exports.ticketsOrderCompute = (uid, productSku, buyNumber, yohoCoin) => { @@ -180,23 +180,21 @@ exports.ticketsOrderCompute = (uid, productSku, buyNumber, yohoCoin) => {
180 * @param string $couponCode 优惠券码 180 * @param string $couponCode 优惠券码
181 * @param mixed $yohoCoin 使用的有货币数量或为空 181 * @param mixed $yohoCoin 使用的有货币数量或为空
182 * @param string $skuList 购买限购商品时需要传递的参数 182 * @param string $skuList 购买限购商品时需要传递的参数
183 - * @param string $qhyUnio 友盟有关信息  
184 * @param string|null $userAgent 联盟过来用户下单时需要的User-Agent信息 183 * @param string|null $userAgent 联盟过来用户下单时需要的User-Agent信息
185 * @param int $times 184 * @param int $times
186 * @param null $activityInfo 套餐数据 185 * @param null $activityInfo 套餐数据
187 - * @param isWechat 是否是微信商城 186 + * @param otherParams 其他参数
188 * @return array 接口返回的数据 187 * @return array 接口返回的数据
189 */ 188 */
190 exports.orderSub = (uid, addressId, cartType, deliveryTime, 189 exports.orderSub = (uid, addressId, cartType, deliveryTime,
191 deliveryWay, invoices, paymentId, paymentType, remark, 190 deliveryWay, invoices, paymentId, paymentType, remark,
192 - couponCode, yohoCoin, skuList, qhyUnio,  
193 - userAgent, times, activityInfo, ip, isWechat) => {  
194 - if (!qhyUnio) {  
195 - qhyUnio = ''; 191 + couponCode, yohoCoin, skuList, times, activityInfo, otherParams) => {
  192 + if (!otherParams.unionKey) {
  193 + otherParams.unionKey = '';
196 } 194 }
197 195
198 - if (!userAgent) {  
199 - userAgent = null; 196 + if (!otherParams.userAgent) {
  197 + otherParams.userAgent = null;
200 } 198 }
201 199
202 if (!times) { 200 if (!times) {
@@ -221,8 +219,7 @@ exports.orderSub = (uid, addressId, cartType, deliveryTime, @@ -221,8 +219,7 @@ exports.orderSub = (uid, addressId, cartType, deliveryTime,
221 219
222 return shoppingAPI.orderSub(uid, addressId, cartType, deliveryTime, 220 return shoppingAPI.orderSub(uid, addressId, cartType, deliveryTime,
223 deliveryWay, invoices, paymentId, paymentType, 221 deliveryWay, invoices, paymentId, paymentType,
224 - remark, couponCode, yohoCoin, skuList, qhyUnio,  
225 - userAgent, times, activityInfo, ip, isWechat).then(orderSubRes => { 222 + remark, couponCode, yohoCoin, skuList, times, activityInfo, otherParams).then(orderSubRes => {
226 let finalResult = {}; 223 let finalResult = {};
227 224
228 if (orderSubRes && orderSubRes.data && orderSubRes.data.is_hint === 'Y') { 225 if (orderSubRes && orderSubRes.data && orderSubRes.data.is_hint === 'Y') {
@@ -241,7 +241,7 @@ const getPriceGiftList = (promotionIds, promotionType) => { @@ -241,7 +241,7 @@ const getPriceGiftList = (promotionIds, promotionType) => {
241 method: 'app.Shopping.queryPromotionGifts', 241 method: 'app.Shopping.queryPromotionGifts',
242 promotion_ids: promotionIds 242 promotion_ids: promotionIds
243 }).then((data) => { 243 }).then((data) => {
244 - return data.code === 200 ? cartProcess.procPriceGiftData(data.data, promotionType) : void 0; 244 + return data.code === 200 ? cartProcess.procPriceGiftData(data.data, promotionType) : {};
245 }); 245 });
246 }; 246 };
247 247
@@ -149,16 +149,15 @@ exports.checkTickets = (uid, productSku, buyNumber, useYohoCoin, yohoCoinMode) = @@ -149,16 +149,15 @@ exports.checkTickets = (uid, productSku, buyNumber, useYohoCoin, yohoCoinMode) =
149 * @param string $couponCode 优惠券码 149 * @param string $couponCode 优惠券码
150 * @param mixed $yohoCoin 使用的有货币数量或为空 150 * @param mixed $yohoCoin 使用的有货币数量或为空
151 * @param string $skuList 购买限购商品时需要传递的参数 151 * @param string $skuList 购买限购商品时需要传递的参数
152 - * @param string $qhyUnion 友盟有关信息  
153 * @param string|null $userAgent 联盟过来用户下单时需要的User-Agent信息 152 * @param string|null $userAgent 联盟过来用户下单时需要的User-Agent信息
154 * @param $times 153 * @param $times
155 * @param null $activityInfo 套餐信息 154 * @param null $activityInfo 套餐信息
156 - * @param isWechat 是否是微信商城 155 + * @param @param otherParams 其他参数
157 * @return array 接口返回的数据 156 * @return array 接口返回的数据
158 */ 157 */
159 exports.orderSub = (uid, addressId, cartType, deliveryTime, 158 exports.orderSub = (uid, addressId, cartType, deliveryTime,
160 deliveryWay, invoices, paymentId, paymentType, remark, couponCode, 159 deliveryWay, invoices, paymentId, paymentType, remark, couponCode,
161 - yohoCoin, skuList, qhyUnion, userAgent, times, activityInfo, ip, isWechat) => { 160 + yohoCoin, skuList, times, activityInfo, otherParams) => {
162 if (!activityInfo) { 161 if (!activityInfo) {
163 activityInfo = null; 162 activityInfo = null;
164 } 163 }
@@ -173,7 +172,8 @@ exports.orderSub = (uid, addressId, cartType, deliveryTime, @@ -173,7 +172,8 @@ exports.orderSub = (uid, addressId, cartType, deliveryTime,
173 payment_id: paymentId, 172 payment_id: paymentId,
174 payment_type: paymentType, 173 payment_type: paymentType,
175 remark: remark, 174 remark: remark,
176 - uid: uid 175 + uid: uid,
  176 + udid: otherParams.udid
177 }; 177 };
178 178
179 /* tar add 161130 结算优化 */ 179 /* tar add 161130 结算优化 */
@@ -223,19 +223,19 @@ exports.orderSub = (uid, addressId, cartType, deliveryTime, @@ -223,19 +223,19 @@ exports.orderSub = (uid, addressId, cartType, deliveryTime,
223 } 223 }
224 224
225 // 友盟有关信息的传递 225 // 友盟有关信息的传递
226 - if (qhyUnion) {  
227 - params.qhy_union = qhyUnion; 226 + if (otherParams.unionKey) {
  227 + params.qhy_union = otherParams.unionKey;
228 } 228 }
229 229
230 // 是否是微信商城 230 // 是否是微信商城
231 - if (isWechat) { 231 + if (otherParams.isWechat) {
232 params.client_type = 'wechat'; 232 params.client_type = 'wechat';
233 } 233 }
234 234
235 return api.post('', params, { 235 return api.post('', params, {
236 headers: { 236 headers: {
237 - 'X-Forwarded-For': ip || '',  
238 - 'User-Agent': userAgent 237 + 'X-Forwarded-For': otherParams.ip || '',
  238 + 'User-Agent': otherParams.userAgent
239 } 239 }
240 }); 240 });
241 }; 241 };
@@ -201,7 +201,7 @@ const packageData = (id, isApp, isWeixin, channel, isShare) => { @@ -201,7 +201,7 @@ const packageData = (id, isApp, isWeixin, channel, isShare) => {
201 201
202 return Promise.all(promises).then(datas => { 202 return Promise.all(promises).then(datas => {
203 203
204 - let getArticleContent = {}; 204 + let getArticleContent = [];
205 205
206 if (datas) { 206 if (datas) {
207 if (datas[1]) { 207 if (datas[1]) {
@@ -188,6 +188,7 @@ const addressModify = (req, res, next) => { @@ -188,6 +188,7 @@ const addressModify = (req, res, next) => {
188 */ 188 */
189 const changeAddress = (req, res, next) => { 189 const changeAddress = (req, res, next) => {
190 let uid = req.user.uid; 190 let uid = req.user.uid;
  191 + let udid = req.cookies._yasvd || 'yoho';
191 192
192 if (!uid) { 193 if (!uid) {
193 return res.json({ 194 return res.json({
@@ -202,7 +203,8 @@ const changeAddress = (req, res, next) => { @@ -202,7 +203,8 @@ const changeAddress = (req, res, next) => {
202 username: req.body.username, 203 username: req.body.username,
203 areaCode: req.body.area_code, 204 areaCode: req.body.area_code,
204 address: req.body.address, 205 address: req.body.address,
205 - mobile: req.body.mobile 206 + mobile: req.body.mobile,
  207 + udid: udid
206 }).then(result => { 208 }).then(result => {
207 res.json(result); 209 res.json(result);
208 }).catch(next); 210 }).catch(next);
@@ -374,7 +374,8 @@ const changeAddress = (params) => { @@ -374,7 +374,8 @@ const changeAddress = (params) => {
374 user_name: params.username, 374 user_name: params.username,
375 area_code: params.areaCode, 375 area_code: params.areaCode,
376 address: params.address, 376 address: params.address,
377 - mobile: params.mobile 377 + mobile: params.mobile,
  378 + udid: params.udid
378 }; 379 };
379 380
380 if (params.addressId) { 381 if (params.addressId) {
@@ -90,8 +90,8 @@ router.get('/helpDetail', help.helpDetail); @@ -90,8 +90,8 @@ router.get('/helpDetail', help.helpDetail);
90 // 意见反馈 90 // 意见反馈
91 router.get('/suggest', suggest.suggestData); 91 router.get('/suggest', suggest.suggestData);
92 router.post('/upAndDown', suggest.upAndDown); 92 router.post('/upAndDown', suggest.upAndDown);
93 -router.get('/suggestSub', suggest.suggestSub);  
94 -router.post('/savesuggest', suggest.saveSuggest); 93 +router.get('/suggestSub', auth, suggest.suggestSub);
  94 +router.post('/savesuggest', auth, suggest.saveSuggest);
95 95
96 // 消息 96 // 消息
97 router.use('/message', auth, disableBFCache, message.index); 97 router.use('/message', auth, disableBFCache, message.index);
@@ -10,10 +10,12 @@ const passport = require('passport'); @@ -10,10 +10,12 @@ const passport = require('passport');
10 10
11 // const md5 = require('yoho-md5'); 11 // const md5 = require('yoho-md5');
12 const uuid = require('uuid'); 12 const uuid = require('uuid');
  13 +const co = Promise.coroutine;
13 const cookie = global.yoho.cookie; 14 const cookie = global.yoho.cookie;
14 const helpers = global.yoho.helpers; 15 const helpers = global.yoho.helpers;
15 const log = global.yoho.logger; 16 const log = global.yoho.logger;
16 const config = global.yoho.config; 17 const config = global.yoho.config;
  18 +const cache = global.yoho.cache;
17 const utils = require(global.utils); 19 const utils = require(global.utils);
18 const RegService = require('../models/reg-service'); 20 const RegService = require('../models/reg-service');
19 const AuthHelper = require('../models/auth-helper'); 21 const AuthHelper = require('../models/auth-helper');
@@ -81,7 +83,9 @@ const common = { @@ -81,7 +83,9 @@ const common = {
81 let passLogin = _.get(req, 'cookies._WX_PASS_LOGIN', false); 83 let passLogin = _.get(req, 'cookies._WX_PASS_LOGIN', false);
82 84
83 if (req.yoho.isWechat && !passLogin) { 85 if (req.yoho.isWechat && !passLogin) {
84 - return res.redirect('/passport/login/wechat'); 86 + return res.redirect(helpers.urlFormat('/passport/login/wechat', {
  87 + refer: req.query.refer || req.get('Referer') || '/'
  88 + }));
85 } 89 }
86 next(); 90 next();
87 }, 91 },
@@ -120,19 +124,10 @@ const local = { @@ -120,19 +124,10 @@ const local = {
120 req.session.captchaValidCount = 5; 124 req.session.captchaValidCount = 5;
121 } 125 }
122 126
123 - // 先清除cookie  
124 - // res.clearCookie('LE' + md5('_LOGIN_EXPIRE'), {  
125 - // domain: 'yohobuy.com'  
126 - // });  
127 -  
128 - // 设置登录有效时间30分钟, 防机器刷,cache不稳定,改为cookie  
129 - // res.cookie('LE' + md5('_LOGIN_EXPIRE'), (new Date()).getTime() / 1000 + 1800);  
130 -  
131 -  
132 res.render('login', { 127 res.render('login', {
133 width750: true, 128 width750: true,
134 loginIndex: true, // 模板中使用JS的标识 129 loginIndex: true, // 模板中使用JS的标识
135 - captchaShow: true, // 170306 因为暴力破解密码问题,要求每次都展示验证码 130 + captchaShow: req.yoho.captchaShow,
136 backUrl: 'javascript:history.go(-1)', // eslint-disable-line 131 backUrl: 'javascript:history.go(-1)', // eslint-disable-line
137 showHeaderImg: true, // 控制显示头部图片 132 showHeaderImg: true, // 控制显示头部图片
138 isPassportPage: true, // 模板中模块标识 133 isPassportPage: true, // 模板中模块标识
@@ -162,21 +157,11 @@ const local = { @@ -162,21 +157,11 @@ const local = {
162 req.session.captchaValidCount = 5; 157 req.session.captchaValidCount = 5;
163 } 158 }
164 159
165 - // 先清除cookie  
166 - // res.clearCookie('LE' + md5('_LOGIN_EXPIRE'), {  
167 - // domain: 'yohobuy.com'  
168 - // });  
169 -  
170 - // 设置登录有效时间30分钟, 防机器刷,cache不稳定,改为cookie  
171 - // res.cookie('LE' + md5('_LOGIN_EXPIRE'), (new Date()).getTime() / 1000 + 1800);  
172 -  
173 -  
174 -  
175 res.render('international', { 160 res.render('international', {
176 width750: true, 161 width750: true,
177 backUrl: 'javascript:history.go(-1)', // eslint-disable-line 162 backUrl: 'javascript:history.go(-1)', // eslint-disable-line
178 loginInternational: true, // 模板中使用JS的标识 163 loginInternational: true, // 模板中使用JS的标识
179 - captchaShow: true, // 170306 因为暴力破解密码问题,要求每次都展示验证码 164 + captchaShow: req.yoho.captchaShow,
180 isPassportPage: true, // 模板中模块标识 165 isPassportPage: true, // 模板中模块标识
181 headerText: '登录', 166 headerText: '登录',
182 areaCode: '+86', // 默认区号 167 areaCode: '+86', // 默认区号
@@ -206,6 +191,8 @@ const local = { @@ -206,6 +191,8 @@ const local = {
206 captchaShow: true 191 captchaShow: true
207 }; 192 };
208 193
  194 + cache.set(`loginErrorIp:${req.yoho.clientIp}`, true, 3600).catch(log.error);
  195 +
209 res.json(obj); 196 res.json(obj);
210 } else { 197 } else {
211 let refer = req.cookies.refer; 198 let refer = req.cookies.refer;
@@ -250,6 +237,18 @@ const local = { @@ -250,6 +237,18 @@ const local = {
250 237
251 const wechat = { 238 const wechat = {
252 login: (req, res, next) => { 239 login: (req, res, next) => {
  240 + // 微信里边已经登录的时候,不再跳转登录
  241 + if (req.user.uid) {
  242 + let refer = req.query.refer || decodeURI(req.cookies.refer) || config.siteUrl;
  243 +
  244 + if (/sign|login/.test(refer)) {
  245 + refer = `${config.siteUrl}/home`;
  246 + }
  247 +
  248 + refer = utils.refererLimit(refer);
  249 + return res.redirect(refer);
  250 + }
  251 +
253 // 设置为原链接标识originalUrl 252 // 设置为原链接标识originalUrl
254 req.session.originalUrl = 'true'; 253 req.session.originalUrl = 'true';
255 req.session.authState = uuid.v4(); 254 req.session.authState = uuid.v4();
@@ -389,6 +388,36 @@ exports.user = function(req, res, next) { @@ -389,6 +388,36 @@ exports.user = function(req, res, next) {
389 res.jsonp(result); 388 res.jsonp(result);
390 }; 389 };
391 390
  391 +/**
  392 + * 中间件
  393 + * 根据用户登录是否成功决定是否展示验证码
  394 + */
  395 +exports.loginShowCaptchaByIp = function(req, res, next) {
  396 + // 总开关状态
  397 + req.yoho.captchaShow = !_.get(req.app.locals.wap, 'close.loginValidation', false);
  398 +
  399 + // 开关打开,不走任何验证逻辑
  400 + if (!req.yoho.captchaShow) {
  401 + return next();
  402 + } else {
  403 + req.yoho.captchaShow = false;
  404 + }
  405 +
  406 + co(function*() {
  407 + let hasErrorLog = yield cache.get(`loginErrorIp:${req.yoho.clientIp}`);
  408 +
  409 + log.info(`Pagerender clientip ${req.yoho.clientIp} status is ` + hasErrorLog);
  410 +
  411 + if (hasErrorLog) {
  412 + req.yoho.captchaShow = true;
  413 + }
  414 + next();
  415 + })().catch(function(e) {
  416 + req.yoho.captchaShow = true;
  417 + next();
  418 + });
  419 +};
  420 +
392 exports.common = common; 421 exports.common = common;
393 exports.local = local; 422 exports.local = local;
394 exports.wechat = wechat; 423 exports.wechat = wechat;
@@ -7,6 +7,9 @@ @@ -7,6 +7,9 @@
7 'use strict'; 7 'use strict';
8 const _ = require('lodash'); 8 const _ = require('lodash');
9 const config = global.yoho.config; 9 const config = global.yoho.config;
  10 +const co = Promise.coroutine;
  11 +const cache = global.yoho.cache;
  12 +const log = global.yoho.logger;
10 const geetest = require('./geetest'); 13 const geetest = require('./geetest');
11 const captcha = require('./captcha'); 14 const captcha = require('./captcha');
12 15
@@ -20,15 +23,44 @@ const check = (req, res, next) => { @@ -20,15 +23,44 @@ const check = (req, res, next) => {
20 return next(); 23 return next();
21 } 24 }
22 25
23 - // 使用极验证  
24 - let useGeetest = !_.get(req.app.locals.wap, 'geetest.validation', false); 26 + // 默认取配置总开关来决定是否展示验证码
  27 + req.yoho.captchaShow = !_.get(req.app.locals.wap, 'close.loginValidation', false);
25 28
26 - // 某次请求极验证调用注册失败,强制使用自有图形验证码  
27 - if (req.session.useYohoCaptcha) {  
28 - useGeetest = false;  
29 - } 29 + co(function* () {
  30 + // 如果是账号密码登录,那么需要检查是否登录失败过,登录失败过展示验证码
  31 + if (req.path === '/passport/login/auth') {
  32 + let hasErrorLog = yield cache.get(`loginErrorIp:${req.yoho.clientIp}`);
  33 +
  34 + log.info(`Check clientip ${req.yoho.clientIp} status is ` + hasErrorLog);
  35 +
  36 + if (hasErrorLog) {
  37 + req.yoho.captchaShow = true;
  38 + } else {
  39 + req.yoho.captchaShow = false;
  40 + }
  41 + }
  42 +
  43 + return req.yoho.captchaShow;
  44 + })().catch(function() {
  45 + // memcache 不可用,展示验证码
  46 + req.yoho.captchaShow = true;
  47 + return req.yoho.captchaShow;
  48 + }).then(function() {
  49 + // 不是账号密码登录,直接根据配置总开关决定是否需要展示验证码
  50 + if (!req.yoho.captchaShow) {
  51 + return next();
  52 + }
  53 +
  54 + // 使用极验证
  55 + let useGeetest = !_.get(req.app.locals.wap, 'geetest.validation', false);
  56 +
  57 + // 某次请求极验证调用注册失败,强制使用自有图形验证码
  58 + if (req.session.useYohoCaptcha) {
  59 + useGeetest = false;
  60 + }
30 61
31 - return (useGeetest ? geetest : captcha).validate(req, res, next); 62 + return (useGeetest ? geetest : captcha).validate(req, res, next);
  63 + });
32 }; 64 };
33 65
34 /** 66 /**
@@ -2,6 +2,7 @@ @@ -2,6 +2,7 @@
2 const _ = require('lodash'); 2 const _ = require('lodash');
3 const aes = require('./aes-pwd'); 3 const aes = require('./aes-pwd');
4 const authcode = require('../../../utils/authcode'); 4 const authcode = require('../../../utils/authcode');
  5 +const logger = global.yoho.logger;
5 const sign = global.yoho.sign; 6 const sign = global.yoho.sign;
6 const api = global.yoho.API; 7 const api = global.yoho.API;
7 const uuid = require('uuid'); 8 const uuid = require('uuid');
@@ -35,10 +36,13 @@ class Auth { @@ -35,10 +36,13 @@ class Auth {
35 param.shopping_key = shoppingKey; 36 param.shopping_key = shoppingKey;
36 } 37 }
37 38
  39 + logger.info(`${profile}, login from ${ip}`);
  40 +
38 return api.post('', param, { 41 return api.post('', param, {
39 headers: { 42 headers: {
40 'user-agent': 'yoho/nodejs', 43 'user-agent': 'yoho/nodejs',
41 - 'X-YOHO-IP': ip 44 + 'X-YOHO-IP': ip,
  45 + 'X-Forwarded-For': ip
42 } 46 }
43 }); 47 });
44 } 48 }
@@ -27,7 +27,7 @@ const router = express.Router(); // eslint-disable-line @@ -27,7 +27,7 @@ const router = express.Router(); // eslint-disable-line
27 router.get('/passport/geetest/register', geetest.register); 27 router.get('/passport/geetest/register', geetest.register);
28 28
29 // 兼容老的路由 29 // 兼容老的路由
30 -router.get('/signin.html', validateCode.load, login.common.weixinCheck, 30 +router.get('/signin.html', login.common.weixinCheck, validateCode.load,
31 login.common.beforeLogin, login.common.clearCookie, smsLogin.loginPage); 31 login.common.beforeLogin, login.common.clearCookie, smsLogin.loginPage);
32 router.get('/reg.html', validateCode.load, disableBFCahce, reg.index); 32 router.get('/reg.html', validateCode.load, disableBFCahce, reg.index);
33 router.get('/login.html', validateCode.load, 33 router.get('/login.html', validateCode.load,
@@ -39,10 +39,21 @@ router.get('/emailback.html', back.indexEmailPage); @@ -39,10 +39,21 @@ router.get('/emailback.html', back.indexEmailPage);
39 router.get('/passport/signout/index', login.common.clearCookie, login.local.logout); 39 router.get('/passport/signout/index', login.common.clearCookie, login.local.logout);
40 40
41 // 登录页面 41 // 登录页面
42 -router.get('/passport/login', validateCode.load,  
43 - login.common.beforeLogin, login.common.clearCookie, login.local.loginPage);  
44 -router.get('/passport/international', validateCode.load,  
45 -login.common.beforeLogin, login.common.clearCookie, login.local.international); 42 +router.get('/passport/login',
  43 + validateCode.load,
  44 + login.common.beforeLogin,
  45 + login.common.clearCookie,
  46 + login.loginShowCaptchaByIp,
  47 + login.local.loginPage
  48 +);
  49 +
  50 +router.get('/passport/international',
  51 + validateCode.load,
  52 + login.common.beforeLogin,
  53 + login.common.clearCookie,
  54 + login.loginShowCaptchaByIp,
  55 + login.local.international
  56 +);
46 57
47 // 本地登录 58 // 本地登录
48 router.post('/passport/login/auth', validateCode.check, login.local.login); 59 router.post('/passport/login/auth', validateCode.check, login.local.login);
@@ -78,10 +89,6 @@ router.get('/passport/login/qq/callback', login.qq.callback); @@ -78,10 +89,6 @@ router.get('/passport/login/qq/callback', login.qq.callback);
78 router.get('/passport/login/alipay', login.common.beforeLogin, login.alipay.login); 89 router.get('/passport/login/alipay', login.common.beforeLogin, login.alipay.login);
79 router.get('/passport/login/alipay/callback', login.alipay.callback); 90 router.get('/passport/login/alipay/callback', login.alipay.callback);
80 91
81 -// alipay登录  
82 -router.get('/login/alipay', login.common.beforeLogin, login.alipay.login);  
83 -router.get('/login/alipay/callback', login.alipay.callback);  
84 -  
85 // 登录绑定 92 // 登录绑定
86 router.get('/passport/bind/index', validateCode.load, bind.indexPage); 93 router.get('/passport/bind/index', validateCode.load, bind.indexPage);
87 router.post('/passport/bind/bindCheck', validateCode.check, bind.bindCheck); 94 router.post('/passport/bind/bindCheck', validateCode.check, bind.bindCheck);
@@ -10,7 +10,7 @@ @@ -10,7 +10,7 @@
10 <input id="pwd" class="pwd input" type="password" placeholder="密码"> 10 <input id="pwd" class="pwd input" type="password" placeholder="密码">
11 </div> 11 </div>
12 {{!--图片验证--}} 12 {{!--图片验证--}}
13 - <div data-geetest="{{useGeetest}}" id="js-img-check"></div> 13 + <div data-userverify="{{captchaShow}}" data-geetest="{{useGeetest}}" id="js-img-check"></div>
14 14
15 <span id="btn-login" class="btn btn-login disble row">登录</span> 15 <span id="btn-login" class="btn btn-login disble row">登录</span>
16 </div> 16 </div>
@@ -9,7 +9,7 @@ @@ -9,7 +9,7 @@
9 <input id="pwd" class="pwd input" type="password" placeholder="密码"> 9 <input id="pwd" class="pwd input" type="password" placeholder="密码">
10 </div> 10 </div>
11 {{!--图片验证--}} 11 {{!--图片验证--}}
12 - <div data-geetest="{{useGeetest}}" id="js-img-check"></div> 12 + <div data-userverify="{{captchaShow}}" data-geetest="{{useGeetest}}" id="js-img-check"></div>
13 <span id="btn-login" class="btn btn-login disable">登录</span> 13 <span id="btn-login" class="btn btn-login disable">登录</span>
14 <p class="op-container"> 14 <p class="op-container">
15 <a class="op-item internat" href={{internationalUrl}}>海外手机</a> 15 <a class="op-item internat" href={{internationalUrl}}>海外手机</a>
@@ -231,6 +231,7 @@ const category = (req, res, next) => { @@ -231,6 +231,7 @@ const category = (req, res, next) => {
231 order: '0', 231 order: '0',
232 page: 1, 232 page: 1,
233 limit: 12, 233 limit: 12,
  234 + isApp: params.app_version
234 }, params); 235 }, params);
235 236
236 if (uid) { 237 if (uid) {
@@ -881,7 +881,7 @@ const getLimitProductData = (uid, limitProductCode) => { @@ -881,7 +881,7 @@ const getLimitProductData = (uid, limitProductCode) => {
881 881
882 if (obj.attaches.length > 1) { 882 if (obj.attaches.length > 1) {
883 obj.attaches.sort((v1, v2) => { 883 obj.attaches.sort((v1, v2) => {
884 - return v1.orderBy - v2.orderBy; 884 + return v2.orderBy - v1.orderBy;
885 }); 885 });
886 } 886 }
887 887
@@ -123,6 +123,8 @@ const selectHotrank = (yhChannel, gender, sort, tabId, limit, page, notab) => { @@ -123,6 +123,8 @@ const selectHotrank = (yhChannel, gender, sort, tabId, limit, page, notab) => {
123 } 123 }
124 124
125 return formData; 125 return formData;
  126 + } else {
  127 + return {};
126 } 128 }
127 129
128 }); 130 });
@@ -25,7 +25,7 @@ const domains = { @@ -25,7 +25,7 @@ const domains = {
25 25
26 module.exports = { 26 module.exports = {
27 app: 'h5', 27 app: 'h5',
28 - appVersion: '5.5.1', // 调用api的版本 28 + appVersion: '5.5.2', // 调用api的版本
29 port: 6001, 29 port: 6001,
30 siteUrl: '//m.yohobuy.com', 30 siteUrl: '//m.yohobuy.com',
31 assetUrl: '//127.0.0.1:5001', 31 assetUrl: '//127.0.0.1:5001',
@@ -67,11 +67,6 @@ module.exports = { @@ -67,11 +67,6 @@ module.exports = {
67 handleExceptions: true, 67 handleExceptions: true,
68 maxFiles: 7 68 maxFiles: 7
69 }, 69 },
70 - udp: { // send by udp  
71 - measurement: 'yohobuy_wap_node_log',  
72 - level: 'error', // logger level  
73 - port: '4444' // influxdb port  
74 - },  
75 console: { 70 console: {
76 level: 'info', 71 level: 'info',
77 colorize: 'all', 72 colorize: 'all',
@@ -22,7 +22,7 @@ module.exports = (req, res, next) => { @@ -22,7 +22,7 @@ module.exports = (req, res, next) => {
22 return next(); 22 return next();
23 } 23 }
24 24
25 - if (res.statusCode == 403) { 25 + if (_.toNumber(res.statusCode) === 403) {
26 return res.end(); 26 return res.end();
27 } 27 }
28 28
@@ -21,7 +21,11 @@ const _getClientIp = req => { @@ -21,7 +21,11 @@ const _getClientIp = req => {
21 remoteIp = _.trim(arr[arr.length - 1]); 21 remoteIp = _.trim(arr[arr.length - 1]);
22 } 22 }
23 23
24 - return remoteIp; 24 + if (_.startsWith(remoteIp, '10.66.')) {
  25 + remoteIp = req.get('X-Real-IP');
  26 + }
  27 +
  28 + return _.trim(remoteIp);
25 }; 29 };
26 30
27 module.exports = () => { 31 module.exports = () => {
1 { 1 {
2 "name": "m-yohobuy-node", 2 "name": "m-yohobuy-node",
3 - "version": "5.5.11", 3 + "version": "5.5.20",
4 "private": true, 4 "private": true,
5 "description": "A New Yohobuy Project With Express", 5 "description": "A New Yohobuy Project With Express",
6 "repository": { 6 "repository": {
@@ -50,7 +50,7 @@ @@ -50,7 +50,7 @@
50 "xml2js": "^0.4.17", 50 "xml2js": "^0.4.17",
51 "yoho-express-session": "^2.0.0", 51 "yoho-express-session": "^2.0.0",
52 "yoho-md5": "^2.0.0", 52 "yoho-md5": "^2.0.0",
53 - "yoho-node-lib": "=0.2.11", 53 + "yoho-node-lib": "=0.2.17",
54 "yoho-zookeeper": "^1.0.8" 54 "yoho-zookeeper": "^1.0.8"
55 }, 55 },
56 "devDependencies": { 56 "devDependencies": {
@@ -13,6 +13,7 @@ let $phoneNum = $('#phone-num'), @@ -13,6 +13,7 @@ let $phoneNum = $('#phone-num'),
13 $loginBtn = $('#btn-login'), 13 $loginBtn = $('#btn-login'),
14 14
15 $captcha = $('#js-img-check'), 15 $captcha = $('#js-img-check'),
  16 + useVerify = $captcha.data('userverify'), // 170406 是否使用验证
16 17
17 pnPass = false, 18 pnPass = false,
18 pwdPass = false; 19 pwdPass = false;
@@ -23,15 +24,18 @@ let tip = require('plugin/tip'); @@ -23,15 +24,18 @@ let tip = require('plugin/tip');
23 let trim = $.trim; 24 let trim = $.trim;
24 let showErrTip = tip.show; 25 let showErrTip = tip.show;
25 26
26 -let validate = new Validate($captcha, {  
27 - useREM: {  
28 - rootFontSize: 40,  
29 - picWidth: 150  
30 - }  
31 -}); 27 +let validate = {};
32 28
33 -validate.init(); 29 +if (useVerify) {
  30 + validate = new Validate($captcha, {
  31 + useREM: {
  32 + rootFontSize: 40,
  33 + picWidth: 150
  34 + }
  35 + });
34 36
  37 + validate.init();
  38 +}
35 39
36 // 登录按钮状态切换 40 // 登录按钮状态切换
37 function switchLoginBtnStatus() { 41 function switchLoginBtnStatus() {
@@ -45,6 +49,47 @@ function resetForm() { @@ -45,6 +49,47 @@ function resetForm() {
45 $loginBtn.text('登录').addClass('disable'); 49 $loginBtn.text('登录').addClass('disable');
46 } 50 }
47 51
  52 +/**
  53 + * 登录校验
  54 + */
  55 +function loginAuth(params) {
  56 + $.ajax({
  57 + type: 'POST',
  58 + url: '/passport/login/auth',
  59 + data: params,
  60 + success: function(data) {
  61 + let res;
  62 +
  63 + validate && validate.type === 2 && validate.refresh();
  64 + if (data.code === 200) {
  65 + res = data.data;
  66 + showErrTip('登录成功');
  67 +
  68 + // 3秒后强制跳转
  69 + setTimeout(() => {
  70 + location.href = res.href;
  71 + }, 1500);
  72 +
  73 + $loginBtn.text('登录成功');
  74 + showErrTip('登录成功');
  75 + } else {
  76 + if (useVerify && data.captchaShow) {
  77 + ((data.changeCaptcha && validate.type !== 2) && validate.refresh());
  78 + }
  79 +
  80 + showErrTip(data.message);
  81 + resetForm();
  82 + }
  83 + },
  84 + error: function() {
  85 + showErrTip('网络断开连接啦~');
  86 + $loginBtn.text('登录');
  87 +
  88 + validate && validate.refresh();
  89 + }
  90 + });
  91 +}
  92 +
48 // Android-UC下显示select的direction:rtl无效的临时解决办法 93 // Android-UC下显示select的direction:rtl无效的临时解决办法
49 api.selectCssHack($countrySelect); 94 api.selectCssHack($countrySelect);
50 95
@@ -90,52 +135,21 @@ $loginBtn.on('touchstart', function() { @@ -90,52 +135,21 @@ $loginBtn.on('touchstart', function() {
90 } 135 }
91 136
92 if ((api.phoneRegx[areaCode].test(pn) || areaCode !== '+86') && api.pwdValidate(pwd)) { 137 if ((api.phoneRegx[areaCode].test(pn) || areaCode !== '+86') && api.pwdValidate(pwd)) {
93 - validate.getResults().then((result) => {  
94 - $loginBtn.text('正在登录...').addClass('disable');  
95 - let params = {  
96 - areaCode: areaCode.replace('+', ''),  
97 - account: pn,  
98 - password: pwd  
99 - };  
100 -  
101 - $.extend(params, result);  
102 -  
103 - $.ajax({  
104 - type: 'POST',  
105 - url: '/passport/login/auth',  
106 - data: params,  
107 - success: function(data) {  
108 - let res;  
109 -  
110 - validate.type === 2 && validate.refresh();  
111 - if (data.code === 200) {  
112 - res = data.data;  
113 - showErrTip('登录成功');  
114 -  
115 - // 3秒后强制跳转  
116 - setTimeout(() => {  
117 - location.href = res.href;  
118 - }, 1500);  
119 -  
120 - $loginBtn.text('登录成功');  
121 - showErrTip('登录成功');  
122 - } else {  
123 - if (data.captchaShow) {  
124 - ((data.changeCaptcha && validate.type !== 2) && validate.refresh());  
125 - }  
126 -  
127 - showErrTip(data.message);  
128 - resetForm();  
129 - }  
130 - },  
131 - error: function() {  
132 - showErrTip('网络断开连接啦~');  
133 - $loginBtn.text('登录');  
134 -  
135 - validate.refresh();  
136 - } 138 + let params = {
  139 + areaCode: areaCode.replace('+', ''),
  140 + account: pn,
  141 + password: pwd
  142 + };
  143 +
  144 + if (useVerify) {
  145 + validate.getResults().then((result) => {
  146 + $loginBtn.text('正在登录...').addClass('disable');
  147 + $.extend(params, result);
  148 + loginAuth(params);
137 }); 149 });
138 - }); 150 + } else {
  151 + loginAuth(params);
  152 + }
139 } else { 153 } else {
140 showErrTip('账号或密码有错误,请重新输入'); 154 showErrTip('账号或密码有错误,请重新输入');
141 $loginBtn.text('登录').addClass('disable'); 155 $loginBtn.text('登录').addClass('disable');
@@ -32,7 +32,9 @@ let validate = new Validate($captcha, { @@ -32,7 +32,9 @@ let validate = new Validate($captcha, {
32 } 32 }
33 }); 33 });
34 34
35 -validate.init(); 35 +if ($captcha.data('userverify')) {
  36 + validate.init();
  37 +}
36 38
37 // 登录按钮状态切换 39 // 登录按钮状态切换
38 function switchLoginBtnStatus() { 40 function switchLoginBtnStatus() {
@@ -60,6 +62,67 @@ function hideRetrivePanel() { @@ -60,6 +62,67 @@ function hideRetrivePanel() {
60 $ways.hide(); 62 $ways.hide();
61 } 63 }
62 64
  65 +/**
  66 + * 登录校验
  67 + */
  68 +function loginAuth(params, acc) {
  69 + $.ajax({
  70 + type: 'POST',
  71 + url: '/passport/login/auth',
  72 + data: params,
  73 + success: function(data) {
  74 + let res,
  75 + LOGI_TYPE;
  76 +
  77 + if (acc.indexOf('@') > 0) {
  78 + LOGI_TYPE = 8;
  79 + } else {
  80 + LOGI_TYPE = 5;
  81 + }
  82 +
  83 + if (window._yas && window._yas.sendCustomInfo) {
  84 + window._yas.sendCustomInfo({
  85 + op: 'YB_MY_LOGIN_C',
  86 + param: JSON.stringify({
  87 + C_ID: window._ChannelVary[window.cookie('_Channel')],
  88 + LOGI_TYPE: LOGI_TYPE
  89 + })
  90 + }, true);
  91 + }
  92 + validate && validate.type === 2 && validate.refresh();
  93 + if (data.code === 200) {
  94 + res = data.data;
  95 +
  96 + showErrTip('登录成功');
  97 + location.href = res.href;
  98 + $loginBtn.text('登录成功');
  99 + } else {
  100 + $captcha.data('userverify', data.captchaShow);
  101 + if (data.captchaShow) {
  102 + if (validate.atWorking) {
  103 + ((data.changeCaptcha && validate.type !== 2) && validate.refresh());
  104 + } else {
  105 + validate.init();
  106 + }
  107 + }
  108 +
  109 + showErrTip(data.message);
  110 + resetForm();
  111 + }
  112 +
  113 + return data;
  114 + },
  115 + error: function() {
  116 + showErrTip('网络断开连接啦~');
  117 +
  118 + validate && validate.refresh();
  119 + },
  120 + complete: function() {
  121 + $loginBtn.text('登录').removeClass('disable');
  122 + }
  123 + });
  124 +}
  125 +
63 // 密码显示与隐藏 126 // 密码显示与隐藏
64 api.bindEyesEvt(); 127 api.bindEyesEvt();
65 128
@@ -95,67 +158,23 @@ $loginBtn.on('touchstart', function() { @@ -95,67 +158,23 @@ $loginBtn.on('touchstart', function() {
95 158
96 // 验证账号(数字或者邮箱)和密码合理性 159 // 验证账号(数字或者邮箱)和密码合理性
97 if ((/^[0-9]+$/.test(acc) || api.emailRegx.test(acc)) && api.pwdValidate(pwd)) { 160 if ((/^[0-9]+$/.test(acc) || api.emailRegx.test(acc)) && api.pwdValidate(pwd)) {
98 - validate.getResults().then((result) => {  
99 - $loginBtn.text('正在登录...').addClass('disable');  
100 -  
101 - let params = {  
102 - account: acc,  
103 - password: pwd  
104 - };  
105 -  
106 - $.extend(params, result);  
107 -  
108 - $.ajax({  
109 - type: 'POST',  
110 - url: '/passport/login/auth',  
111 - data: params,  
112 - success: function(data) {  
113 - let res,  
114 - LOGI_TYPE;  
115 -  
116 - if (acc.indexOf('@') > 0) {  
117 - LOGI_TYPE = 8;  
118 - } else {  
119 - LOGI_TYPE = 5;  
120 - }  
121 -  
122 - if (window._yas && window._yas.sendCustomInfo) {  
123 - window._yas.sendCustomInfo({  
124 - op: 'YB_MY_LOGIN_C',  
125 - param: JSON.stringify({  
126 - C_ID: window._ChannelVary[window.cookie('_Channel')],  
127 - LOGI_TYPE: LOGI_TYPE  
128 - })  
129 - }, true);  
130 - }  
131 - validate.type === 2 && validate.refresh();  
132 - if (data.code === 200) {  
133 - res = data.data;  
134 -  
135 - showErrTip('登录成功');  
136 - location.href = res.href;  
137 - $loginBtn.text('登录成功');  
138 - } else {  
139 - if (data.captchaShow) {  
140 - ((data.changeCaptcha && validate.type !== 2) && validate.refresh());  
141 - }  
142 -  
143 - showErrTip(data.message);  
144 - resetForm();  
145 - }  
146 -  
147 - return data;  
148 - },  
149 - error: function() {  
150 - showErrTip('网络断开连接啦~');  
151 -  
152 - validate.refresh();  
153 - },  
154 - complete: function() {  
155 - $loginBtn.text('登录').removeClass('disable');  
156 - }  
157 - });  
158 - }, () => {}); 161 + let params = {
  162 + account: acc,
  163 + password: pwd
  164 + };
  165 +
  166 + if ($captcha.data('userverify')) {
  167 + validate.getResults().then((result) => {
  168 + $loginBtn.text('正在登录...').addClass('disable');
  169 +
  170 + $.extend(params, result);
  171 +
  172 + // auth
  173 + loginAuth(params, acc);
  174 + }, () => {});
  175 + } else {
  176 + loginAuth(params, acc);
  177 + }
159 } else { 178 } else {
160 showErrTip('账号或密码有错误,请重新输入'); 179 showErrTip('账号或密码有错误,请重新输入');
161 $loginBtn.text('登录').removeClass('disable'); 180 $loginBtn.text('登录').removeClass('disable');
@@ -102,6 +102,11 @@ exports.processProductList = (list, options) => { @@ -102,6 +102,11 @@ exports.processProductList = (list, options) => {
102 return; 102 return;
103 } 103 }
104 104
  105 + // H5 暂时不支持全球购商品,先过滤掉 2017.04.09
  106 + if (product.is_global === 'Y') {
  107 + return;
  108 + }
  109 +
105 // 商品信息有问题,则不显示 110 // 商品信息有问题,则不显示
106 if (!( 111 if (!(
107 (product.product_id && _.get(product, 'goods_list.length', 0)) || product.recommend_type 112 (product.product_id && _.get(product, 'goods_list.length', 0)) || product.recommend_type