2017-02-17 9 views
1

Необходимо понимать некоторые рекомендации по управлению элементами внутри фреймов. Selenium WebDriver работает только в контексте фрейма/основного документа. Он не может найти элементы для других кадров до того, как I IWebDriver.SwitchTo() этоУправление кадрами в селене C# WebDriver

Боль в том, что мне постоянно приходится переключаться между кадрами. Ни в коем случае я не могу доверять, на каком кадре находится IWebDriver.

Могу ли я иметь несколько экземпляров IWebDriver (клон или что-то еще) в одном экземпляре браузера или только один экземпляр браузера? Я предполагаю, что у меня могло бы быть свойство IWebDriver Driver, переключено на конкретный кадр, где я могу доверять, я найду там элементы. Для другого класса я использовал бы свойство IWebDriver Driver для другого фрейма.

Кроме того, как обрабатывать кадры при построении объекта страницы с помощью PageFactory.InitElements? Я должен переключить IWebDriver для исправления кадра перед поиском элементов. Но будет ли мой объект Object Object всегда работать, независимо от того, каков я впоследствии переключаюсь? Я даю 2 страницы объектов из разных кадров - могу ли я легко использовать их в своих тестах, не думая о кадрах?

Не удалось найти рекомендации по управлению кадрами.

ответ

1

Было бы хорошо, если бы поддержка iframe в WebDriver была немного более надежной, но есть способы помочь ситуации. Отвечая на вопрос о том, будет ли WebDriver без проблем обрабатывать переключение iframe в ваших тестах - это не будет. Вам нужно будет управлять тем, что включается самостоятельно по мере необходимости, даже после того, как PageFactory будет запущен против объекта страницы.

Одним из вариантов, который стоит рассмотреть, является создание некоторых методов утилиты, которые обрабатывают включение и выход из фреймов.

Это означает, что вы можете позвонить в ваш метод переключения iframe до доступа к элементу и найти его в файле PageFactory. Эта логика может быть в объекте страницы, поэтому автору теста не нужно обрабатывать переключение iframe в тестах. Тезисы этого уровня сложности из тестов помогут им сосредоточиться на делах. Это также поможет в обслуживании, так как изменения продукта, связанные с этими iframe, могут быть просто изменены в объекте страницы, а затем все тесты, в которых используется объект страницы, не нужно будет изменять (относительно фреймов).

Пример:

public class MyPageObject 
    { 
     private readonly IWebDriver _driver; 

     [FindsBy(How = How.Id, Using = "id")] 
     private IWebElement _myWebElementInIFrame; 

     public MyPageObject(IWebDriver webDriver) 
     { 
      PageFactory.InitElements(webDriver, this); 
      _driver = webDriver; 
     } 

     public void DoStuff() 
     { 
      SwitchToIframe("myiframe"); 
      _myWebElementInIFrame.Click(); //element found using PageFactory data now 
      SwitchToDefaultContent(); 
     } 

     public void SwitchToIframe(string frameName) 
     { 
      _driver.SwitchTo().Frame(frameName); 
     } 

     public void SwitchToDefaultContent() 
     { 
      _driver.SwitchTo().DefaultContent(); 
     } 
    } 

Вы можете взять это немного дальше, используя некоторый метод шаблонов:

public class MyPageObject : BasePageObject 
    { 

     [FindsBy(How = How.Id, Using = "id")] 
     private IWebElement _myWebElementInIFrame; 

     public MyPageObject(IWebDriver webDriver) 
      : base(webDriver) 
     { 
      PageFactory.InitElements(webDriver, this); 
     } 

     public void DoStuff() 
     { 
      ExecuteActionInIFrame(() => 
      { 
       _myWebElementInIFrame.Click(); //element found using PageFactory data now 
      }, "myiframe", "mynestediframe"); 
     } 
    } 

    public abstract class BasePageObject 
    { 
     protected IWebDriver WebDriver { get; } 

     protected BasePageObject(IWebDriver webDriver) 
     { 
      WebDriver = webDriver; 
     } 

     public void ExecuteActionInIFrame(Action action, params string[] frameNames) 
     { 
      foreach (string frameName in frameNames) 
      { 
       WebDriver.SwitchTo().Frame(frameName); //switch into multiple nested iframes in passed in order 
      } 

      //perform action now that we're in proper iframe 
      action(); 

      //bounce out to root to have a standard starting point for next action 
      WebDriver.SwitchTo().DefaultContent(); 
     } 
    } 

Еще один совет, который помог мне был вы можете получить имя текущего фрейма с помощью некоторых JavaScript. Это может помочь вам определить, где именно вы находитесь в общей DOM при обходе iframe, если вам нужна такая информация.

Надеюсь, это поможет.

+0

Хорошо, спасибо за ответ. Я подозревал, что мне приходится моделировать свои классы, чтобы не зависеть от того, какой кадр я есть, но всегда делаю правильное переключение. –