Javascript anti-triche pour navigateur / jeu HTML5

35

Je prévois de créer un jeu d'action à un seul joueur en js / html5, et j'aimerais éviter de tricher. Je n'ai pas besoin d'une protection à 100%, car ce ne sera pas un jeu multijoueur, mais je veux un niveau de protection.

Alors, quelles stratégies proposez-vous au-delà de la réduction et de l'obscurcissement?

Je ne prendrais pas la peine de faire une simple vérification côté serveur, mais je ne veux pas utiliser le chemin Diablo 3 en conservant tous les changements d'état de ma partie côté serveur.

Puisqu'il s'agira d'une sorte de RPG, j'ai eu l'idée de créer un inspecteur de statistiques chargé de contrôler les changements brusques de leurs valeurs, mais je ne suis pas certain de la cohérence et de la fiabilité de ce dernier.

Qu'en est-il des variables et des fonctions escopes? Travailler sur des escopes plus petites chaque fois que possible est plus sûr, mais cela en vaut-il la peine?

Existe-t-il un moyen pour le javascript de vérifier lui-même le texte, comme dans une somme de contrôle?

Il existe des solutions spécifiques au navigateur? Je ne prendrais pas la peine de le limiter pour Chrome uniquement dans les premières versions.

Billy Ninja
la source
Où sont vos données sauvegardées, comment sont-elles sauvegardées?
DogDog
C'est marrant que vous parliez de Diable 3, la "manière Diablo 1" était exactement cela, faire confiance au client. Faites une recherche google si vous êtes trop jeune pour vous rappeler ce qui s'est passé à cause de ça!
Valmond
Apoc, pour l’instant, j’ai juste une preuve de concept et je n’ai mis en œuvre aucune sorte de persistance - mais j’ai l’intention de mettre en œuvre une certaine persistance dans la base de données dans les premières versions et / ou le stockage local afin que les joueurs ne puissent pas continuer à jouer là où ils sont partis. Oui, Valdmond, j'ai joué ma part de Diablo à l'époque. Mais je ne construis pas un jeu multijoueur compétitif, ni un AAA complet. Byte56, je ne suis pas inquiet de voler mon code (qui voudrait quand même cette merde?)
Billy Ninja
Malheureusement, vous devez emprunter le chemin diablo 3, si vous êtes vraiment préoccupé par le piratage / les astuces
Noob Game Developer

Réponses:

46

La réponse courte est que vous ne pouvez pas le faire. Tout ce qui fonctionne côté client, en particulier à partir des sources, peut être modifié pour déjouer vos tactiques. Si vous mettez en place un vérificateur côté client pour rechercher des modifications soudaines, un utilisateur peut simplement désactiver le vérificateur.

La bonne nouvelle est qu’en règle générale, il n’ya que très peu de tricheurs sur les jeux en mode solo. La seule exception majeure concerne les jeux qui ont de grandes communautés de "scores élevés sur youtube" comme Line Rider, où les joueurs se font concurrence sur YouTube.

Si vous visez cela ou si vous êtes trop têtu pour accepter que des personnes trichent dans le jeu ou gardent vous-même des scores élevés (ce qui est une forme de jeu multijoueur), vous devez alors effectuer tous les calculs côté serveur. . Oui, tout ce qui compte. Vous ne pouvez même pas répéter le calcul côté client pour essayer de donner le score à l'utilisateur, puis le "vérifier" avec le serveur car l'utilisateur peut simplement désactiver le contrôle et désactiver tout système garantissant qu'il y a des contrôles.

J'aimerais qu'il y ait une meilleure réponse à cette question, mais il n'y en a pas.

Cela dit, vous pouvez faire quelque chose pour rendre un peu plus difficile de tricher. Ils n'empêcheront personne sérieux de le faire et de publier une boîte à outils pour tromper, mais cela les ralentira:

  • Réduisez et obscurcissez votre JS, ce qui rendra le code plus difficile à lire. Vous pouvez minimiser et trier de-obscurcir, mais vous ne pouvez jamais récupérer les bons noms de variable et de fonction, ni les commentaires.
  • Cuire dans les valeurs avec une langue différente. Dans ce cas, vous pouvez utiliser PHP ou d'autres langages côté serveur pour gérer les variables d'installation statiques. Si la distance de saut est toujours supposée être de 2 espaces, vous définissez normalement une distance de saut pour l'objet joueur. Ne gérez pas cela avec PHP pour que la source JS se retrouve avec 2s sur tout le code dans un million d'emplacements. Cela a l’effet secondaire heureux de pouvoir également accélérer votre JS.
  • Avec un peu de pratique, vous maîtriserez le mélange et vous pourrez même personnaliser votre JS pour chaque joueur. Ce qui est un autre moyen d'éviter la triche. Si le code de chaque joueur est différent d'une manière ou d'une autre, il est alors plus difficile d'écrire une triche qui peut faire partie d'une boîte à outils.
  • Enfin, vous pouvez contrôler la source en fonction de l'identité du joueur. Dites leur adresse IP et / ou nom d'utilisateur. Vous savez quelle sera la version spécifique du joueur du JS. Vous pouvez créer une somme de contrôle et demander qu’elle soit identique à l’autre. Facile à désactiver, comme tout JS côté client, mais rend encore une fois un peu plus difficile de créer une boîte à outils.

Alors. Comme vous le voyez, ce n'est probablement pas la peine de suivre cette voie. C'est difficile. Nécessite beaucoup de pratiques de codage vraiment stupides, et est finalement encore relativement facile à vaincre. Vous devrez faire tous les calculs côté serveur pour éviter les tricheries. Ou laissez-vous aller et acceptez que la tricherie arrive.

DampeS8N
la source
L’exemple de coureur de ligne est en fait assez simple à faire côté serveur, en permettant à l’utilisateur de télécharger la carte qu’il a dessinée et de calculer le score. Mais des jeux comme les arcades sont quasiment impossibles à calculer le score côté serveur sans un travail important.
Orlp
@nightcracker Vous avez raison, même avec quelque chose comme Line Rider, si vous ne vérifiez que lorsque le jeu est terminé, que la vidéo a été faite et que les YouTubes sont déjà dupes. Vous devez télécharger la carte lorsque l’utilisateur va jouer, calculer le chemin qui est trivial, puis le renvoyer. Le jeu ne devrait pas être capable de calculer le chemin. (Si nous parlons de faire preuve de triche, ce que ce jeu n'est pas. C'est juste assez simple pour que tricher soit évident pour ses fans.)
DampeS8N
14

J'ai déjà répondu à une question comme celle- , et je suis désolé de le dire, mais:

Je ne prendrais pas la peine de faire une simple vérification côté serveur, mais je ne veux pas utiliser le chemin Diablo 3 en conservant tous les changements d'état de ma partie côté serveur.

Est-ce la pire chose que vous puissiez dire ici? Si vous voulez faire un moteur "anti-triche", vous devrez le faire. Vous pouvez ajouter tout ce que vous voulez côté client pour faciliter le travail côté serveur, mais vous ne devez jamais faire confiance au client. Toute la logique que vous avez doit être au moins côté serveur. Vous pouvez le reproduire côté client si vous le souhaitez, mais aucune solution uniquement client ne le fera.

Et au fait, si vous voulez trouver la faiblesse de votre programme, ne le dissimulez pas, laissez les gens voir votre code et dites-leur "ici, vous avez un problème".

C'est bon pour vous, pour votre code, pour vos utilisateurs et pour la communauté.

tonnerre
la source
3
+1 pour l'autorité du serveur, cela ne fonctionne tout simplement pas si vous essayez de faire confiance au client ...
Valmond
Il est dangereux de reproduire des choses côté client. Soyez prudent avec même cela, car si tout est répliqué côté client, l'utilisateur peut tricher en déconnectant les vérifications avec le serveur. Ils peuvent ensuite jouer au jeu, enregistrer une vidéo et devenir une star de YouTube. Ceci ne s'applique qu'aux jeux solo, ce que ce jeu sera.
DampeS8N
Quand je parle du côté client, c'est pour le "calcul des mouvements", les "collisions", etc. Cela peut être fait des deux côtés, même pour un jeu multijoueur. Les calculs côté serveur doivent toujours être considérés comme prioritaires, mais cela peut être utile lorsque le temps de latence du serveur est également atteint par le côté client. Mais pour tout ce qui est "vérifier la triche" logique, alors je suis d'accord que tout devrait être côté serveur.
dievardump
Oui, j'ai ça. Mais je fais ce projet comme passe-temps dans le peu de temps libre que j'ai. Faire ce genre de vérification de serveur réduirait de beaucoup la complexité du projet, le rendant ainsi non viable. Bien, je continuerai d'avancer avec le projet en sachant cela, et s'il commence à devenir plus gros et plus sérieux que je ne pourrais en arriver à un contrôle sérieux du côté serveur, probablement avec Node.js.
Billy Ninja
C'est une réponse plus appropriée à OP
Noob Game Developer
3

Eh bien, un bon point de départ est d'utiliser la fonction Object.freeze (qui permettra une protection contre les correctifs d'objet).

Ceci "empêche l'ajout de nouvelles propriétés", "empêche les propriétés existantes d'être supprimées", "empêche les propriétés existantes, ou leur énumérabilité, leur configurabilité ou leur capacité d'écriture" d'être modifiées "; toute modification de l'état interne doit être effectuée via des accesseurs. L'exemple suivant fonctionne sur chrome (devrait fonctionner sur firefox, je ne connais pas IE si ...):

var b = {}
// Fill your object with whatever you want
b.a = "ewq"
// Freeze all changes
Object.freeze(b)
// Try to put new value. This wont throw any error, put wont work either, 
// as we shall see ...
b.b = "qwe"

// Values 
console.log(b.a); // outputs "eqw"
console.log(b.b); // outputs  undefined
fableal
la source
5
Même cela ne fera que ralentir un tricheur déterminé. S'il ne peut rien faire d'autre, il peut voler la source, l'héberger sur sa propre machine, supprimer le code gel, puis utiliser son fichier hosts pour amener son navigateur à penser que la nouvelle page est l'ancienne et la reconnecter au serveur.
DampeS8N
@ DampeS8N Oui, je suppose que vous avez raison.
fableal
Comme je l'ai dit dans le PO, je veux juste un certain niveau de protection.
Billy Ninja
Cela ne va pas aider du tout! L'utilisateur peut simplement définir un point d'arrêt pour le débogueur dans la première fonction JS qui est exécutée et entrer Object.freeze = function(o) {};dans la console JS.
Philipp
2

malheureusement, vous devez emprunter le chemin diablo 3 si vous êtes vraiment préoccupé par les hacks / cheats. si vous ne l'êtes pas, vous devez effectuer les vérifications de base ou il est fortement conseillé de le faire.

  • acheter des chèques - Si j'achète quelque chose, je devrais avoir assez d'or
  • sellchecks - Si je vends quelque chose, j'ai besoin de l'avoir dans mes vérifications de commerce d'inventaire - comme pour vendre une arme
  • équiper les contrôles - Si je suis en train d’équiper une arme, est-ce que je l’ai / possède?
  • Contrôle des dégâts - Si j'attaque quelque chose (ennemi), je ne peux pas toucher plus que le maximum de dégâts que mon arme puisse subir (dans ce cas, vous ne devez pas vous attendre à ce que le client dise quelle arme il a utilisée car elle aurait dû être persistée plus tôt)
  • Contrôles de fabrication - Si j'ai fabriqué quelque chose, dois-je tous les ingrédients / composants requis?

... etc

1 point est un peu délicat, c'est la position du héros, puisque vous n'êtes pas inquiet, vous pouvez le laisser, mais il vaut mieux le faire aussi avec une vérification minimale comme celle ci-dessous.

  • Je suis à la place1 @ T1, je suis à la place2 T2, quel est le temps minimal qu’il faut pour voyager de place1 à place2 et il correspond à mon T2 - T1. Vous pouvez avoir une cartographie de cela de petite à grande en fonction de la taille de la carte. Vous devriez avoir une liste au moins des zones principales telles que, PNJ - patron, PNJ - zone de ponte ennemie (pas nécessairement l'emplacement exact)

J'espère que cela aide, cela semble difficile, mais vous devez apprendre à faire de vrais jeux de travail

Noob Game Developer
la source
Très bonne réponse! J'écrivais une question sur la manière de mettre en œuvre la vérification de serveur, juste pour mesurer approximativement à quel point il est difficile de mettre en œuvre la vérification de serveur. Vous voyez, je ne veux pas perdre des dizaines d’heures à mettre en place un backbone de type MMO et à la fin de la journée, il est toujours facile de tricher simplement en remplaçant un paramètre de demande client ou quelque chose du genre. Ou simplement exagérer ce qui était supposé être un jeu tout simplement amusant: une perte de temps pour la sécurité au lieu de proposer des fonctionnalités plus intéressantes ou de peaufiner des objets.
Billy Ninja
1

C'est fondamentalement pas possible. Il serait si facile de contourner tout ce que vous avez mis en place pour éviter de tricher.

Le problème, c’est que tous les logiciels que vous distribuez peuvent être modifiés en mémoire facilement.

D'ailleurs s'ils veulent tricher, laissez-les. Ils sont en train de ruiner le jeu pour eux-mêmes. Il n'y a pas de réelle utilité pratique pour tricher dans cette situation, il vous suffirait de détruire le gameplay par vous-même.

tsturzl
la source
1

J'ai eu une idée d'une mesure que vous pourriez prendre pour prévenir / réduire la tricherie (en plus d'autres réponses). Vous pouvez le configurer de manière à ce que le client ne reçoive pas tout le code source en même temps, plutôt que chaque fois que le client souhaite, par exemple, acheter un nouvel article dans le magasin, le client doit envoyer certaines informations à le serveur et ne recevez toutes les informations pour ce qu’ils achètent que si toutes les informations correspondent à ce qui est censé l’être. Si ce n'est pas le cas, le serveur met en liste noire leur adresse IP ou autre chose.

Vous pouvez utiliser cela conjointement avec ce que Dampes8n a dit à propos de l’utilisation de différentes versions sources: si vous pouviez trouver un moyen de générer de nombreuses versions différentes, de sorte que chaque utilisateur utiliserait une version source entièrement différente à chaque fois. vérifiez également les listes noires de cette version source, afin de ne jamais divulguer les informations d’élément correctes pour cette version source.

La raison principale en est que si un pirate informatique ne réussit pas du premier coup, il sera beaucoup plus difficile de modifier le hack, car chaque fois que le hack ne fonctionne pas parfaitement, il doit changez leur adresse IP et réécrivez le hack pour la nouvelle version source.

AJMansfield
la source
Je ferais attention. La dernière chose que vous voulez faire est d’interdire accidentellement un client payant.
John McDonald
@JohnMcDonald C'est vrai, ça. Peut-être juste en train de tuer cette version source. De cette façon, s'ils déclenchent accidentellement le piège, il leur suffit d'actualiser le navigateur, tout en obligeant les pirates à recoder tous leurs hacks.
AJMansfield
0

Oui, cela ne peut être complètement fait. Toujours avoir la vérification sur le serveur. Tout ce qui a un impact sur le jeu doit nécessiter une autorisation du serveur.

C’est dans ce sens que je vais répéter d’autres réponses.

Cependant, nous pouvons faire beaucoup plus pour empêcher les tricheurs que de simplement vérifier sur le serveur. Nous devrons peut-être ajouter des vérifications spéciales du serveur. Sachez toutefois que les vérifications côté client ne sont pas sans valeur, elles permettent d’économiser la bande passante et le travail du serveur lorsque des tricheurs ne sont pas impliqués.

Ceci étant dit:

  • Atténuer les clients difficiles: Servir via HTTPS, utiliser le partage de ressources inter-origines (CORS), autoriser uniquement la même origine, utiliser l'intégrité de la sous-ressource. Je suggère de mettre en place un service worker pour l’appliquer à toutes les requêtes, ce qui signifiera également que le jeu ne fonctionnera pas simplement en le déplaçant vers HTTP (car sans HTTPS, il n’existe pas de service worker, le serveur worker fait la partie cliente de CORS et le serveur s’attend à ce que CORS), et s’ils servent via HTTPS, cela ne fonctionnera pas car le serveur rejettera l’autre origine.
  • Atténuer les scripts: utilisez l'authentification et nécessitez un jeton pour effectuer toute action. Chaque cycle de mise à jour, le serveur doit fournir au client un nouveau jeton, lequel est consommé en agissant de la sorte. Faire quoi que ce soit nécessite un jeton valide. Le jeton est en train de changer, il est donc impossible de le deviner, et si le client envoie le même jeton deux fois ou un mauvais jeton, le serveur sait que quelque chose se passe. Pour une protection supplémentaire: créez un code d'authentification de message (MAC) du jeton avec une clé secrète et ajoutez-le au cookie. La modification du cookie va tuer la session (et ils doivent deviner la clé) et la modification du jeton fera échouer la vérification MAC.
  • Atténuer les modifications de code: outre l'intégrité des sous-ressources (que les navigateurs modernes vérifieront également à l'exécution), gardez vos variables dans une portée limitée (à l'aide de let, de fonctions anonymes à exécution automatique et de modules javascript). De plus, ne vous fiez pas au DOM (le DOM s’applique uniquement aux E / S, pas au stockage, si vous devez attacher des attributs pour envelopper vos objets DOM et les ajouter aux wrappers). Ainsi, quoi que vous fassiez sur la console, vous ne devriez pas pouvoir accéder à la logique de jeu (à moins d'exploiter une vulnérabilité du navigateur). Vous pouvez également envisager d'utiliser des techniques pour détecter les outils de développement (ceux-ci sont spécifiques à chaque navigateur et peuvent ne pas fonctionner dans tous les cas ou cesser de fonctionner à l'avenir ... il s'agit donc d'une course aux armements).
  • Quelque chose se passe? La session s'est-elle arrêtée? Kick le joueur du match en cours, demande de se connecter à nouveau. Considérez un captcha ... qui présente également l'avantage de dire à l'utilisateur que "nous savons que quelque chose de rare se passe" (ce n'était pas une panne de serveur aléatoire), et oui, il s'agit d'une forme d'atténuation. Oh, et ne pas s'embourber pour les enregistrer. Vous devez être en mesure de vérifier pourquoi ils se sont produits, à la fois pour empêcher les faux postifs et pour répondre aux demandes d'assistance.

Oui, ce sont toutes des mesures d'atténuation. Nous pouvons toujours avoir un navigateur personnalisé qui ne vérifie pas l'intégrité et ne vous laisse pas accéder aux variables des portées locales ... jouer.

Theraot
la source