diff --git a/src/controllers/AccountController.ts b/src/controllers/AccountController.ts index d0fd7e9..2a7eeb9 100644 --- a/src/controllers/AccountController.ts +++ b/src/controllers/AccountController.ts @@ -13,6 +13,7 @@ import { import { fetchAccount } from '../dao/AccountDao' import { generateId } from '../utils/security.util' import { getRandom } from '../utils/number.util' +import { RobotDao } from '../dao/RobotDao' const isProd = process.env.NODE_ENV === 'production' const DEFAULT_NICKNAME = '匿名玩家' @@ -72,23 +73,26 @@ export default class AccountController extends BaseController { let accountid, targetScore if (datas.length > 0) { for (let i = 0; i < datas.length; i += 2) { - let gameing = await checkGameing(datas[i]) - if (gameing) { - continue - } if (!datas[i].startsWith(BaseConst.ROBOT_PREFIX)) { continue } - if (!accountSet.has(datas[i]) ) { - accountid = datas[i] - targetScore = datas[i + 1] | 0 - break + if (accountSet.has(datas[i])) { + continue } + let gameing = new RobotDao().checkGameing(datas[i]) + if (gameing) { + continue + } + accountid = datas[i] + targetScore = datas[i + 1] | 0 + break } } + if (!accountid) { accountid = BaseConst.ROBOT_PREFIX + generateId() targetScore = getRandom(min, max) | 0 + new RobotDao().setGameing(accountid) } let account = await fetchAccount({accountid, robot: true}) if (account.isnew) { @@ -103,7 +107,6 @@ export default class AccountController extends BaseController { account.isnew = 0 await account.save() } - await setGameing(accountid, 30) return { accountid: account._id, nickname: account.nickname || DEFAULT_NICKNAME, diff --git a/src/dao/RobotDao.ts b/src/dao/RobotDao.ts new file mode 100644 index 0000000..6964adb --- /dev/null +++ b/src/dao/RobotDao.ts @@ -0,0 +1,28 @@ +import { singleton } from '../decorators/singleton.decorator' + +const MAX_SEC = 30 +@singleton +export class RobotDao { + accountSet: Map + constructor() { + this.accountSet = new Map() + } + + setGameing(key: string) { + let now = Date.now() / 1000 | 0 + this.accountSet.set(key, now) + } + checkGameing(key: string) { + let now = Date.now() / 1000 | 0 + for(let [key, sec] of this.accountSet) { + if (now - sec >= MAX_SEC) { + this.accountSet.delete(key) + } + } + let result = this.accountSet.has(key) + if (!result) { + this.accountSet.set(key, now) + } + return result + } +}