#java #selenium #cucumber #testng #java.util.concurrent
#java #селен #огурец #testng #java.util.concurrent
Вопрос:
Когда я запускаю свои тестовые примеры с cucumber textNg на jenkins с maven, не всегда, но иногда это выдает ошибку java.util.concurrent.Ex.
, можете ли вы мне помочь? Некоторые из моих методов синхронизированы, так может быть? Мне нужно использовать synchronized, чтобы мои методы работали правильно.
Это мой тестовый xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "https://testng.org/testng-1.0.dtd">
<suite name="Suite" data-provider-thread-count="8"
thread-count="1" parallel="tests">
<listeners>
<listener
class-name="com.oneapi.ta.oneapihub.listeners.TestNGListener" />
</listeners>
<test name="Firefox">
<parameter name="browser" value="firefox"></parameter>
<classes>
<class
name="com.oneapi.ta.oneapihub.runners.OneApiHubTestAutomationRunnerTest" />
</classes>
</test>
<test name="Chrome">
<parameter name="browser" value="chrome"></parameter>
<classes>
<class
name="com.oneapi.ta.oneapihub.runners.OneApiHubTestAutomationRunnerTest" />
</classes>
</test>
<!-- <test name="Edge"> -->
<!-- <parameter name="browser" value="edge"></parameter> -->
<!-- <classes> -->
<!-- <class -->
<!-- name="com.oneapi.ta.oneapihub.runners.OneApiHubTestAutomationRunnerTest" /> -->
<!-- </classes> -->
<!-- </test> -->
<!-- <test name="Safari"> -->
<!-- <parameter name="browser" value="safari"></parameter> -->
<!-- <classes> -->
<!-- <class -->
<!-- name="com.oneapi.ta.oneapihub.runners.OneApiHubTestAutomationRunnerTest" /> -->
<!-- </classes> -->
<!-- </test> -->
</suite>
Это мой runnerClass
@BeforeClass(alwaysRun = true)
public void setUpClass() throws Exception {
testNGCucumberRunner = new TestNGCucumberRunner(this.getClass());
}
@Parameters({ "browser" })
@BeforeMethod
public static void launchBrowser(String browser) throws Throwable {
DriverManager.testNgBrowserParameter = browser;
}
@Test(dataProvider = "scenarios")
public void runScenario(PickleWrapper pickleWrapper, FeatureWrapper featureWrapper, ITestContext iTestContext)
throws Throwable {
String browser = iTestContext.getCurrentXmlTest().getLocalParameters().get("browser");
System.out.println("Running Test on Browser:" browser " Thread ID:" Thread.currentThread().getId());
if (ExtentReportManager.getFeature(featureWrapper.toString()) == null) {
ExtentReportManager.startFeature(featureWrapper.toString());
ExtentReportManager.startScenario(featureWrapper.toString(), pickleWrapper.getPickle().getName());
ExtentReportManager.getScenario().assignCategory(browser);
} else {
ExtentReportManager.startScenario(featureWrapper.toString(), pickleWrapper.getPickle().getName());
ExtentReportManager.getScenario().assignCategory(browser);
}
DriverManager.setScenarioName(pickleWrapper.getPickle().getName());
DriverManager.setFeatureName(featureWrapper.toString().replace(""", ""));
DriverManager.setTagName(pickleWrapper.getPickle().getTags().toString().replaceAll("([^a-zA-Z\s])", ""));
testNGCucumberRunner.runScenario(pickleWrapper.getPickle());
}
@DataProvider(parallel = true)
public Object[][] scenarios() {
return testNGCucumberRunner.provideScenarios();
}
@AfterMethod
public static void closeBrowser() {
DriverManager.stopDriver();
ExtentReportManager.flushExtentReport();
DriverManager.removeFinishedMap();
}
@AfterClass(alwaysRun = true)
public void tearDownClass() throws Exception {
testNGCucumberRunner.finish(); The error is this line.
//SendEmail.sendTestResaultWithEmail();
}
Это DriverManager
initializeDriver
это мой метод создания драйвера.
private static Map<Integer, WebDriver> webDriverMap = new HashMap<Integer, WebDriver>();
private static Map<Integer, String> browserMap = new HashMap<Integer, String>();
private static Map<Integer, String> scenarioNameMap = new HashMap<Integer, String>();
private static Map<Integer, String> featureNameMap = new HashMap<Integer, String>();
private static Map<Integer, String> tagNameMap = new HashMap<Integer, String>();
public static Map<String, String> scenarioSteps = new HashMap<String, String>();
public String getBrowser () {
return browserMap.get((int)Thread.currentThread().getId());
}
public static WebDriver getDriver() {
return (WebDriver) webDriverMap.get((int)Thread.currentThread().getId());
}
public static synchronized void startDriver(String browser, String scenarioName) throws Throwable {
webDriverMap.put((int)Thread.currentThread().getId(), initializeDriver(browser, scenarioName));
}
public static synchronized void setScenarioName(String scenarioName) throws Throwable {
scenarioNameMap.put((int)Thread.currentThread().getId(), scenarioName);
}
public static synchronized String getScenarioName() throws Throwable {
return scenarioNameMap.get((int)Thread.currentThread().getId());
}
public static synchronized void setFeatureName(String featureName) throws Throwable {
featureNameMap.put((int)Thread.currentThread().getId(), featureName);
}
public static synchronized String getFeatureName() throws Throwable {
return featureNameMap.get((int)Thread.currentThread().getId());
}
public static synchronized void setTagName(String tagName) throws Throwable {
tagNameMap.put((int)Thread.currentThread().getId(), tagName);
}
public static synchronized String getTagName() throws Throwable {
return tagNameMap.get((int)Thread.currentThread().getId());
}
public static synchronized void setScenarioSteps(String scenario, String steps) throws Throwable {
scenarioSteps.put(scenario, steps);
}
public static synchronized String getScenarioSteps(String scenario) throws Throwable {
return scenarioSteps.get(scenario);
}
public static synchronized void removeFinishedMap() {
webDriverMap.remove((int)Thread.currentThread().getId());
scenarioNameMap.remove((int)Thread.currentThread().getId());
browserMap.remove((int)Thread.currentThread().getId());
featureNameMap.remove((int)Thread.currentThread().getId());
tagNameMap.remove((int)Thread.currentThread().getId());
}
public static void stopDriver() {
getDriver().quit();
webDriverMap.remove((int)Thread.currentThread().getId());
}
Комментарии:
1. Возможно, стоит рассмотреть возможность использования вместо карт с идентификатором потока.
ThreadLocal
Ответ №1:
public String getBrowser () {
public static WebDriver getDriver() {
public static void stopDriver() {
Эти методы не синхронизированы. Это позволяет одновременно изменять карту webdriver и другие карты.
Вы должны синхронизировать эти методы. Или рассмотрите возможность использования a ThreadLocal
вместо map, поскольку вы пытаетесь переопределить ту же семантику.
Комментарии:
1. Привет, @M.P. Korstanje, как я могу тебя подключить к локальной сети? это так? «ThreadLocal<RemoteWebDriver> driver = new ThreadLocal<>();»