Skip to content

Commit 385197d

Browse files
authored
Add integration test with OpenDJ Docker container (#863)
1 parent c0ed63f commit 385197d

File tree

4 files changed

+350
-71
lines changed

4 files changed

+350
-71
lines changed

openam-server/pom.xml

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
* information: "Portions copyright [year] [name of copyright owner]".
1414
*
1515
* Copyright 2011-2016 ForgeRock AS.
16+
* Portions copyright 2017-2025 3A Systems LLC.
1617
-->
1718
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
1819
<modelVersion>4.0.0</modelVersion>
@@ -23,6 +24,9 @@
2324
<artifactId>openam</artifactId>
2425
<version>15.1.6-SNAPSHOT</version>
2526
</parent>
27+
<properties>
28+
<test.config.path>${basedir}/target/config</test.config.path>
29+
</properties>
2630

2731
<!-- Component Definition -->
2832
<name>OpenAM Server</name>
@@ -95,8 +99,8 @@
9599
<systemProperties>
96100
<file.encoding>UTF-8</file.encoding>
97101
<com.sun.xml.ws.transport.http.HttpAdapter.dump>true</com.sun.xml.ws.transport.http.HttpAdapter.dump>
98-
<com.iplanet.services.configpath>${basedir}/target/config</com.iplanet.services.configpath>
99-
<com.sun.identity.configuration.directory>${basedir}/target/config</com.sun.identity.configuration.directory>
102+
<com.iplanet.services.configpath>${test.config.path}</com.iplanet.services.configpath>
103+
<com.sun.identity.configuration.directory>${test.config.path}</com.sun.identity.configuration.directory>
100104
<logback.configurationFile>${basedir}/src/test/resources/logback-test.xml</logback.configurationFile>
101105
<ssoadm.disabled>false</ssoadm.disabled>
102106
<com.iplanet.services.debug.level>message</com.iplanet.services.debug.level>
@@ -114,6 +118,13 @@
114118
</properties>
115119
<pingURL>http://localhost:8207/openam</pingURL>
116120
</deployable>
121+
<deployable>
122+
<type>war</type>
123+
<properties>
124+
<context>am</context>
125+
</properties>
126+
<pingURL>http://localhost:8207/am</pingURL>
127+
</deployable>
117128
</deployables>
118129
<configuration>
119130
<properties>
@@ -157,6 +168,12 @@
157168
<version>4.13.0</version>
158169
<scope>test</scope>
159170
</dependency>
171+
<dependency>
172+
<groupId>org.testcontainers</groupId>
173+
<artifactId>testcontainers</artifactId>
174+
<version>1.20.6</version>
175+
<scope>test</scope>
176+
</dependency>
160177
</dependencies>
161178

162179
<profiles>
@@ -179,6 +196,9 @@
179196
<artifactId>maven-failsafe-plugin</artifactId>
180197
<configuration>
181198
<skip>false</skip>
199+
<systemProperties>
200+
<test.config.path>${test.config.path}</test.config.path>
201+
</systemProperties>
182202
</configuration>
183203
<executions>
184204
<execution>
Lines changed: 127 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,127 @@
1+
/*
2+
* The contents of this file are subject to the terms of the Common Development and
3+
* Distribution License (the License). You may not use this file except in compliance with the
4+
* License.
5+
*
6+
* You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
7+
* specific language governing permission and limitations under the License.
8+
*
9+
* When distributing Covered Software, include this CDDL Header Notice in each file and include
10+
* the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
11+
* Header, with the fields enclosed by brackets [] replaced by your own identifying
12+
* information: "Portions copyright [year] [name of copyright owner]".
13+
*
14+
* Copyright 2025 3A Systems LLC.
15+
*/
16+
17+
package org.openidentityplatform.openam.test.integration;
18+
19+
import org.openqa.selenium.By;
20+
import org.openqa.selenium.StaleElementReferenceException;
21+
import org.openqa.selenium.WebDriver;
22+
import org.openqa.selenium.WebElement;
23+
import org.openqa.selenium.chrome.ChromeDriver;
24+
import org.openqa.selenium.chrome.ChromeOptions;
25+
import org.openqa.selenium.support.ui.ExpectedCondition;
26+
import org.openqa.selenium.support.ui.ExpectedConditions;
27+
import org.openqa.selenium.support.ui.WebDriverWait;
28+
import org.testcontainers.shaded.org.apache.commons.io.FileUtils;
29+
import org.testng.annotations.AfterClass;
30+
import org.testng.annotations.BeforeClass;
31+
import org.testng.annotations.BeforeMethod;
32+
33+
import java.io.BufferedReader;
34+
import java.io.FileReader;
35+
import java.io.IOException;
36+
import java.nio.file.Path;
37+
import java.nio.file.Paths;
38+
import java.time.Duration;
39+
import java.util.List;
40+
41+
public abstract class BaseTest {
42+
WebDriver driver;
43+
WebDriverWait wait;
44+
45+
final static String AM_PASSWORD = "AMp@ssw0rd";
46+
final static String PA_PASSWORD = "PAp@ssw0rd";
47+
48+
@BeforeClass
49+
public void webdriverSetup() {
50+
ChromeOptions options = new ChromeOptions();
51+
options.addArguments("--remote-allow-origins=*","--headless", "--disable-dev-shm-usage", "--no-sandbox", "--verbose");
52+
//options.addArguments("--remote-allow-origins=*", "--verbose");
53+
driver = new ChromeDriver(options);
54+
wait = new WebDriverWait(driver, Duration.ofSeconds(10));
55+
}
56+
57+
@AfterClass
58+
public void webDriverTearDown() {
59+
if(driver != null) {
60+
driver.quit();
61+
}
62+
}
63+
64+
@BeforeMethod
65+
public void cleanup() throws IOException {
66+
String testConfigPath = System.getProperty("test.config.path");
67+
Path testConfig = Paths.get(testConfigPath);
68+
if(testConfig.toFile().exists()) {
69+
System.out.println("delete existing config directory");
70+
FileUtils.deleteDirectory(testConfig.toFile());
71+
}
72+
}
73+
74+
protected void printInstallLogFile() {
75+
String testConfigPath = System.getProperty("test.config.path");
76+
Path installLog = Paths.get(testConfigPath, "install.log");
77+
if(installLog.toFile().exists()) {
78+
System.err.println("install.log file:");
79+
try (BufferedReader reader = new BufferedReader(new FileReader(installLog.toFile()))) {
80+
String line;
81+
while ((line = reader.readLine()) != null) {
82+
System.err.println(line);
83+
}
84+
} catch (IOException e) {
85+
System.err.println("Error reading file: " + e.getMessage());
86+
}
87+
}
88+
89+
}
90+
91+
WebElement waitForElement(By by) {
92+
return wait.until(ExpectedConditions.presenceOfElementLocated(by));
93+
}
94+
95+
WebElement waitForElementVisible(By by) {
96+
return wait.until(ExpectedConditions.visibilityOfElementLocated(by));
97+
}
98+
99+
public static ExpectedCondition<WebElement> visibilityOfAnyElement(final By locator) {
100+
return new ExpectedCondition<WebElement>() {
101+
102+
@Override
103+
public WebElement apply(WebDriver webDriver) {
104+
List<WebElement> elements = webDriver.findElements(locator);
105+
return elements.stream().filter(WebElement::isDisplayed).findFirst().orElse(null);
106+
}
107+
108+
@Override
109+
public String toString() {
110+
return "visibility of any element " + locator;
111+
}
112+
};
113+
}
114+
115+
public boolean isTextPresent(String str) {
116+
Exception lastException = new Exception();
117+
for(int i = 0; i < 3; i++) {
118+
try {
119+
WebElement bodyElement = new WebDriverWait(driver,Duration.ofSeconds(20)).until(ExpectedConditions.presenceOfElementLocated(By.tagName("body")));
120+
return bodyElement.getText().toLowerCase().contains(str.toLowerCase());
121+
} catch (StaleElementReferenceException e) {
122+
lastException = e;
123+
}
124+
}
125+
throw new RuntimeException(lastException);
126+
}
127+
}
Lines changed: 37 additions & 69 deletions
Original file line numberDiff line numberDiff line change
@@ -1,45 +1,44 @@
1+
/*
2+
* The contents of this file are subject to the terms of the Common Development and
3+
* Distribution License (the License). You may not use this file except in compliance with the
4+
* License.
5+
*
6+
* You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
7+
* specific language governing permission and limitations under the License.
8+
*
9+
* When distributing Covered Software, include this CDDL Header Notice in each file and include
10+
* the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
11+
* Header, with the fields enclosed by brackets [] replaced by your own identifying
12+
* information: "Portions copyright [year] [name of copyright owner]".
13+
*
14+
* Copyright 2022-2025 3A Systems LLC.
15+
*/
16+
117
package org.openidentityplatform.openam.test.integration;
218

319
import org.openqa.selenium.Alert;
420
import org.openqa.selenium.By;
5-
import org.openqa.selenium.StaleElementReferenceException;
6-
import org.openqa.selenium.WebDriver;
21+
import org.openqa.selenium.TimeoutException;
722
import org.openqa.selenium.WebElement;
8-
import org.openqa.selenium.chrome.ChromeDriver;
9-
import org.openqa.selenium.chrome.ChromeOptions;
1023
import org.openqa.selenium.interactions.Actions;
11-
import org.openqa.selenium.support.ui.ExpectedCondition;
1224
import org.openqa.selenium.support.ui.ExpectedConditions;
1325
import org.openqa.selenium.support.ui.WebDriverWait;
14-
import org.testng.annotations.AfterTest;
15-
import org.testng.annotations.BeforeTest;
1626
import org.testng.annotations.Test;
1727

1828
import java.time.Duration;
19-
import java.util.List;
2029

2130
import static org.testng.Assert.assertTrue;
2231

23-
public class IT_Setup {
32+
public class IT_Setup extends BaseTest {
2433

25-
WebDriver driver;
26-
WebDriverWait wait;
34+
@Test
35+
public void testSetup() {
2736

28-
final static String OPENAM_URL = "http://openam.local:8207/openam";
29-
final static String AM_PASSWORD = "AMp@ssw0rd";
30-
final static String PA_PASSWORD = "PAp@ssw0rd";
3137

32-
@BeforeTest
33-
public void webdriverSetup() {
34-
ChromeOptions options = new ChromeOptions();
35-
options.addArguments("--remote-allow-origins=*","--headless", "--disable-dev-shm-usage", "--no-sandbox", "--verbose");
36-
driver = new ChromeDriver(options);
37-
wait = new WebDriverWait(driver, Duration.ofSeconds(10));
38-
}
3938

40-
@Test
41-
public void testSetup() {
42-
driver.get(OPENAM_URL);
39+
final String openamUrl = "http://openam.local:8207/openam";
40+
41+
driver.get(openamUrl);
4342

4443
//wait for setup page is loaded
4544
waitForElement(By.id("pushConfigDialog_c"));
@@ -65,8 +64,19 @@ public void testSetup() {
6564

6665
//wait for setup complete
6766
WebDriverWait waitComplete = new WebDriverWait(driver, Duration.ofSeconds(300));
68-
WebElement proceedToConsole = waitComplete.until(visibilityOfAnyElement(By.cssSelector("#confComplete a")));
69-
proceedToConsole.click();
67+
try {
68+
WebElement proceedToConsole = waitComplete.until(visibilityOfAnyElement(By.cssSelector("#confComplete a")));
69+
proceedToConsole.click();
70+
} catch (TimeoutException e) {
71+
System.err.println("error occurred during install: " + e);
72+
WebElement progressIframe = waitForElement(By.id("progressIframe"));
73+
driver.switchTo().frame(progressIframe);
74+
System.err.println("output messages: " + waitForElement(By.id("progressP")).getText());
75+
printInstallLogFile();
76+
throw e;
77+
} finally {
78+
driver.switchTo().defaultContent();
79+
}
7080

7181
waitForElement(By.id("IDToken1")).sendKeys("amadmin");
7282
waitForElement(By.id("IDToken2")).sendKeys(AM_PASSWORD);
@@ -79,7 +89,7 @@ public void testSetup() {
7989
assertTrue(isTextPresent("You are logged out."));
8090

8191
//check XUI
82-
driver.get(OPENAM_URL.concat("/XUI"));
92+
driver.get(openamUrl.concat("/XUI"));
8393
waitForElement(By.id("idToken1")).sendKeys("amadmin");
8494
waitForElement(By.id("idToken2")).sendKeys(AM_PASSWORD);
8595
waitForElement(By.id("loginButton_0")).click();
@@ -88,47 +98,5 @@ public void testSetup() {
8898
waitForElementVisible(By.id("mainNavBar"));
8999
}
90100

91-
@AfterTest
92-
public void webDriverTearDown() {
93-
if(driver != null) {
94-
driver.quit();
95-
}
96-
}
97-
98-
WebElement waitForElement(By by) {
99-
return wait.until(ExpectedConditions.presenceOfElementLocated(by));
100-
}
101-
102-
WebElement waitForElementVisible(By by) {
103-
return wait.until(ExpectedConditions.visibilityOfElementLocated(by));
104-
}
105-
106-
public static ExpectedCondition<WebElement> visibilityOfAnyElement(final By locator) {
107-
return new ExpectedCondition<WebElement>() {
108101

109-
@Override
110-
public WebElement apply(WebDriver webDriver) {
111-
List<WebElement> elements = webDriver.findElements(locator);
112-
return elements.stream().filter(WebElement::isDisplayed).findFirst().orElse(null);
113-
}
114-
115-
@Override
116-
public String toString() {
117-
return "visibility of any element " + locator;
118-
}
119-
};
120-
}
121-
122-
public boolean isTextPresent(String str) {
123-
Exception lastException = new Exception();
124-
for(int i = 0; i < 3; i++) {
125-
try {
126-
WebElement bodyElement = new WebDriverWait(driver,Duration.ofSeconds(20)).until(ExpectedConditions.presenceOfElementLocated(By.tagName("body")));
127-
return bodyElement.getText().toLowerCase().contains(str.toLowerCase());
128-
} catch (StaleElementReferenceException e) {
129-
lastException = e;
130-
}
131-
}
132-
throw new RuntimeException(lastException);
133-
}
134102
}

0 commit comments

Comments
 (0)