Winiumを使用したWindowsアプリケーションのテスト自動化

何を食べますか



Winiumを使用すると、通常のWindowsアプリケーションを自動化できます。 原則として、Winiumは、標準のWindowsツールを使用して、ウィンドウ内にあるこれらの要素を操作できます(原則として、これらの要素にはタブ順序があります)。 これらのツールは標準キットで提供されます(たとえば、インストール後にダウンロードできます。たとえば、C:\ Program Files(x86)\ Windows Kits \ 8.1 \ bin \ x64)。 私は自分にとって最も便利な検査検証を検討していますが味方と色は、仲間の何人かが言うように、すべてのマーカーが異なっています。



ただし、自己作成アプリケーションを自動化するために、仲間の開発者が要素に適切なClassName、Name、およびAutomationIdがあることを確認しておくと便利です。 もちろん、特定の状況では、特定のキーのキーストロークを送信して座標をクリックすることで節約できますが、これは万能薬ではありません。 GUIが常に変化せず、さまざまな状況で適切に動作するという事実に依存するよりも、オブジェクト記述の形式で事前に準備された「レバー」のセットを常に用意する方が適切です。



Winiumを通常モードで使用すると、PythonおよびJavaを使用してSeleniumを介して通信できます。 いずれにせよ、星が立っていたため、選択はJavaに委ねられました。



設置



まず、Winium Desktop Driverが必要です。 たとえば、 ここからダウンロードできます。 このケースを解凍し、テスト中に実行する必要があります。 これにより、SeleniumサーバーはWindowsアプリケーションと通信します。



第二に、実際には、Java-IDE(IntelliJ IDEAコミュニティで使用されました。特別に感謝します)とJDK。 JAVA_HOME環境変数をJDKへのパスの値(私の場合はC:\ Program Files \ Java \ jdk1.8.0_131)でチェック/登録す​​ることを忘れないでください。



第三に、Seleniumサーバーも必要です。こちらからSelenium Standalone Server(JARファイル)をダウンロードしてください



次に、プロジェクトの設定時に-新しいJavaプロジェクトを作成し、外部ライブラリに追加します( プロジェクト構造ボタン(またはCtrl + Alt + Shift + S)をクリックし、 プロジェクト設定プロジェクト ライブラリを選択してプラス記号をクリックします)。 それだけです、あなたは書くことができます。



使用する



すべてが機能するためには、テストの使用中に管理者権限でWinium.Desktop.Driverを実行する必要があります。 ただし、ドライバーは何らかの理由で時々フリーズする可能性があるため、各テストの前に実行し、最後に終了するのが便利です。 たとえば、この目的でProcessBuilderを使用できます。



ProcessBuilder pro = new ProcessBuilder(windriverPath + windriverName, windriverParam); shell = pro.start(); //< > shell.destroy();
      
      





ここで、展開を簡単にするために、 windriverPathwindriverName-ドライバーへのパスと実行可能ファイルの名前を指定できます。 windriverParam-必要に応じて、追加の起動オプション。



最初に、コードでドライバー変数を実際のWiniumドライバーにアタッチする必要があります。



 DesiredCapabilities cap = new DesiredCapabilities(); cap.setCapability("app","<path to executable file>"); //    -  cap.setCapability("launchDelay","5"); //    WebDriver driver = new RemoteWebDriver(new URL("http://localhost:9999"),cap); //      Winium 
      
      





何らかのアプリケーションを実行したくないが、既に実行中のアプリケーションに単純に接続する場合、2行目と3行目は安全に省略できます。



要素を操作するには、まず要素にアタッチする必要があります。 By.name -Nameフィールド、 By.className -ClassNameおよびBy.xpathフィールドにより、より高度な検索条件の3つの接続メカニズムが知られています。 また、最初の/唯一の要素が必要な場合は、 findElementメソッドを使用できます。そのようなすべての要素のリストを取得するには、 findElementsメソッドを使用する必要があります。 2番目の場合、要素はタブオーダーの順序で追加されます。 使用例:



 WebElement wrk = driver.findElement(By.name("  Name")); // ,    Name List<WebElement> wrkL = driver.findElements(By.className("  ClassName")); //     ClassName
      
      





別の要素の要素にアタッチすることもできます。



 WebElement wrk1 = wrk.findElement(By.name("  Name"));
      
      





最初の2つの接続メカニズムが高度に専門化されている場合、つまり 階層構造で厳密に機能し、NameフィールドとClassNameフィールドで厳密に機能します。他のケースで機能するには、3番目のメカニズム、つまりBy.xpathが必要です



このメカニズムでは、すべてがxpathを使用する基準に厳密に従っています(いずれにせよ、すべてが使用されたケースから正常に機能しました)。 xpathを使用すると、IsOffscreen、AutomationId、HasKeyboardFocusの各フィールドを取得して処理できます。



 WebElement field = wrk.findElement(By.xpath("*[@HasKeyboardFocus='True']")); //   wrk,    
      
      





xpathを使用する場合、特により複雑な条件で作業している場合は、xpathに渡された文字列全体を追跡してエラーの可能性を追跡すると便利です。



 String xpathStr = "*[(@AutomationId='" + autId + "') and (@IsOffscreen='False')]"; //       -  AutomationId = autId     IsOffscreen = False log("Performing xpath search: " + xpathStr); WebElement tWrk = wrk1.findElement(By.xpath(xpathStr));
      
      





もちろん、現在のウィンドウの要素だけでなく、xpathを使用して検索することもできますが、そのような検索は非常に長時間続く可能性があります。



他の検索方法もありますが、いずれにしても、すべて上記の方法になります。 たとえば、 そのような



また、キーボードからのキーボード入力をシミュレートする必要がある場合があります。 通常の方法では、これは要素でsendKeys(「文字のシーケンス」)メソッドを使用して行われます。 ただし、一部の文字はサービス文字として使用され、エスケープする必要があることに注意してください(たとえば、「+」はShiftです。「+」を入力するには、シーケンス「+ =」を渡す必要があります)。 コードを使用するために、すべての "+"を自動的に "+ ="に置き換えるラッパーを作成できますが、ここでは誰にとっても便利です。 キーボードショートカットの転送標準については、 こちらをご覧ください 。 それにもかかわらず、キーボード上のキーストロークの正しい転送に問題があったため、残念ながら現在のバージョンのドライバーでは、回避策を探す必要があります。



これらの回避策の1つは、特定の要素に関する座標をクリックすることです。 これは最も簡単なタスクではありませんが、ここではアクションを使用できます。



 Actions builder = new Actions(driver); Action enter = builder .moveToElement(wrk) .moveByOffset(x,y) .click() .build(); enter.perform();
      
      





ここで、 wrkはWebElementの名前であり、その中心からマウスを移動します。 xy-移動する距離( xの正の値はカーソルを右に移動し、正のy-下に移動します)。



プロジェクトの全体的な構造について少しだけ



既に少し述べたように、外界との相互作用の主な要素は「レバレッジ」です。 これらは、フィールドnameclassName 、およびautomationIdを持つクラスによって簡単に記述でき、ブロック内の個別のクラスに保存できます。



多くの場合、自動テストは相互に任意のステップを繰り返すため、これらのプロシージャは個別の静的メソッドとしてフォーマットされ、ブロック内の個別のクラスにも保存されます。



他のすべては、通常通り安全に行うことができます-テスト付きのクラス、テストを実行するためのクラスなど。



おわりに



一般に、Winiumの世界に没頭することは非常に興味深く、それほど難しくはありません。 この記事を最後まで読んでくれたすべての読者に感謝します。 この投稿がWiniumの開発に役立つことを本当に願っています。 パートナーのユージニアに感謝します。彼と一緒に彼の荒野に飛び込みました。 すべての人に良い!



All Articles