jsdi
V2EX  ›  问与答

排行榜怎么防止恶意用户刷榜?

  •  
  •   jsdi · Jan 6, 2022 · 6196 views
    This topic created in 1769 days ago, the information mentioned may be changed or developed.
    业务需求是前端有一个网页小游戏,通过小游戏会获得一个分数,这个分数要提交到后端进行排序返回小游戏的分数排行榜。如何不使用复杂的加密算法简单的实现这个需求呢?

    刚开始是用 base64 编码,不至于那么裸奔。后来导师让我用 referer 请求头实现,只有是公司域名才能访问此接口。但是 google 发现 referer 也是可以伪造的,而且使用 referer 测试好像没法单独进行接口测试。

    请问真的可以使用 referer 实现吗?有没有其他实现方式呢?
    35 replies  •  2022-01-07 09:46:43 +08:00
    murmur
    murmur
    Jan 6, 2022
    1
    这不就是反外挂技术么,肯定得是边玩边追踪的,大概就是给开发人员一个更宽松的条件,让他在上帝模式下打出一个分数,然后以这个分数为基准,超过这个分数离谱的就得人工去核算了

    现在还没看到一个完全自动化反外挂的方案
    murmur
    murmur
    Jan 6, 2022
    2
    当然这种方式也比不上玩家的脑洞,原神不就是各种叠 buff 搞伤害竞赛,最高都叠到 700w 了,所以官方干脆锁了伤害上限
    stormer
    stormer
    Jan 6, 2022
    3
    纯前端提交的,你只能用 js 写个校验算法,然后要对 js 进行层层加密,这个只能防菜鸟,高手没用

    没其他方式了...所有校验前端提交的方式只能说增加伪造门槛, 不过你可以后端自己伪造分数, 让自己人排 1/2/3 名,哈哈哈
    mineralsalt
    mineralsalt
    Jan 6, 2022❤️2
    4
    先考虑这个游戏有没有人玩吧
    jsdi
    jsdi
    OP
    Jan 6, 2022
    5
    @murmur 安全可靠的好像就只有非对称加密可以实现,但又感觉没必要太复杂哈哈
    jsdi
    jsdi
    OP
    Jan 6, 2022
    6
    @mineralsalt 哈哈哈应该还是有人玩的
    jsdi
    jsdi
    OP
    Jan 6, 2022
    7
    @stormer 确实 设置一个上限是最简单的
    tomczhen
    tomczhen
    Jan 6, 2022 via Android
    8
    领奖条件加一条:要求获奖用户直播打一次,得分至少要到获奖分数的 75%。
    :doge:
    Rheinmetal
    Rheinmetal
    Jan 6, 2022❤️2
    9
    上传操作和随机种子 看看人能否 fuxian
    排行榜延迟显示 人工审核
    boringcc
    boringcc
    Jan 6, 2022
    10
    要求游玩的人一边录屏摄手打
    oppoic
    oppoic
    Jan 6, 2022
    11
    微信授权登录之后才可以玩,刷榜的碰到这种的基本就折腾了
    loading
    loading
    Jan 6, 2022❤️2
    12
    微信绑定登陆,必须点一个广告再说。
    Celebi
    Celebi
    Jan 6, 2022
    13
    交 5 元查看排行
    wu67
    wu67
    Jan 6, 2022
    14
    没必要. 这种通常情况下是把游戏难度搞难一点, 然后开发的时候页面仔直接就能给你玩出极限分数了. 超出这个的基本上都难, 要么开挂, 要么是赌脸那种寿命玩法. 榜爱怎么排就怎么排, 反正统计是需要服务器资源和时间的, 你觉得不对, 那就按前面测出的极限分数, 让后台把超过这个分数太多的给 ban 了...
    by 一个曾经切过几个活动页面游戏的前端仔.
    yancy0l
    yancy0l
    Jan 6, 2022
    15
    既然是导师的实现方案,那可能不是商业化的东西,只是产品功能需要。看了描述应该是担心 通信报文有明文数据被修改,那用加密算法挺合适的,非对称加密,完美解决问题,而且也不是特别麻烦,一般网上有 Demo 。 这样实现,更合理一些,别为了解决安全问题,去绕弯子。
    leafre
    leafre
    Jan 6, 2022
    16
    除非把逻辑放在服务端实现,否则只能增加破解难度
    jackzhengjbs
    jackzhengjbs
    Jan 6, 2022 via Android
    17
    啥游戏啊?我的八门神器已经饥渴难耐了
    Mutoo
    Mutoo
    Jan 6, 2022
    18
    游戏可以实现录制功能,将客户端版本、玩家每帧操作和随机数种子记录下来,高分玩家分数与记录一并提交,后端可以用一个 headless 模拟器快速重放游戏过程,看看分数是否一致即可。
    libook
    libook
    Jan 6, 2022
    19
    referer 没用,可以伪造。

    计分机制、加密秘钥、加密算法都放到 wasm 里,有了最终分数后用对称加密发送到服务端,服务端解密记录排序返回排行榜。

    为了避免重放请求攻击,需要在加密的时候加个时间戳,这样即便分数相同加密后的密文也会不一样,服务端解密后判断时间戳是不是在过去一定时间范围内。

    以上这么处理之后,再想刷榜就只能逆向 wasm 代码,或者从游戏玩法上面做一些外挂。
    jsdi
    jsdi
    OP
    Jan 6, 2022
    20
    说得很好,下次别说了[:doge]
    maplerecall
    maplerecall
    Jan 6, 2022 via Android
    21
    没用的,referer 一样可以十分简单的伪造。除非游戏主要逻辑在服务端,基本没有什么好方法能够限制客户端作弊行为,无论 web 还是原生客户端。
    ch2
    ch2
    Jan 6, 2022
    22
    无法避免
    mxT52CRuqR6o5
    mxT52CRuqR6o5
    Jan 6, 2022
    23
    倒是确实直接把逻辑扔 wasm 里相比在 js 层搞各种东西破解难度要大得多
    lysS
    lysS
    Jan 6, 2022
    24
    @jsdi TLS 是防止用户访问了伪造的服务器,而且你这是网页版的,做什么都不能防止用户给你发假数据。
    Privileges
    Privileges
    Jan 6, 2022
    25
    Referer 伪造成本太低了。。。
    itechify
    itechify
    Jan 6, 2022
    26
    把菜鸟用户拦截就行了,前端代码混淆,前端上传分数接口数据非对称加密
    final7genesis
    final7genesis
    Jan 6, 2022
    27
    @libook 感觉这个方案最靠谱些
    chashao
    chashao
    Jan 6, 2022
    28
    实时上传玩家操作,在服务端进行玩法逻辑计算以及计算分数
    t6attack
    t6attack
    Jan 6, 2022
    29
    终极解决方法只有一个:服务端运算。
    t6attack
    t6attack
    Jan 6, 2022
    30
    打个形象的比方:打完游戏,分数由客户机一次提交,这就好比考完试,让学生自己判卷,然后把分数报上来。也不检查卷纸。那么这个分数排行榜?只能用作参考。不能认真。
    省时点的逻辑,就是优化排行榜:加个简单判断,把排行榜里离谱的分数过滤掉。再把短时间取得不可能分数的过滤掉。这样,排行榜看起来就能正常一点。

    为什么 PC 上外挂很多,游戏机上相对较少?因为 PC 是全功能生产工具,傻瓜式的内存修改器就 N 多种。
    不管你提交过程怎么加密,怎么防伪造。这个游戏分数是一定存在某段内存里的。我用 CE 修改器定位到分数的内存地址,做一次乘方。然后游戏结束,这个离谱的分数,经过你那复杂的加密逻辑,顺利的通过服务端,登上排行榜。你辛苦编写的加密逻辑,全都变成了无用功。
    你的程序运行在我的地盘,我对它有上帝视角。你让我自己判卷,我想判多少分就判多少分。就是这么个逻辑。
    bellx
    bellx
    Jan 6, 2022 via iPhone
    31
    楼上也说到了,最终解就是服务端计算,前端做加密只是破解难易的区别而已
    jsdi
    jsdi
    OP
    Jan 6, 2022
    32
    @oneisall8955 非对称加密有用吗?公钥放在客户端,用户通过翻 js 文件就可以看到加密逻辑,然后他也可以把加完密的离谱分数提交到后端,后端是没法判断的
    jsdi
    jsdi
    OP
    Jan 6, 2022
    33
    @t6attack 确实 前端还是太裸奔了阿 底裤都让人看光了
    lawler
    lawler
    Jan 7, 2022
    34
    就冲 ”后来导师让我用 referer 请求头实现“ 这句话。
    游戏内容都用不着抓包这么啰嗦的手法。

    请问真的可以使用 referer 实现吗?
    答:可以,但只能避免试图刷榜中的很小一部分。
    有没有其他实现方式呢?
    答:很多并不能完全阻断这种行为。所以归纳下来无非是三种方向,加密(数据、协议等方式方法尽量复杂)、记录(操作日志、录像录屏、实时数据流等尽可能详尽可追溯)和加密结合记录。
    itechify
    itechify
    Jan 7, 2022 via Android
    35
    @jsdi 防菜鸟而已,一般的菜鸟看到接口要上传加密的数据就不想翻前端源码,再有混淆了前端代码也不太好找到密钥和加密算法
    About   ·   Help   ·   Advertise   ·   Blog   ·   API   ·   FAQ   ·   Privacy   ·   Solana   ·   2493 Online   Highest 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 87ms · UTC 04:38 · PVG 12:38 · LAX 20:38 · JFK 23:38
    ♥ Do have faith in what you're doing.