aozhiwei 7474f9a409 1
2023-07-25 17:44:29 +08:00

153 lines
4.4 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

const app = require('j7/app');
const utils = require('j7/utils');
const constant = require('../constant');
const Redis = require('../services/redis');
const RANKING_KEY = 'game2006api:';
const LAST_IDX = 'userLastIdx';
class Rankings {
async start() {
console.log('Rankings.start');
while (true) {
await this.doRanking();
const sleepTime = 60*60*2
console.log('sleepTime:' + sleepTime, new Date(), sleepTime /60);
await utils.sleep(sleepTime * 1000);
}
}
async doRanking() {
try {
const {err, conn} = await app.getDbConn("GameDb20060");
if (err){
throw err
}
if (await Redis.exists(RANKING_KEY + "account")){
await Redis.del(RANKING_KEY + 'account')
await Redis.del(RANKING_KEY + 'ranking')
await this.calcRanking();
console.log("跟新rank榜单")
}else {
await this.calcRanking();
console.log("生成rank榜单")
}
}catch (err){
console.log(err);
}
}
//计算用户排行榜
async calcRanking() {
console.log("calc ranking...");
const {err, conn} = await app.getDbConn("GameDb20060");
if (err) {
throw err;
}
if (!err && conn) {
// 从user表中遍历所有用户每次取1000个用户逐步加入到排序表中
let sorted = [];
let lastIdx = 0;
while(lastIdx>=0) {
const result = await this.getRecords(conn, lastIdx, 1000);
lastIdx = result.lastIdx;
if (lastIdx != -1) {
this.recordsSort(sorted, result.records)
}
}
await this.pushResultToRedis(sorted);
// let rankList = await this.pushRankingResult(sorted);
// console.log(rankList);
//存储到redis中
// let listJson = JSON.stringify(rankList);
// Redis.set(RANKING_KEY + "rank",listJson);
console.log("calc ranking end");
}
}
//增加排名列
async pushResultToRedis(sorted) {
let rankingList = [];
await utils.serial(
sorted,
(value , index) =>{
value.ranking = index+1
Redis.hset(RANKING_KEY + "ranking",value.ranking,value.account_id)
Redis.hset(RANKING_KEY + "account",value.account_id,value.ranking)
}
)
}
//获取用户记录
async getRecords(conn, lastIdx, limit) {
const {err, rows} = await conn.execQuery(
'select idx,account_id,channel,convert(`name` using utf8) as name,head_id,head_frame,rank,history_best_rank,score,history_best_score,createtime, score_modifytime from t_user where idx > ? order by idx LIMIT ?',
[
lastIdx,
limit
]
);
if (err) {
throw err;
}
if (rows.length==0) {
return {
lastIdx: -1,
records: []
};
}
// Redis.set(LAST_IDX,rows[rows.length-1].idx)
return {
lastIdx: rows[rows.length-1].idx,
records: rows
};
}
//给记录按分数排序
recordsSort(sorted, records) {
// 根据分数加入到排序表中
for (let element of records) {
if (element.score>2800) {
if (sorted.length >= 10000){
if (element.score >= sorted[sorted.length - 1].score){
sorted.pop()
this._recordsSort(sorted,element)
}
} else {
this._recordsSort(sorted,element)
}
}
}
// if (sorted.length>10000) {
// sorted.length = 10000;
// }
}
_recordsSort(sorted,element){
sorted.push(element);
sorted.sort(function(a,b) {
let r = b.score - a.score;
if (r==0) {
r = a.score_modifytime - b.score_modifytime;
}
if (r==0) {
r = a.idx - b.idx;
}
return r;
});
}
}
function init() {
(new Rankings()).start();
}
exports.init = init;