1

为了关闭我网页上的随机弹出窗口,我遵循了使用代理包装器包装网页元素的教程: https ://www.vinsguru.com/selenium-webdriver-how-to-handle-annoying-random-弹出警报/

在我的代码中实施此解决方案后,随机弹出窗口关闭,但我遇到了以前没有的“没有此类元素异常”。我试图通过使用不同的元素和方法来更改代码行,但我的行为没有解决这个问题 - 没有元素被识别。

我将不胜感激任何帮助:)

导致异常的方法(最后一行):

private void search(String gameName) {
    Wait.visible(homeBtn);
    Methods.click(searchBtn);
    Methods.sendKeys(searchBox, gameName);  
    Wait.visible(searchResultsTitle);    
}

代理页面工厂类:

public class ProxyPageFactory {

 public static <T> void initElements(WebDriver driver, T pageobject){
        
     //first init elements
     PageFactory.initElements(driver, pageobject);
        
     //then access all the WebElements and create a wrapper
     for(Field f: pageobject.getClass().getDeclaredFields()){
         if(f.getType().equals(WebElement.class)){
             boolean accessible = f.isAccessible();
             f.setAccessible(true);
         
             //reset the webelement with proxy object
             try {
                 f.set(pageobject, ElementGuard.guard((WebElement)f.get(pageobject))); 
             } catch (IllegalArgumentException e) {         
                 e.printStackTrace();
             } catch (IllegalAccessException e) {
                 e.printStackTrace();
             }          
         
        f.setAccessible(accessible);
     }  
  }
}

元素保护类:

public class ElementGuard {

public static WebElement guard(WebElement element) {
    ElementProxy proxy = new ElementProxy(element);
    WebElement wrappdElement = (WebElement) Proxy.newProxyInstance(ElementProxy.class.getClassLoader(),
                                                                   new Class[] { WebElement.class },
                                                                   proxy);
    return wrappdElement;
}

元素代理类:

public class ElementProxy implements InvocationHandler {

   private final WebElement element;

   public ElementProxy(WebElement element) {
       this.element = element;
   }

   @Override
   public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
      //before invoking actual method check for the popup
      this.checkForPopupAndKill();
      return  (method.invoke(element, args));
   }

   private void checkForPopupAndKill() {    
     // closing the pop up
   } }

错误:

org.openqa.selenium.support.ui.ExpectedConditions.elementIfVisible(ExpectedConditions.java:314) 上 com.sun.proxy.$Proxy27.isDisplayed(Unknown Source) 上的 java.lang.reflect.UndeclaredThrowableException。 support.ui.ExpectedConditions.access$000(ExpectedConditions.java:43) at org.openqa.selenium.support.ui.ExpectedConditions$10.apply(ExpectedConditions.java:300) at org.openqa.selenium.support.ui.ExpectedConditions$10 .apply(ExpectedConditions.java:297) at org.openqa.selenium.support.ui.FluentWait.lambda$checkConditionInLoop$2(FluentWait.java:233) at java.base/java.util.concurrent.CompletableFuture$AsyncSupply.run( CompletableFuture.java:1764) 在 java.base/java.util.concurrent.CompletableFuture$AsyncSupply.exec(CompletableFuture.java:1756) 在 java.base/java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:290)在 java.base/java。util.concurrent.ForkJoinPool$WorkQueue.topLevelExec(ForkJoinPool.java:1016) 在 java.base/java.util.concurrent.ForkJoinPool.scan(ForkJoinPool.java:1665) 在 java.base/java.util.concurrent.ForkJoinPool。 runWorker(ForkJoinPool.java:1598) at java.base/java.util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:183) at ✽。我执行一个动作来调用块(file:///C:/Users /may/Desktop/automation-git/GTH-QA/cucumber/features/Blocks.feature:9) 引起:java.lang.reflect.InvocationTargetException at jdk.internal.reflect.GeneratedMethodAccessor6.invoke(Unknown Source) at java。 base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.base/java.lang.reflect.Method.invoke(Method.java:564) at infrastructure.ElementProxy.invoke(ElementProxy.java: 27) 在 com.sun.proxy.$Proxy27。isDisplayed(Unknown Source) at org.openqa.selenium.support.ui.ExpectedConditions.elementIfVisible(ExpectedConditions.java:314) at org.openqa.selenium.support.ui.ExpectedConditions.access$000(ExpectedConditions.java:43) at org .openqa.selenium.support.ui.ExpectedConditions$10.apply(ExpectedConditions.java:300) at org.openqa.selenium.support.ui.ExpectedConditions$10.apply(ExpectedConditions.java:297) at org.openqa.selenium.support .ui.FluentWait.lambda$checkConditionInLoop$2(FluentWait.java:233) 在 java.base/java.util.concurrent.CompletableFuture$AsyncSupply.run(CompletableFuture.java:1764) 在 java.base/java.util.concurrent。 CompletableFuture$AsyncSupply.exec(CompletableFuture.java:1756) at java.base/java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:290) at java.base/java.util.concurrent.ForkJoinPool$WorkQueue.topLevelExec( ForkJoinPool.java:1016) 在 java.base/java.util.concurrent.ForkJoinPool.runWorker(ForkJoinPool.java:1598) 在 java.base/java.base/java.base/java.util.concurrent.ForkJoinPool.scan(ForkJoinPool.java:1665) .util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:183) 引起:org.openqa.selenium.NoSuchElementException:没有这样的元素:无法找到元素:{“method”:“xpath”,“selector”:“/ /div[contains(text(),'SEARCH RESULTS')]"}(会话信息:chrome=86.0.4240.111)有关此错误的文档,请访问:没有这样的元素:无法找到元素:{"method":"xpath","selector":"//div[contains(text(),'SEARCH RESULTS')]"} (会话信息:chrome=86.0.4240.111 ) 有关此错误的文档,请访问:没有这样的元素:无法找到元素:{"method":"xpath","selector":"//div[contains(text(),'SEARCH RESULTS')]"} (会话信息:chrome=86.0.4240.111 ) 有关此错误的文档,请访问:https://selenium.dev/exceptions/#no_such_element *** 元素信息:{Using=xpath, value=//div[contains(text(),'SEARCH RESULTS')]} at jdk.internal.reflect.GeneratedConstructorAccessor15.newInstance(Unknown Source) at java.base/jdk .internal.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45) 在 java.base/java.lang.reflect.Constructor.newInstanceWithCaller(Constructor.java:500) 在 java.base/java.lang.reflect.Constructor.newInstance (Constructor.java:481) 在 org.openqa.selenium.remote.codec.w3c.W3CHttpResponseCodec.createException(W3CHttpResponseCodec.java:196) 在 org.openqa.selenium.remote.codec.w3c.W3CHttpResponseCodec.decode(W3CHttpResponseCodec.java :129) 在 org.openqa.selenium.remote.HttpCommandExecutor.execute(HttpCommandExecutor.java:160) 在 org.openqa.selenium.remote.HttpCommandExecutor.execute(HttpCommandExecutor.java:160) 在 org.openqa.selenium.remote.codec.w3c.W3CHttpResponseCodec.decode(W3CHttpResponseCodec.java:53)。openqa.selenium.remote.service.DriverCommandExecutor.execute(DriverCommandExecutor.java:83) at org.openqa.selenium.remote.RemoteWebDriver.execute(RemoteWebDriver.java:582) at org.openqa.selenium.remote.RemoteWebDriver.findElement( RemoteWebDriver.java:333) 在 org.openqa.selenium.remote.RemoteWebDriver.findElementByXPath(RemoteWebDriver.java:451) 在 org.openqa.selenium.By$ByXPath.findElement(By.java:394) 在 org.openqa.selenium .remote.RemoteWebDriver.findElement(RemoteWebDriver.java:325) 在 org.openqa.selenium.support.pagefactory.DefaultElementLocator.findElement(DefaultElementLocator.java:70) 在 org.openqa.selenium.support.pagefactory.internal.LocatingElementHandler.invoke (LocatingElementHandler.java:39) 在 com.sun.proxy.$Proxy25.isDisplayed(Unknown Source) ... 17 更多java:83) 在 org.openqa.selenium.remote.RemoteWebDriver.findElement(RemoteWebDriver.java:333) 在 org.openqa.selenium.remote 的 org.openqa.selenium.remote.RemoteWebDriver.execute(RemoteWebDriver.java:582) .RemoteWebDriver.findElementByXPath(RemoteWebDriver.java:451) 在 org.openqa.selenium.By$ByXPath.findElement(By.java:394) 在 org.openqa.selenium.remote.RemoteWebDriver.findElement(RemoteWebDriver.java:325) 在org.openqa.selenium.support.pagefactory.internal.LocatingElementHandler.invoke(LocatingElementHandler.java:39) 在 com.sun.proxy 的 org.openqa.selenium.support.pagefactory.DefaultElementLocator.findElement(DefaultElementLocator.java:70)。 $Proxy25.isDisplayed(Unknown Source) ... 17 更多java:83) 在 org.openqa.selenium.remote.RemoteWebDriver.findElement(RemoteWebDriver.java:333) 在 org.openqa.selenium.remote 的 org.openqa.selenium.remote.RemoteWebDriver.execute(RemoteWebDriver.java:582) .RemoteWebDriver.findElementByXPath(RemoteWebDriver.java:451) 在 org.openqa.selenium.By$ByXPath.findElement(By.java:394) 在 org.openqa.selenium.remote.RemoteWebDriver.findElement(RemoteWebDriver.java:325) 在org.openqa.selenium.support.pagefactory.internal.LocatingElementHandler.invoke(LocatingElementHandler.java:39) 在 com.sun.proxy 的 org.openqa.selenium.support.pagefactory.DefaultElementLocator.findElement(DefaultElementLocator.java:70)。 $Proxy25.isDisplayed(Unknown Source) ... 17 更多java:333) 在 org.openqa.selenium.By$ByXPath.findElement(By.java:394) 在 org.openqa.selenium.remote 的 org.openqa.selenium.RemoteWebDriver.findElementByXPath(RemoteWebDriver.java:451) .RemoteWebDriver.findElement(RemoteWebDriver.java:325) 在 org.openqa.selenium.support.pagefactory.DefaultElementLocator.findElement(DefaultElementLocator.java:70) 在 org.openqa.selenium.support.pagefactory.internal.LocatingElementHandler.invoke(LocatingElementHandler .java:39) 在 com.sun.proxy.$Proxy25.isDisplayed(Unknown Source) ... 17 更多java:333) 在 org.openqa.selenium.By$ByXPath.findElement(By.java:394) 在 org.openqa.selenium.remote 的 org.openqa.selenium.RemoteWebDriver.findElementByXPath(RemoteWebDriver.java:451) .RemoteWebDriver.findElement(RemoteWebDriver.java:325) 在 org.openqa.selenium.support.pagefactory.DefaultElementLocator.findElement(DefaultElementLocator.java:70) 在 org.openqa.selenium.support.pagefactory.internal.LocatingElementHandler.invoke(LocatingElementHandler .java:39) 在 com.sun.proxy.$Proxy25.isDisplayed(Unknown Source) ... 17 更多findElement(DefaultElementLocator.java:70) at org.openqa.selenium.support.pagefactory.internal.LocatingElementHandler.invoke(LocatingElementHandler.java:39) at com.sun.proxy.$Proxy25.isDisplayed(Unknown Source) ... 17更多的findElement(DefaultElementLocator.java:70) at org.openqa.selenium.support.pagefactory.internal.LocatingElementHandler.invoke(LocatingElementHandler.java:39) at com.sun.proxy.$Proxy25.isDisplayed(Unknown Source) ... 17更多的

4

1 回答 1

0

感谢您提供相关代码。在处理弹出窗口后,尚不完全清楚什么是有效的,什么是失败的,但听起来一次定义所有页面模型元素可能存在问题。(这就是为什么只在需要时实例化元素是个好主意,因为如果页面是动态的,则引用可能会过时。)

有助于了解的一件事是,以前是否曾成功找到此元素?

Unable to locate element: {"method":"xpath","selector":"//div[contains(text(),'SEARCH RESULTS')]"}

如果是,则您的 xpath 很好,但 WebElement 参考已失去相关性。尝试在弹出窗口后从头开始重新创建该 WebElement ,看看是否能解决问题。每次处理弹出窗口时,您可能需要刷新页面模型数据。

于 2020-11-16T17:03:54.193 回答