Parce que l'utilisation de variables globales vous pose un tas de problèmes, et pas vraiment d'avantages.
Les globaux rendent votre code difficile à tester
Bien qu'il ne soit pas directement lié à la sécurité, les tests unitaires sont vitaux pour le développement. Et pour tester correctement quelque chose, vous devez être en mesure de contrôler le contexte exact dans lequel le code est exécuté. Regardez les deux morceaux de code:
Avec Globals
public Money CalculateExpenses (int departmentId) {Department department = (from d in global_db .Departments où d.Id = departmentId sélectionnez d) .Single (); return (from ex in department.Expenses select ex) .Sum ();}
Sans Globals
Public Money CalculateExpenses (int departmentId, Database database) {Department department = (from d dans database.Departments where d.Id = departmentId select d) .Single (); return (from ex in department.Expenses select ex) .Sum ();}
Vous pourriez dire que le code semble presque identique, sauf d'où proviennent les données. Vous pourriez même penser que le code avec Globals est "plus propre", car vous n'avez pas à passer la base de données à chaque fois.
Jusqu'à ce que vous ayez à écrire un test unitaire. Parce que vous devrez alors insérer une logique pour ne pas vous connecter à la base de données de production, mais plutôt à une base de données locale, peut-être spécifique au test. Maintenant, le code non global est beaucoup mieux, car vous pouvez simplement passer la base de données que vous souhaitez utiliser au code.
En résumé: Le code sans Globals est plus facile à tester .
Globals change de comportement si vous ne changez pas le code
Si votre code contient environ 200 lignes de code, alors l'utilisation de Globals ne semble pas si mauvaise. En fait, cela peut sembler une chose parfaitement valable à faire si vous réutilisez le même morceau de code partout (par exemple, une source de données aléatoire, une journalisation, etc.)
Cependant, une fois que votre base de code se développe suffisamment, l'introduction de globals peut être absolument mortelle. Vous perdez tout simplement le contrôle sur la provenance de vos données et sur qui y a accès.
Prenons un exemple dans la langue préférée de tout le monde: PHP 5. Exemple par Eevee.
@fopen ('http://example.com/not-existing-file', 'r');
Que fait ce code? Vous ne le savez pas, car cela dépend du comportement global. Si PHP a été compilé avec --disable-url-fopen-wrapper
, alors cela ne fonctionnera pas. Idem pour la configuration globale allow_url_fopen
. Nous ne savons pas ce qu'il fera.
Le @
au début désactivera les messages d'erreur, sauf si scream.enabled
est défini dans le global Config PHP. Il ne sera pas non plus imprimé si le niveau global error_reporting
n'est pas défini. Où exactement il sera imprimé, s'il s'imprime, dépendra des display_errors
globaux.
Donc, comme vous l'avez vu, le comportement d'une ligne inoffensive dépend de 5 variables globales différentes . Imaginez maintenant ce scénario dans une base de code avec un million de lignes, et 100 programmeurs différents, tous répartis dans différentes équipes, et vous verrez rapidement pourquoi l'utilisation de Globals est odieuse et conduit à toutes sortes de problèmes.
Imaginez aller travailler un jour et votre code se brise soudainement, même si vous ne l'avez pas touché. C'est la magie de Globals.
Il y a d'autres exemples des raisons pour lesquelles l'utilisation de Globals est mauvaise, que vous pouvez trouver dans les autres réponses.