Il s'agit d'un analyseur PHP préliminaire conçu dès le départ pour les scénarios d'utilisation de l'EDI (voir Objectifs de conception pour plus de détails). Il y a encore une tonne de travail à faire, donc à ce stade, ce dépôt sert principalement d'expérience et de début de conversation.
Il s'agit de la branche v0.1, qui modifie les structures de données pour prendre en charge la syntaxe ajoutée après la ligne de version 0.0.x initiale.
Après avoir configuré votre machine, vous pouvez utiliser l'analyseur pour générer et travailler avec l'arbre de syntaxe abstraite (AST) via une API conviviale.
<?php// Chargement automatique requis classesrequire __DIR__ . "/vendor/autoload.php";use MicrosoftPhpParser{DiagnosticsProvider, Node, Parser, PositionUtilities};// Instancier une nouvelle instance d'analyseur$parser = new Parser();// Renvoie et imprime un AST à partir du contenu de la chaîne$astNode = $parser ->parseSourceFile('<?php /* commentaire */ echo "salut!"');var_dump($astNode);// Récupère et imprime les erreurs du nœud AST. L'analyseur gère les erreurs avec élégance,// afin qu'il puisse être utilisé dans des scénarios d'utilisation de l'EDI (où le code est souvent incomplet).$errors = DiagnosticsProvider::getDiagnostics($astNode);var_dump($errors);// Parcourez tous les descendants de nœuds de $astNodeforeach ($astNode->getDescendantNodes() as $descendant) {if ($descendant instanceof NodeStringLiteral) {// Imprimer le texte du nœud (sans espaces ni commentaires)var_dump($descendant->getText());// Tous les nœuds renvoient à leurs parents, il est donc facile de naviguer dans l'arborescence.$grandParent = $descendant- >getParent()->getParent();var_dump($grandParent->getNodeKindName());// L'AST est entièrement représentatif et possibilité d'aller-retour vers la source d'origine.// Cela permet aux consommateurs de créer des outils de formatage et de refactorisation fiables.var_dump($grandParent->getLeadingCommentAndWhitespaceText()); }// En plus de récupérer tous les enfants ou descendants d'un nœud, // les nœuds exposent des propriétés spécifiques au type de nœud.if ($descendant instanceof NodeExpressionEchoExpression) {$echoKeywordStartPosition = $descendant->echoKeyword->getStartPosition();// Pour réduire la consommation de mémoire, les positions sont représentées sous la forme d'un seul index entier// dans le document, mais leurs positions de ligne et de caractère sont facilement récupéré.$lineCharacterPosition = PositionUtilities::getLineCharacterPositionFromPosition($echoKeywordStartPosition,$descendant->getFileContents() );echo "line : $lineCharacterPosition->line, caractère : $lineCharacterPosition->character"; } }
Remarque : l'API n'est pas encore finalisée, veuillez donc nous signaler les problèmes, indiquez-nous quelle fonctionnalité vous souhaitez exposer, et nous verrons ce que nous pouvons faire ! Veuillez également signaler tous les bogues présentant un comportement inattendu dans l'arborescence d'analyse. Nous n’en sommes qu’à nos débuts et tous vos commentaires sont très appréciés.
Conception tolérante aux erreurs : dans les scénarios IDE, le code est, par définition, incomplet. Dans le cas où un code invalide est saisi, l'analyseur doit toujours être capable de récupérer et de produire une arborescence valide + complète, ainsi que des diagnostics pertinents.
Rapide et léger (devrait être capable d'analyser plusieurs Mo de code source par seconde, pour laisser de la place à d'autres fonctionnalités).
Structures de données économes en mémoire
Autoriser une analyse incrémentielle à l'avenir
Adhère aux spécifications du langage PHP, prend en charge les grammaires PHP5 et PHP7
L'AST généré fournit des propriétés (entièrement représentatives, etc.) nécessaires aux opérations sémantiques et transformationnelles, qui doivent également être performantes.
Entièrement représentatif et pouvant être renvoyé au texte à partir duquel il a été analysé (tous les espaces et les commentaires "anecdotes" sont inclus dans l'arbre d'analyse)
Possibilité de parcourir facilement l'arborescence à travers les nœuds parent/enfant
Temps de réponse de l'interface utilisateur < 100 ms, donc chaque opération du serveur de langue doit être < 50 ms pour laisser de la place à toutes les autres tâches se déroulant en parallèle.
Simple et maintenable au fil du temps - les analyseurs ont tendance à devenir très confus et très rapides, la lisibilité et la capacité de débogage sont donc une priorité élevée.
Testable - l'analyseur doit produire des arbres d'analyse dont la validité est prouvée. Nous y parvenons en définissant et en testant continuellement un ensemble d’invariants concernant l’arbre.
API conviviale et descriptive pour permettre aux autres de s'appuyer facilement sur elle.
Écrit en PHP - permettez à la communauté PHP de consommer et de contribuer aussi facilement que possible.
Pour garantir un niveau d'exactitude suffisant à chaque étape du processus, l'analyseur est développé en utilisant l'approche incrémentale suivante :
Phase 1 : Écrivez un lexer qui ne prend pas en charge la grammaire PHP, mais prend en charge les jetons EOF et Unknown. Écrivez des tests pour tous les invariants.
Phase 2 : Prise en charge de la grammaire lexicale PHP, de nombreux tests
Phase 3 : écrivez un analyseur qui ne prend pas en charge la grammaire PHP, mais produit une arborescence de nœuds d'erreur. Écrivez des tests pour tous les invariants.
Phase 4 : Prise en charge de la grammaire syntaxique PHP, de nombreux tests
Phase 5 (en cours) : Validation et optimisation en situation réelle
Exactitude : valider qu'aucune erreur n'a été produite sur des exemples de bases de code, comparer avec d'autres analyseurs (enquêter sur tout cas de désaccord), effectuer des tests fuzz
Performance : profil, benchmark par rapport aux grosses applications PHP
Phase 6 : Finaliser l'API pour la rendre aussi simple que possible à consommer pour les utilisateurs.
Quelques constructions grammaticales PHP (à savoir l'expression de rendement et les chaînes de modèle) ne sont pas encore prises en charge et il existe également d'autres bugs divers. Cependant, comme l'analyseur est tolérant aux erreurs, ces erreurs sont traitées correctement et l'arborescence résultante est par ailleurs complète. Pour avoir une idée plus globale de notre situation, vous pouvez exécuter la suite de tests de « validation » (voir Directives de contribution pour plus d'informations sur l'exécution des tests). Ou simplement, jetez un œil aux résultats des tests de validation actuels.
Même si nous n'avons pas encore commencé la phase d'optimisation des performances, nous avons constaté jusqu'à présent des résultats prometteurs et il reste encore beaucoup à faire. Découvrez Comment cela fonctionne pour plus de détails sur notre approche actuelle et exécutez les tests de performances sur votre propre machine pour voir par vous-même.
Objectifs de conception : découvrez les objectifs de conception du projet (fonctionnalités, mesures de performances, etc.).
Documentation - découvrez comment référencer l'analyseur de votre projet et comment effectuer des opérations sur l'AST pour répondre aux questions sur votre code.
Outil de visualisation de syntaxe : obtenez une impression plus tangible de l'AST. Soyez créatif – voyez si vous pouvez le briser !
État actuel et approche : dans quelle mesure la grammaire est-elle prise en charge ? Performance? Mémoire? Stabilité de l'API ?
Comment cela fonctionne : découvrez l'architecture, les décisions de conception et les compromis.
Lexer et analyseur
Stratégie de tolérance aux erreurs
Analyse incrémentielle
Questions ouvertes
Stratégie de validation
Contribuer! - apprenez à vous impliquer, consultez quelques conseils sur les engagements éducatifs qui vous aideront à améliorer la base de code (même si vous n'avez jamais travaillé sur un analyseur auparavant) et les flux de travail recommandés qui facilitent l'itération.
Ce projet a adopté le code de conduite Microsoft Open Source. Pour plus d’informations, consultez la FAQ sur le code de conduite ou contactez [email protected] pour toute question ou commentaire supplémentaire.