Wir haben Selen mit großem Erfolg verwendet, um Website-Tests auf hoher Ebene durchzuführen (zusätzlich zu umfangreichen Python-Doctests auf Modulebene). Jetzt verwenden wir jedoch extjs für viele Seiten, und es erweist sich als schwierig, Selentests für komplexe Komponenten wie Gitter zu integrieren.
Hat jemand erfolgreich automatisierte Tests für extjs-basierte Webseiten geschrieben? Viele googeln finden Menschen mit ähnlichen Problemen, aber nur wenige Antworten. Vielen Dank!
unit-testing
extjs
selenium
web-testing
mm2001
quelle
quelle
Antworten:
Die größte Hürde beim Testen von ExtJS mit Selenium besteht darin, dass ExtJS keine Standard-HTML-Elemente rendert und die Selenium-IDE naiv (und zu Recht) Befehle generiert, die auf Elemente abzielen, die nur als Dekor dienen - überflüssige Elemente, die ExtJS auf dem gesamten Desktop unterstützen. Look-and-Feel. Hier sind einige Tipps und Tricks, die ich beim Schreiben eines automatisierten Selenium-Tests gegen eine ExtJS-App gesammelt habe.
Allgemeine Hinweise
Elemente lokalisieren
Beim Generieren von Selenium-Testfällen durch Aufzeichnen von Benutzeraktionen mit Selenium IDE unter Firefox basiert Selenium die aufgezeichneten Aktionen auf den IDs der HTML-Elemente. Für die meisten anklickbaren Elemente verwendet ExtJS jedoch generierte IDs wie "ext-gen-345", die sich bei einem späteren Besuch derselben Seite wahrscheinlich ändern, selbst wenn keine Codeänderungen vorgenommen wurden. Nach dem Aufzeichnen von Benutzeraktionen für einen Test muss manuell gearbeitet werden, um alle Aktionen, die von den generierten IDs abhängen, durchzuführen und zu ersetzen. Es gibt zwei Arten von Ersetzungen, die vorgenommen werden können:
Ersetzen eines ID-Locators durch einen CSS- oder XPath-Locator
CSS-Locators beginnen mit "css =" und XPath-Locators beginnen mit "//" (das Präfix "xpath =" ist optional). CSS-Locators sind weniger ausführlich und leichter zu lesen und sollten XPath-Locators vorgezogen werden. Es kann jedoch Fälle geben, in denen XPath-Locators verwendet werden müssen, da ein CSS-Locator sie einfach nicht schneiden kann.
JavaScript ausführen
Einige Elemente erfordern aufgrund des komplexen Renderings von ExtJS mehr als nur einfache Maus- / Tastaturinteraktionen. Beispielsweise ist eine Ext.form.CombBox nicht wirklich ein
<select>
Element, sondern eine Texteingabe mit einer getrennten Dropdown-Liste, die sich irgendwo am Ende des Dokumentbaums befindet. Um eine ComboBox-Auswahl richtig zu simulieren, können Sie zuerst einen Klick auf den Dropdown-Pfeil simulieren und dann auf die angezeigte Liste klicken. Das Auffinden dieser Elemente über CSS- oder XPath-Locators kann jedoch umständlich sein. Eine Alternative besteht darin, die ComoBox-Komponente selbst zu suchen und Methoden aufzurufen, um die Auswahl zu simulieren:In Selenium kann der
runScript
Befehl verwendet werden, um die obige Operation in einer präziseren Form auszuführen:Umgang mit AJAX und Slow Rendering
Selen verfügt über die Varianten "* AndWait" für alle Befehle zum Warten auf das Laden von Seiten, wenn eine Benutzeraktion zu Seitenübergängen oder Neuladungen führt. Da AJAX-Abrufe jedoch keine tatsächlichen Seitenladevorgänge beinhalten, können diese Befehle nicht für die Synchronisierung verwendet werden. Die Lösung besteht darin, visuelle Hinweise wie das Vorhandensein / Fehlen einer AJAX-Fortschrittsanzeige oder das Auftreten von Zeilen in einem Raster, zusätzliche Komponenten, Links usw. zu verwenden. Zum Beispiel:
Manchmal wird ein Element erst nach einer bestimmten Zeit angezeigt, je nachdem, wie schnell ExtJS Komponenten rendert, nachdem eine Benutzeraktion zu einer Ansichtsänderung geführt hat. Anstatt willkürliche Verzögerungen mit dem
pause
Befehl zu verwenden, besteht die ideale Methode darin, zu warten, bis das interessierende Element in unsere Reichweite gelangt. So klicken Sie beispielsweise auf ein Element, nachdem Sie darauf gewartet haben, dass es angezeigt wird:Sich auf beliebige Pausen zu verlassen, ist keine gute Idee, da Zeitunterschiede, die sich aus der Ausführung der Tests in verschiedenen Browsern oder auf verschiedenen Computern ergeben, die Testfälle schuppig machen.
Nicht anklickbare Elemente
Einige Elemente können vom
click
Befehl nicht ausgelöst werden . Dies liegt daran, dass sich der Ereignis-Listener tatsächlich im Container befindet und nach Mausereignissen für seine untergeordneten Elemente sucht, die schließlich zum übergeordneten Element aufsteigen. Das Registersteuerelement ist ein Beispiel. Um auf die Registerkarte a zu klicken, müssen Sie einmouseDown
Ereignis auf der Registerkarte beschriften:Feldvalidierung
Formularfelder (Ext.form. * -Komponenten), denen reguläre Ausdrücke oder v-Typen zur Validierung zugeordnet sind, lösen die Validierung mit einer bestimmten Verzögerung aus (siehe die
validationDelay
Eigenschaft, die standardmäßig auf 250 ms festgelegt ist), nachdem der Benutzer Text eingegeben hat oder sofort, wenn das Feld verliert Fokus - oder Unschärfen (siehevalidateOnDelay
Eigenschaft). Um die Feldvalidierung nach der Ausgabe des Befehls Typ Selenium auszulösen, um Text in ein Feld einzugeben, müssen Sie einen der folgenden Schritte ausführen:Auslösen einer verzögerten Validierung
ExtJS löst den Validierungsverzögerungszeitgeber aus, wenn das Feld Keyup-Ereignisse empfängt. Um diesen Timer auszulösen, geben Sie einfach ein Dummy-Keyup-Ereignis aus (es spielt keine Rolle, welchen Schlüssel Sie verwenden, da ExtJS ihn ignoriert), gefolgt von einer kurzen Pause, die länger als die Validierungsverzögerung ist:
Sofortige Validierung auslösen
Sie können ein Unschärfeereignis in das Feld einfügen, um eine sofortige Validierung auszulösen:
Überprüfung auf Validierungsergebnisse
Nach der Validierung können Sie überprüfen, ob ein Fehlerfeld vorhanden ist oder nicht:
Beachten Sie, dass die Prüfung "Anzeige: Keine" erforderlich ist, da ExtJS das Fehlerfeld einfach ausblendet, sobald es angezeigt wird und dann ausgeblendet werden muss, anstatt es vollständig aus dem DOM-Baum zu entfernen.
Elementspezifische Tipps
Klicken Sie auf eine Ext.form.Button
Option 1
Befehl: Klicken Sie auf Ziel: css = Schaltfläche: enthält ('Speichern')
Wählt die Schaltfläche anhand ihrer Beschriftung aus
Option 2
Befehl: Klicken Sie auf die Schaltfläche Ziel: css = # Speicheroptionen
Wählt die Schaltfläche anhand ihrer ID aus
Auswählen eines Werts aus einer Ext.form.ComboBox
Legt zuerst den Wert fest und löst dann das Auswahlereignis explizit aus, falls Beobachter vorhanden sind.
quelle
Dieser Blog hat mir sehr geholfen. Er hat ziemlich viel zu diesem Thema geschrieben und es scheint immer noch aktiv zu sein. Der Typ scheint auch gutes Design zu schätzen.
Er spricht im Wesentlichen davon, Javascript für Abfragen zu senden und die Ext.ComponentQuery.query-Methode zu verwenden, um Inhalte auf dieselbe Weise abzurufen, wie Sie es in Ihrer ext-App intern tun. Auf diese Weise können Sie xtypes und itemIds verwenden und müssen sich keine Sorgen mehr machen, wenn Sie versuchen, die verrückten automatisch generierten Inhalte zu analysieren.
Ich fand diesen Artikel besonders hilfreich.
Könnte bald etwas detaillierteres hier posten - ich versuche immer noch, mir klar zu machen, wie man das richtig macht
quelle
Ich habe meine ExtJs-Webanwendung mit Selen getestet. Eines der größten Probleme war die Auswahl eines Elements im Raster, um etwas damit zu tun.
Zu diesem Zweck habe ich eine Hilfsmethode geschrieben (in der SeleniumExtJsUtils-Klasse, die eine Sammlung nützlicher Methoden zur einfacheren Interaktion mit ExtJs darstellt):
und wenn ich eine Zeile auswählen musste, rief ich einfach an:
Damit dies funktioniert, muss ich meine ID im Raster festlegen und darf ExtJs nicht ihre eigene generieren lassen.
quelle
Um festzustellen, dass dieses Element sichtbar ist, verwenden Sie die folgende Klausel:
not(contains(@style, "display: none")
Es ist besser, dies zu verwenden:
quelle
Können Sie mehr Einblick in die Arten von Problemen geben, die Sie beim Testen von extjs haben?
Eine Selenium-Erweiterung, die ich nützlich finde, ist waitForCondition . Wenn Ihr Problem Probleme mit den Ajax-Ereignissen zu sein scheint, können Sie waitForCondition verwenden, um auf Ereignisse zu warten.
quelle
Ext JS-Webseiten können aufgrund des komplizierten HTML-Codes, den sie wie bei Ext JS-Rastern generieren, schwierig zu testen sein.
HTML5 Robot behandelt dies, indem es eine Reihe von Best Practices verwendet, um Komponenten basierend auf Attributen und Bedingungen, die nicht dynamisch sind, zuverlässig zu suchen und mit ihnen zu interagieren. Anschließend werden Verknüpfungen mit allen HTML-, Ext JS- und Sencha Touch-Komponenten bereitgestellt, mit denen Sie interagieren müssten. Es gibt zwei Geschmacksrichtungen:
Wenn Sie beispielsweise die Ext JS-Rasterzeile mit dem Text "Foo" suchen möchten, können Sie in Java Folgendes tun:
... und Sie könnten in Gwen Folgendes tun:
Sowohl für Java als auch für Gwen gibt es zahlreiche Dokumentationen zur Arbeit mit Ext JS-spezifischen Komponenten. In der Dokumentation wird auch der resultierende HTML-Code für alle diese Ext JS-Komponenten beschrieben, den Sie möglicherweise auch nützlich finden.
quelle
Nützliche Tipps zum Abrufen des Rasters über die ID des Rasters auf der Seite: Ich denke, Sie können die nützlichere Funktion dieser API erweitern.
quelle
Einfacheres Testen durch benutzerdefinierte HTML-Datenattribute
Aus der Sencha-Dokumentation :
Beim Überschreiben der Methode
Ext.AbstractComponent
'sonBoxReady
setze ich ein benutzerdefiniertes Datenattribut (dessen Name von meiner benutzerdefiniertentestIdAttr
Eigenschaft jeder Komponente stammt) auf denitemId
Wert der Komponente , falls vorhanden. Fügen Sie dieTesting.overrides.AbstractComponent
Klasseapplication.js
demrequires
Array Ihrer Datei hinzu .Diese Methode bietet Entwicklern die Möglichkeit, einen beschreibenden Bezeichner in ihrem Code wiederzuverwenden und diese Bezeichner bei jedem Rendern der Seite verfügbar zu machen. Kein Durchsuchen von nicht beschreibenden, dynamisch generierten IDs mehr.
quelle
Wir entwickeln ein Testframework, das Selen verwendet und auf Probleme mit extjs stößt (da es clientseitig gerendert wird). Ich finde es nützlich, nach einem Element zu suchen, sobald das DOM fertig ist.
quelle
Für komplexe Benutzeroberflächen, die kein formales HTML sind, können Sie sich immer auf xPath verlassen, aber ein wenig komplex, wenn es um die Implementierung verschiedener Benutzeroberflächen mit ExtJs geht.
Sie können Firebug und Firexpath als Firefox-Erweiterungen verwenden, um den xpath eines bestimmten Elements zu testen, und einfach den vollständigen xpath als Parameter an Selen übergeben.
Zum Beispiel in Java-Code:
quelle
Als ich die ExtJS-Anwendung mit WebDriver getestet habe, habe ich den nächsten Ansatz verwendet: Ich habe nach Feld anhand des Textes des Labels gesucht und das
@for
Attribut vom Label erhalten. Zum Beispiel haben wir ein EtikettUnd wir müssen WebDriver einige Eingaben zeigen :
//input[@id=(//label[contains(text(),'Name Of Needed Label')]/@for)]
.Es wird also die ID aus dem
@for
Attribut auswählen und weiter verwenden. Dies ist wahrscheinlich der einfachste Fall, bietet Ihnen jedoch die Möglichkeit, Elemente zu lokalisieren. Es ist viel schwieriger, wenn Sie keine Beschriftung haben, aber dann müssen Sie ein Element finden und Ihren xpath schreiben, um nach Geschwistern zu suchen, Elemente abzusteigen / aufzusteigen.quelle