Dans cette vidéo, j'aimerais vous montrer un petit peu
comment on peut utiliser l'inspecteur pour naviguer et
comprendre l'intérieur du système.
Alors l'inspecteur, c'est un objet comme un microscope
qui va nous permettre d'aller explorer l'intérieur du
système et aussi, comme si on pouvait envoyer des sondes
aller modifier le système. C'est comme si on était un
biologiste qui en fait va manipuler des bactéries et les faire réagir.
Donc on va s'amuser à explorer ce que c'est que "Smalltalk globals".
En fait, c'est le name space, c'est-à-dire l'endroit où
toutes les classes de Pharo sont stockées.
Donc c'est un dictionnaire, le système dictionnary c'est
un dictionnaire, ce qui est intéressant avec l'inspecteur
c'est que si je regarde l'inspecteur c'est un
grand tableau avec des
valeurs à l'intérieur.
Donc par exemple si je prends, je ne sais pas, moi,
Breakpoint, je vais voir que dans mon tableau j'ai
une clé qui contient au moins un objet qui contient
cet objet-là, qui contient une clé de valeur.
Alors ce qui est intéressant avec l'inspecteur c'est que
là, par exemple ce que je vois, je vois que à l'élément 2
du tableau, j'ai quoi ?
J'ai ce qu'on appelle une variable globale.
Donc une variable globale qu'est-ce qu'elle a?
C'est un objet qui est composé d'une clé et d'une valeur.
Donc la clé, là je vois si je clique dessus, la clé je
vois que c'est un ByteSymbol qui représente le nom, et si
je reviens en arrière et si je regarde la
valeur, là je vais avoir une classe.
Donc on va aller s'amuser à aller dans les classes après.
Donc là, je vais revenir au début.
Donc le nouvel inspecteur de Pharo, ce
qui s'appelle GT inspecteur, du nom de l'équipe de
développeurs qui l'a développé pour Pharo, va nous
proposer donc des onglets dédiés.
Donc sur le système dictionnary qu'est-ce que j'ai comme
onglets dédiés? J'ai cet onglet qui nous montre les
paires clés/valeurs pour mes classes,
ou alors je ne vais avoir que des clés.
Donc les clés c'est un peu moins intéressant puisque je
ne vais avoir que les noms des classes en
question.
Maintenant, ce qui est sympa aussi, c'est que cet
inspecteur, donc vous avez vu soit je peux naviguer, ça
veut dire prenons un exemple.
J'ai navigué, je vais d'un objet à un autre en
sélectionnant un chemin dans la structure en question.
Donc si je prends la clé par exemple, si je prends la
valeur, voilà, là j'obtiens une classe et si sur cette
classe, je vais aller dans son dictionnaire de méthodes.
Du dictionnaire de méthodes, je pourrais aller sur une
méthode compilée etc.
Donc je navigue vraiment et avec cet outil-là, je peux
restreindre la vue de ce que je veux voir ou par exemple voir tout mon flot.
Mais ce qui est sympa, c'est que je peux aussi injecter
un nouveau branchement dans mon flot.
Donc c'est ce qu'on va faire ici donc imaginons que je
réduise, je revienne au départ.
Là, finalement, imaginons que je me dise, tiens je suis
intéressé par la classe point.
La classe point je sais que normalement, je peux faire
"Smalltalk global" at #Point pour y arriver.
Donc là, ce que je vais faire, je le fais et ce que je
lui dis, je lui dis, exécute-le et ouvre-moi un
inspecteur dans l'inspecteur actuel.
Et là, tout d'un coup, j'ai, donc si on regarde la
navigation, ce que j'ai fait, j'ai fait un branchement
entre la navigation que j'avais et celle où je veux aller.
Donc ça c'est sympa, ça veut dire que vous pouvez taper
des tas d'expressions et commencer une navigation.
Donc là, qu'est-ce qu'on voit ?
On voit la classe Point comme un objet.
En fait, là, ce que l'inspecteur nous montre c'est qu'il
y a des onglets qui sont spécifiques pour les classes.
Donc là, l'onglet brut "Raw", nous
montre, bon ben la classe Point elle est définie dans la
catégorie Kernel, elle a un environnement, elle pointe
sur ce le même space, ça c'est le format d'encodage de
ces instances, elle a un layout.
Bref, c'est l'implémentation en Pharo de ce qu'est une classe.
Maintenant, ce qui est sympa avec cet inspecteur, c'est
que je peux voir donc, voilà par exemple la définition,
le commentaire et il y a d'autres onglets comme toutes les références.
Donc si je clique sur la référence, là je vais voir, ah
ben oui, Point est bien utilisé
dans la méthode @.
Et là je vais voir encore une fois, ça c'est la version
brute de l'information qui est un objet qui représente une
méthode et là son Source, et donc je vais pouvoir à
chaque fois choisir quelle est la meilleure
représentation pour la tâche que je suis en train de faire.
Donc revenons en arrière.
Donc si je regarde
ma classe, là j'aimerais aller dans le dictionnaire des méthodes.
Donc le dictionnaire des méthodes, en gros qu'est-ce que c'est?
C'est un dictionnaire avec une clé qui est le nom de la
méthode et une valeur qui est une méthode compilée, une
instance de CompileMethod. Donc si je regardais l'aspect
brut, vous voyez que c'est déjà un peu plus embêtant
parce qu'il faudrait que je comprenne comment sont
implémentés des dictionnaires de méthodes, pour pouvoir
interagir avec alors que là, ce n'est pas ça qui m'intéresse,
c'est d'aller voir une méthode compilée.
Donc pour voir une méthode compilée, ce que je vais
faire, je vais prendre par exemple degrees et là je
navigue et tout d'un coup j'obtiens une CompileMethod.
Une CompileMethod c'est un objet, qui encore une fois, va
proposer différentes façons d'être vue par l'inspecteur.
Et donc là ce qu'on voit, on voit une méthode compilée en
fait c'est une structure de données, c'est un tableau un
peu particulier, donc là il contient du Bytecode, et qui
contient des littéraux. Alors qu'est-ce que c'est que les literal?
Quand à chaque fois dans le code, quand vous avez
asFloat, arcTan, degrees or RadianToDegrees, il
faut bien que ça soit stocké quelque part.
Eh ben là c'est stocké, vous voyez, dans le début
de la méthode compilée.
Et qu'est-ce que va faire le Bytecode?
Il va pouvoir faire référence à ces objets-là pour
pouvoir les mettre sur la pile et invoquer les méthodes.
Donc là, c'est ce qu'on voit par exemple, si on regarde
la vue, je vais réduire ça, si on regarde la vue du
Bytecode qu'est-ce que ça fait ?
Ca va faire PushRcvr donc ça va mettre 0 sur la pile et faire égal.
Alors à quoi ça correspond ça?
Si on regarde un tout petit peu,
je vais mettre en double, alors cette vue-là elle est
vraiment très très pratique parce que vous allez voir ce
qu'on va faire avec, c'est que si je veux voir maintenant
le source, alors je vais me mettre en Bytecode ici et
ici en source, ces expressions-là correspondent, ah ben
tiens, vous avez vu, ça s'affiche.
Donc ça c'est super.
Donc là ça veut dire je veux faire un push de la variable
d'instance 0 du receveur, je vais te mettre 0 sur la pile
et je vais envoyer le message égal.
Et là tout d'un coup c'est génial parce que ça veut dire
que, pour la personne qui est en train de faire le
compilateur, elle peut voir que le Bytecode qu'elle a
émis, eh bien correspond bien à la structure du code.
De la même manière, ce qu'il peut voir
facilement, c'est, alors je vais retourner en arrière,
si je suis en haut et que je clique sur Self,
voilà, là, j'ai mes 2 méthodes compilées.
Donc là j'ai mes 2 méthodes compilées et en fait, ce que
j'aimerais bien voir, c'est finalement si j'ai
un arbre de syntaxe abstraite, une augmentation de
syntaxe abstraite et le source, je peux aussi naviguer dedans.
Donc là par exemple, dans mon arbre qui peut être
compliqué pour cette méthode, si j'ouvre tout, je vois
que si je sélectionne la variable
temporaire Time, je vais sélectionner le
morceau de texte auquel elle se réfère.
Donc ça, c'est vraiment super aussi, encore une fois, si
je regarde ça, ah tiens le message qui envoie égal à X
avec 0 en argument, ben c'est ce petit morceau d'arbre
qui correspond à ce morceau-là.
L'inspecteur va me permettre de gérer, dans la
représentation textuelle de l'arbre par exemple, les
sélections que j'ai des noeuds de l'arbre.
Donc ça fait un superbe outil pour aider par exemple les
gens qui font le compilateur de Pharo.
Et cette approche-là, on va pouvoir la retrouver pour
chacun des domaines, et donc même pour vos objets de
votre domaine vous allez pouvoir étendre l'inspecteur,
pour pouvoir proposer des facets et des vues qui font du sens.