3

GlobalVariables クラスは、フレームワーク全体で使用されるさまざまな変数を保持します。そのうちの 1 つは WebDriver インスタンスです。

  public class GlobalVariables
        {
        public static WebDriver driver;
    //Some other static global variables required across my framework
        public GlobalVariables(String propertiesFile)
        {
        initializeVariables(propertiesFile);
        }
        public void initializeVariables(String propertiesFile)
        {
        GlobalInitializer obj=new GlobalInitializer();
        obj.initialize(String propertiesFile);
        }
   }

GlobalInitializer には、すべての GlobalVariables を初期化するメソッドが含まれています。

public class GlobalInitializer extends GlobalVariables
{
public void initialize(String propertiesFile)
{
  //Some logic to read properties file and based on the properties set in it, call other initialization methods to set the global variables.
}
public void initializeDriverInstance(String Browser)
{
driver=new FireFoxDriver();
}

//他のグローバル変数を初期化する他のメソッド。}

ドライバ インスタンスを使用して UI コントロール要素を取得する多くの GetElement クラスがあります。

public class GetLabelElement extends GlobaleVariables
{
public static WebElement getLabel(String someID)
{
return driver.findElement(By.id(someId));
}
//Similar methods to get other types of label elements.
}

public class GetTextBoxElement extends GlobaleVariables
{
public static WebElement getTextBox(String someXpath)
{
return driver.findElement(By.xpath(someXpath));
}
//Similar methods to get other types of text box elements.
}

UI コントロールでいくつかのアクションを実行する他のクラスがあります (このクラスもグローバル変数を使用します)。

public class GetLabelProperties extends GlobalVariables
{
public static String getLabelText(WebElement element)
{
return element.getText();
}
}

public class PerformAction extends GlobalVariables
{
public static void setText(String textBoxName,String someText)
{
driver.findElement(someLocator(textBoxName)).setText("someText");
}
    //Some other methods which may or may not use the global variables to perform some action
}

testng の私のテスト クラスは次のようになります。

public class TestClass
{
GlobalVariables globalObj=new GlobalVariables(String propertiesFile);
@Test(priority=0)
{
GlobalVariables.driver.get(someURL);
//Some assertion.
}
@Test(priority=1)
{
WebElement element=GetLabelElement.getLabel(someID);
String labelName=GetLabelProperties.getLabelText(element);
//Some assertion.
}
@Test(priority=2)
{
WebElement element=GetTextBoxElement.getTextBox(someXpath);
PerformAction.setText(element.getText(),someText);
//Some assertion.
}
}

シナリオに基づいて、同様の複数のテスト クラスがあります。個別に実行している場合、このテストは正常に実行されます。しかし、それらを並行して実行しようとすると、このテストは奇妙な方法で失敗します。分析すると、静的グローバル変数が各テストによって初期化され、他のテストが失敗することがわかりました。フレームワーク設計の変更を最小限に抑えて、複数のテストを並行して実行するという目的を達成するにはどうすればよいでしょうか? 私はオプションを検索しようとしましたが、いくつかのオプション、つまり1)同期の使用に出くわしました。2)ThreadLocalインスタンスを作成します(注:この解決策を試しましたが、まだ同じ問題です。テストが互いに混ざり合って失敗しています。WebDriver インスタンスを ThreadLocal としてマークし、ThreadLocal の initialValue メソッドをオーバーライドしてドライバー インスタンスを初期化しました。それでも、正しく実装したかどうかはわかりません。) 今、特定のシナリオでこのソリューションのいずれかを実装する最善の方法がわかりません。どんな助けでも大歓迎です。ティア!

4

4 に答える 4

4

私は解決策を見つけました: ThreadLocal の使用は、巨大なマルチスレッド環境でテストを実行するための最良の解決策です。マルチスレッド環境で WebDriver を使用するためのコード スニペット:

public static ThreadLocal<WebDriver> driver;
driver=new ThreadLocal<WebDriver>()
                {
                    @Override
                    protected WebDriver initialValue()
                    {
                        return new FirefoxDriver(); //You can use other driver based on your requirement.
                    }
                };

これで、テスト スレッドが作成されるたびに、新しいブラウザーが開きます。ThreadLocal は、スレッドごとに静的 webdriver インスタンスのコピーが 1 つだけであることを確認します。[注: 他のグローバル変数が ThreadLocals すぎることを確認してください。私の場合、それらは私がテストの間抜け問題に遭遇した理由ではありませんでした]。他の人が参考になるように、共有したい追加の知識があります。ThreadLocal では、 ThreadLocal.get() メソッドが呼び出されるたびに、上記の initialValue() メソッドで示されているように、スレッド ローカルを初期化するための規定があることを確認する必要があります。そうしないと、null ポインター例外が発生する可能性があります。みんな、ありがとう。

于 2013-09-29T06:40:56.943 に答える
1

あなたはこのようなことを試すことができます

public class DriverManager {

private static final ThreadLocal<WebDriver> threadLocal = new ThreadLocal<WebDriver>();

public static WebDriver getDriver() {
    return threadLocal.get();
}

public static void setDriver(WebDriver driver) {
    threadLocal.set(driver);
}

public static void closeDriver() {
    if (getDriver() != null) {
        try {
            getDriver().close();
        } catch (Exception e) {
            e.printStackTrace();
        }
        try {
            getDriver().quit();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
    threadLocal.remove();
}

}

于 2016-10-03T03:37:16.543 に答える