2008-10-29 9 views
101

J'utilise XPather Browser pour vérifier mes expressions XPATH sur une page HTML.Utilisation de XPATH pour rechercher du texte contenant  

Mon objectif final est d'utiliser ces expressions dans Selenium pour le test de mes interfaces utilisateur.

j'ai reçu un fichier HTML avec un contenu similaire à ceci:

 
<tr> 
    <td>abc</td> 
    <td>&nbsp;</td> 
</tr> 

Je veux sélectionner un nœud avec un texte contenant la chaîne « &nbsp; ».

Avec une chaîne normale comme "abc" il n'y a pas de problème. J'utilise un XPATH similaire à //td[text()="abc"].

Lorsque j'essaie avec un XPATH comme //td[text()="&nbsp;"] il ne retourne rien. Y a-t-il une règle spéciale concernant les textes avec "&"?

+0

Ou seulement Xpather? –

Répondre

82

Il semble que OpenQA, les gars derrière Selenium, ont déjà résolu ce problème. Ils ont défini certaines variables pour correspondre explicitement aux espaces blancs. Dans mon cas, j'ai besoin d'utiliser un XPATH similaire à //td[text()="${nbsp}"].

Je reproduit ici le texte de OpenQA concernant cette question (qui se trouve here):

HTML normalise automatiquement des espaces dans les éléments, en ignorant espaces principaux/arrière et la conversion espaces supplémentaires, des onglets et des sauts de ligne dans un espace unique. Lorsque Sélénium lit le texte sur la page, il tente de reproduire ce comportement, vous pouvez donc ignorer tous les onglets et les sauts de ligne dans votre code HTML et faire des affirmations basées sur la façon dont le texte regarde dans le navigateur lorsque rendu. Nous le faisons en remplaçant tous les espaces non visibles (y compris l'espace insécable "&nbsp;") avec un espace unique . Toutes les nouvelles lignes visibles (<br>, <p> et <pre> formatées nouvelles lignes) doivent être conservées.

Nous utilisons la même logique de normalisation sur le texte des tables de test HTML Selenese . Cela a un certain nombre d'avantages . Tout d'abord, vous n'avez pas besoin de regarder la source HTML de la page à comprendre ce que vos affirmations devraient être; "&nbsp;" les symboles sont invisibles à l'utilisateur final, et donc vous ne devriez pas avoir à vous soucier d'eux lors de l'écriture tests Selenese. (Vous n'avez pas besoin de mettre marqueurs « &nbsp; » dans votre cas de test à assertText sur un champ qui contient « &nbsp; ».) Vous pouvez également mettre supplémentaires et des espaces dans les nouvelles lignes de votre Selenese <td> étiquettes; puisque nous utilisons la même logique de normalisation sur le cas de test que nous le faisons sur le texte, nous pouvons assurer que les assertions et le texte extrait correspondent exactement.

Cela crée un peu un problème sur ces rares occasions où vous avez vraiment voulez/besoin d'insérer des espaces supplémentaire dans votre cas de test. Par exemple, vous devrez peut-être taper du texte dans un champ comme ceci: "foo". Mais si vous simplement écrivez <td>foo </td> dans votre cas de test Selenese, nous remplacerons vos espaces supplémentaires avec un seul espace.

Ce problème a une solution de contournement simple. Nous avons défini une variable dans Selenese, ${space}, dont la valeur est un seul espace . Vous pouvez utiliser ${space} à insérer un espace qui ne sera pas automatiquement rogné, comme ceci: <td>foo${space}${space}${space}</td>. Nous avons également inclus une variable ${nbsp}, que vous pouvez utiliser pour insérer un espace insécable.

Notez que XPaths fait pas normaliser d'espace comme nous le faisons. Si vous avez besoin d'écrire un XPath comme //div[text()="hello world"] mais le HTML du lien est vraiment « hello&nbsp;world », vous devrez insérer un véritable « &nbsp; » dans votre cas de test Selenese pour l'obtenir au match, comme ceci: //div[text()="hello${nbsp}world"].

0

Rechercher &nbsp; ou seulement nbsp - Avez-vous essayé? Essayez d'utiliser l'entité décimale &#160; au lieu de l'entité nommée.

+0

Je reconnais que cela devrait fonctionner mais ce n'est pas exactement sûr de ce que je trouve. XPATH doit avoir un moyen d'encoder une certaine manière pour correspondre à ce que je cherche. – Bergeroy

+0

Peut-être que je devrais regarder vers une expression régulière. – Bergeroy

3

Si cela ne fonctionne pas, vous devriez simplement utiliser le unicode character for a non-breaking space au lieu de l'entité &nbsp;.

(Note:. Je n'ai pas essayé cela en XPather, mais j'ai essayé en oxygène)

16

Je trouve que je peux faire le match quand je l'entrée d'un disque codé espace insécable (U + 00A0) en tapant Alt + 0160 sur Windows entre les deux citations ...

//table[@id='TableID']//td[text()=' '] 

travaillé pour moi avec le caractère spécial. D'après ce que j'ai compris, la norme XPath 1.0 ne gère pas les caractères Unicode qui s'échappent. Il semble y avoir des fonctions pour cela dans XPath 2.0 mais il semble que Firefox ne le supporte pas (ou j'ai mal compris quelque chose). Donc, vous devez faire avec la page de codes locale. Laid, je sais. En fait, il semble que la norme utilise le langage de programmation XPath pour fournir la bonne séquence d'échappement Unicode ... Donc, d'une certaine façon, j'ai fait ce qu'il fallait.

+0

L'utilisation de Xpather 1.4.1 dans Firefox 2, // td [text() = ''] ne donne aucun résultat. –

+0

Désolé. Ça ne marche pas pour moi. Mon but final est de l'utiliser dans Selenium pour les tests de mes interfaces Web. Le sélénium conserve lui-même les expressions de test dans une structure XML et le typage Alt Windows semble être perdu dans le chemin. En outre, mon   renvoie en XML. – Bergeroy

+0

Zack, comme je l'ai écrit, vous devez remplacer l'espace entre les deux guillemets par le caractère produit par Alt + 0160 (sur le clavier numérique). – PhiLho

1

Je ne peux pas obtenir un match à l'aide Xpather, mais ce qui suit travaillé pour moi avec des fichiers XML simples et XSL dans le Bloc-notes XML de Microsoft:

<xsl:value-of select="count(//td[text()='&nbsp;'])" /> 

La valeur retournée est 1, ce qui est la valeur correcte dans mon test Cas.

Cependant, je ne dois déclarer nbsp comme une entité au sein de mon XML et XSL en utilisant les éléments suivants:

<!DOCTYPE xsl:stylesheet [ <!ENTITY nbsp "&#160;"> ]> 

Je ne suis pas sûr si cela vous aide, mais j'ai pu réellement trouver nbsp en utilisant une expression XPath.

Modifier: Mon exemple de code contient réellement les caractères '& nbsp;' mais la surbrillance de la syntaxe JavaScript la convertit en caractère espace. Ne sois pas trompé!

+0

Vous pouvez modifier votre exemple de code comme cela a été fait pour l'échantillon dans ma question. Remplacez votre entité nbsp par & nbsp ;. – Bergeroy

1

Gardez à l'esprit qu'un processeur XML conforme aux normes aura remplacé toutes les références d'entités autres que cinq les standards de XML (&amp;, &gt;, &lt;, &apos;, &quot;) avec le caractère correspondant dans le codage cible par le temps Les expressions XPath sont évaluées. Compte tenu de ce comportement, les suggestions de PhiLho et de jsulak sont la voie à suivre si vous voulez travailler avec des outils XML. Lorsque vous entrez &#160; dans l'expression XPath, il doit être converti en la séquence d'octets correspondante avant que l'expression XPath ne soit appliquée. Votre transformation XSL actuelle ne renvoie-t-elle rien?

+1

Pas si vous essayez/utilisez XPath dans XPather (GUI) ou en JavaScript (pas de substitution automatique d'entités, puisque nous ne sommes pas en XML). Bon conseil dans d'autres environnements XML (XSTL?). – PhiLho