Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/475.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
在基于JavaScript的游戏中制作在线高分列表的最佳实践是什么?_Javascript - Fatal编程技术网

在基于JavaScript的游戏中制作在线高分列表的最佳实践是什么?

在基于JavaScript的游戏中制作在线高分列表的最佳实践是什么?,javascript,Javascript,[我知道在防止高分列表作弊方面也有类似的问题,但没有答案对基于JavaScript的游戏没有帮助,所以在告诉我类似帖子之前,请试着思考我的问题。我问的是最佳实践,因为JavaScript对用户来说总是可见的,因此不可能o完全防止作弊,我只想让它更难。] 我正在开发一个在浏览器中运行的基于JavaScript的游戏。我想制作一个高分列表,其中包含所有用户的用户名和分数。为了实现这一点,浏览器通过AJAX将用户名和分数发送到我的服务器 将假分数提交到此列表将相当容易:可以查看AJAX请求,然后使用假

[我知道在防止高分列表作弊方面也有类似的问题,但没有答案对基于JavaScript的游戏没有帮助,所以在告诉我类似帖子之前,请试着思考我的问题。我问的是最佳实践,因为JavaScript对用户来说总是可见的,因此不可能o完全防止作弊,我只想让它更难。]

我正在开发一个在浏览器中运行的基于JavaScript的游戏。我想制作一个高分列表,其中包含所有用户的用户名和分数。为了实现这一点,浏览器通过AJAX将用户名和分数发送到我的服务器

将假分数提交到此列表将相当容易:可以查看AJAX请求,然后使用假分数创建自己的AJAX请求。使用令牌之类的东西必须与其他数据一起发送是毫无意义的,因为这样很容易发现

我唯一能防止作弊的方法是向服务器发送每个用户操作的描述,并在那里计算分数。但这实际上并不可行,因为这对服务器来说太多了


我接受了一个答案,但如果有人对如何使作弊更难有其他想法,请创建另一个答案!

你几乎回答了自己的问题。如果你真的想让用户更难作弊,请将游戏日志发送到服务器,在那里你将计算分数

您不必发送所有事件,只需发送影响结果分数的事件即可

不过,有一些技巧可以帮助您:

在您的请求中包含签名。类似于MD5secret_key+params。尽管密钥必须在JS源代码中,但它将有效地保护您免受简单请求拦截,请参见和

如果这是一个多人游戏,接受客户计算的分数并进行比较。假设大多数用户都是诚实的,作弊者将非常明显

你可以设置一个分数上限,这是一个无法达到的结果。每个发布分数高于这个的人都是骗子。例如,快速打字游戏:没有人能以1500个字符/分钟的速度键入正确的文本,即使700个字符/分钟也很难实现


我喜欢玩欺骗作弊者-类似于使用令牌来验证每次调用更新时更改的分数…但我接受使用重复令牌发布的作弊分数。然后我只向作弊者显示作弊分数,因此它似乎有效,但现在作弊者在沙箱中看到了他的结果.

关于分数提交:

从服务器请求一些令牌,这应该是基于时间的,并且仅在大约2秒钟内有效 仅接受包含此令牌的有效哈希、一些salt和分数的提交。 这可以防止手动篡改请求,因为这会使分数超时。如果您想解释高延迟,请在超时之前给它多一点时间

散列函数:

对压缩代码中的哈希函数进行置乱http://dean.edwards.name/packer/ 如果使用jQuery或其他库,确实会产生令人讨厌的代码—只要将哈希功能放在库文件中,查找起来就会非常糟糕,特别是如果使用函数名,如h:

处理分数变量本身:

每个拥有调试控制台的人都可以在运行时更改变量,但如果将整个Javascript封装在一个函数中并调用它,则全局命名空间中没有任何内容,并且很难访问变量:

作用{ //你的js代码在这里 };
根据游戏的性质,您可以使用其他玩家验证结果。在简单的游戏中,这非常有效,在其他游戏中,您必须聪明,并围绕此功能开发许多方面。例如,有时可以根据记录的操作重播和验证结果。此技巧特别适用于人类与AI,只要这个模型是确定性的

另一个选择是重新定义分数概念,使其更以用户为中心,这很容易实现,但往往很难设计,并且只适用于少数类别的游戏

纯粹的推测方法也是可能的,有时很容易知道某些参数不合适。这不会避免作弊,但会大大缓和作弊

最复杂的部分是得到一个足够小的回放日志,但是由于除了玩家的动作之外,大多数数据都不是随机的,实际上不是随机的,因为这取决于游戏,本质上是一个正确设计的问题


此外,如果游戏性得到了足够的扩展,对于动作游戏等,你可以通过进行近似、合并(例如,运动向量)和剪辑无趣的内容来获得大量压缩。

我对此有很多想法,最终决定只使用loca l个人得分很高,所以作弊对玩家并没有真正的好处,对其他人也没有伤害。然而,我的游戏只是一个简单的游戏,有人抱怨没有竞争对手

选项2,是-所采取的方法,以显示您在互联网人群中的地位。所以你们看不到任何其他的结果,人们也看不到你们的结果——但你们可以把自己和人群进行比较


p、 s:说真的,任何一个有Firebug/WebInspector的孩子都可以轻松地破解你的JS游戏,并最终获得很高的分数。

理想情况下,你可以将整个事件日志发送到服务器进行检查。也许您可以实现一个启发式,以便轻松确定分数是否在一组界限内。例如,如果总游戏时间为5秒,您可能会期望比游戏时间长得多的分数低得多

或者,您可以选择手动检查事件日志,以获得真正高分的top-X,这应该是相当稳定的

如果你在做任何像随机事件这样的随机性的事情,你需要一个种子随机数生成器。如果你没有想到的话,这可能会很棘手

您可以找到更多的资源,但它实际上只是归结为服务器端检查。JavaScript在这方面不是唯一的,但可能最容易被利用,因为您不仅可以看到客户端-服务器通信,还可以看到客户端源代码

像星际争霸这样的游戏只记录鼠标点击和按键。然后模拟实际命令。我预计《蠕虫世界末日》也会做类似的事情,但它们的随机事件(如香蕉的弹性)没有正确播种,因此在即时重播中,您可能会得到不同的结果

你可以想象类似的MMORPG。服务器根据按键来计算你的位置,客户端只是试图给出一个很好的早期解释,但当你落后时,你可能会出现偏差,因为服务器会将你放在地图上的其他位置,因为它没有及时获取按键事件


如果你攻击了某个东西,服务器会检查你是否足够接近,以及你在当前统计数据和装备下预计会受到多少伤害。

记录游戏中的关键点,然后将分数与这些关键点一起提交。当人们看到高分时,他们还可以看到所玩游戏的概况,如果看起来不作弊就不可能像那样玩,那么人们可以向管理员报告这些可疑的分数。

如果你依赖客户端将最终分数发送到服务器,那么就没有办法阻止天才作弊。但我认为你也许能够阻止愚蠢的人和诚实的人作弊,这样只有天才和他们的朋友才能主宰你的排行榜

我可以想到两种方法

一,。通过默默无闻实现安全

提出一种算法,将简单的分数转换成其他分数,然后再转换回来。然后混淆它。使它复杂化。写一个函数,将它乘以q,再除以拉尔夫。对它应用一组函数,在5-15个对它进行随机操作的函数中,包括一个将数字乘以19的素数。在您的服务器上,检查以确保每个传入的数字或字母都可以被19整除,然后解码

你必须写一堆复杂的代码,把简单的分数转换成疯狂的样子。您必须以最低效、最通俗的代码方式编写一系列函数。使用 你要做的一件事就是设置一组不允许的值。也就是说,可能所有的分数都是偶数。如果有人试图提交一个奇数,他们显然是在作弊,而且非常愚蠢

二,。时间

您应该能够知道用户何时开始游戏。您应该启动一个会话,并在他们请求页面时进行记录。然后你也应该能够知道他们什么时候提交了分数。你也应该知道最大积分的时间序列。也就是说,你能得到每分钟5分、每分钟100分、每分钟^3分等吗。。。若用户提交的分数超过了这段时间内可能的分数,那个么他们就是在作弊

您还可以在服务器和客户端处理之间取得平衡,并让客户端通过ajax每x分钟发送一次进度更新。如果它没有报告,你就认为它已经被破坏了,就像邦德电影中那样,当他潜入敌人的巢穴时,他打断了一些守卫的脖子。当警卫对他接下来10分钟的值机手续没有反应时,警报就会响起


如果你曾经玩过Zynga扑克,你可能已经看到了当桌上的人互联网连接缓慢时会发生什么。

我使用了一个系统,该系统使用基于时间的请求,有3个参数

req number, curr time, score 
在对更新分数请求的响应中,从服务器返回req编号,每次这是一个新的随机值

当前时间不是从计算机时钟计算的,而是从ga开始计算的 并使用ajax请求与服务器同步

更新分数请求在最长30秒左右的短时间间隔后发送

在服务器上应用以下检查

时间在距离服务器时钟10秒的范围内。 自发送req编号以来,时间不超过40秒。 30秒后发送的分数更改可能在2倍人力范围内

仅当通过上述检查或用户收到断开连接消息时,分数才会更新:


这比大多数方法都要简单,可以很好地消灭所有临时黑客,除非他们读了这篇文章,并想尽快更新分数或自己编写脚本。

如果不作弊比游戏本身更重要,尝试以一种看起来像是找到数学问题的解决方案的方式来构建和展示你的游戏。因此,服务器将向客户端提供一个问题实例示例A:一个棋盘将在3步中获胜,示例B:一个随机生成的几何破折号级别,用户必须解决该问题并发回解决方案示例A:获胜的动作,示例B:准确的时间戳和跳跃强度以避开障碍

使用这种方法,关键是服务器不会两次发送同一级别,否则作弊者可以提前计划和设计他的解决方案。此外,游戏信息必须在服务器中随机生成,而不是通过种子发送,否则作弊者可以伪造种子并随着时间设计解决方案

有效提交的给定时间也必须在服务器中进行跟踪,以便它们只有播放时间而没有设计时间。如果作弊者足够优秀,能够以诚实玩家赢得比赛的速度设计出解决方案,那么他们就有足够的天赋诚实地赢得比赛,并且应该得到他们的分数

回到服务器,您需要检查提交的解决方案是否对该实例有效

当然,这种方法需要大量额外的工作:更多的游戏实例(理想情况下是无限的和不重复的)、服务器端生成、服务器端提交验证、时间上限等


注意:我知道这些方法在几年前已经在多个解决方案中提出,我想补充我的微薄贡献。

我已经想出了无法达到的结果的想法-但这不会阻止作弊者以一个可达到的分数再次尝试。|对我来说,计算服务器上的所有内容都是不可能的。我没有一台服务器能够为许多用户处理这些问题。在计算分数时,你总能得到客户的帮助。存储日志,将其提供给客户,让他们计算分数,然后将结果上传回您。你为带宽和临时日志存储付费,但服务器上没有计算负载。当源代码开放阅读时,JS游戏很难保护。尝试对服务器要解码的数据实施可逆加密。此外,模糊/变量和名称替换/缩小此加密算法的JS代码。虽然仍然可以通过反向工程代码和了解加密工作原理来篡改,但至少可以通过混淆传输的数据(尤其是在使用firefox TamperData add-On时)来帮助篡改。这其实并不重要,但您的分数上限是一个不好的例子。很多人用速记员每分钟可以突破1500个字符,出于某种原因,这些人喜欢在网站上输入高分列表。现代速记员用有经验的速记员输出真实、正确、精确的英语。事实上,我知道至少有一个打字网站从电脑上插入速记的人那里获得了大量的合法分数。所以只是说…这绝对有利于拒绝一些伪造分数,但我认为这不会阻止许多作弊者。一个人可以阻止第一个请求,并使用令牌来请求作弊分数。-+不过我还是要感谢这个好主意!因为任何解决方案都可以进行反向工程,所以实际上没有任何最佳实践。@thedaian建议更好的描述!这根本不能防止作弊,复制和粘贴一些代码就足够了。这确实可以防止“篡改”代码以解锁通常无法访问的可能级别或模式。比如,我“黑客”解锁了当你让它运行更长时间时出现的动画,不知道它是否仍然有效,这涉及到啤酒。在Chrome和firefox中,你可以在调试器中实时编辑javascript源代码。因此,虽然它会阻止window.game.score=9999或window.player.health=Infinity;它不会保护任何this.score=9999或this.health=Infinity;你到底是什么意思?你可以使用其他玩家来验证结果?最简单的形式是,用户需要在运行游戏时处理其他玩家的数据,而不是自己的数据。例如,就在提交自己的分数之前。这是基于这样一个假设,即发送一个小的有效载荷是便宜的,所以
你必须很聪明,先简化,然后分而治之。这不一定是瞬间的,你可以有一个私人高分表,只有在验证后才能公开移动。让我把答案扩大一点……是的,这些东西肯定会让欺骗变得更难。这是一个好主意,但我认为只有当客户端的源代码不可访问时,这种方法才能很好地工作。例如,如果客户端是web浏览器,那么所有用于解决级别问题的代码都可以被潜在的作弊者找到。在许多情况下,源代码只包含游戏规则,而没有任何关于如何获胜的线索。例如,在一个国际象棋拼图或街机游戏中,您必须跳跃以避开障碍物,代码将检测用户是否碰到障碍物,但它不会帮助您获胜或为您提供线索。如果作弊者修改代码,使障碍物消失,那么他将在本地获胜,但游戏将提交服务器不会验证的解决方案,对于该级别的实例,解决方案将遇到障碍物