Skip to content

Commit 39c2526

Browse files
refactor!: Update selenium dependencies to v4.14 (#2036)
BREAKING CHANGE: The library is now only compatible to Java11 and above BREAKING CHANGE: The previously deprecated MobileBy class has been removed. Use AppiumBy instead BREAKING CHANGE: The previously deprecated launchApp, resetApp and closeApp methods have been removed. Use extension methods instead BREAKING CHANGE: The previously deprecated WindowsBy class and related location strategies have been removed BREAKING CHANGE: The previously deprecated ByAll class has been removed in favour of the Selenium one BREAKING CHANGE: The previously deprecated AndroidMobileCapabilityType interface has been removed. Use driver options instead BREAKING CHANGE: The previously deprecated IOSMobileCapabilityType interface has been removed. Use driver options instead BREAKING CHANGE: The previously deprecated MobileCapabilityType interface has been removed. Use driver options instead BREAKING CHANGE: The previously deprecated MobileOptions class has been removed. Use driver options instead BREAKING CHANGE: The previously deprecated YouiEngineCapabilityType interface has been removed. Use driver options instead BREAKING CHANGE: Removed several misspelled methods. Use properly spelled alternatives instead BREAKING CHANGE: Removed startActivity method from AndroidDriver. Use 'mobile: startActivity' extension method instead BREAKING CHANGE: Removed the previously deprecated APPIUM constant from the AutomationName interface BREAKING CHANGE: Removed the previously deprecated PRE_LAUNCH value from the GeneralServerFlag enum BREAKING CHANGE: Moved AppiumUserAgentFilter class to io.appium.java_client.internal.filters package Removed dependencies to Apache Commons libraries
1 parent c6f2154 commit 39c2526

File tree

58 files changed

+239
-2906
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

58 files changed

+239
-2906
lines changed

.github/workflows/gradle.yml

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,10 @@ on:
1414
- 'docs/**'
1515
- '*.md'
1616

17+
concurrency:
18+
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
19+
cancel-in-progress: true
20+
1721
env:
1822
ANDROID_SDK_VERSION: 28
1923
ANDROID_EMU_NAME: test
@@ -27,14 +31,13 @@ jobs:
2731
strategy:
2832
matrix:
2933
include:
30-
# TODO: add new LTS Java ( 21 ) once it's released
31-
- java: 8
32-
platform: macos-latest
33-
e2e-tests: android
3434
- java: 11
3535
# Need to use specific (not `-latest`) version of macOS to be sure the required version of Xcode/simulator is available
3636
platform: macos-12
3737
e2e-tests: ios
38+
- java: 15
39+
platform: macos-latest
40+
e2e-tests: android
3841
- java: 17
3942
platform: ubuntu-latest
4043
fail-fast: false

.github/workflows/publish.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ jobs:
1010
- name: Set up Java
1111
uses: actions/setup-java@v3
1212
with:
13-
java-version: '8'
13+
java-version: '11'
1414
distribution: 'zulu'
1515
cache: 'gradle'
1616
- name: Publish package

build.gradle

Lines changed: 11 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,8 @@ repositories {
1616
}
1717

1818
java {
19-
sourceCompatibility = JavaVersion.VERSION_1_8
20-
targetCompatibility = JavaVersion.VERSION_1_8
19+
sourceCompatibility = JavaVersion.VERSION_11
20+
targetCompatibility = JavaVersion.VERSION_11
2121
withJavadocJar()
2222
withSourcesJar()
2323
}
@@ -34,25 +34,23 @@ dependencies {
3434

3535
api ('org.seleniumhq.selenium:selenium-api') {
3636
version {
37-
strictly "[${seleniumVersion}, 4.14)"
37+
strictly "[${seleniumVersion}, 5.0)"
3838
prefer "${seleniumVersion}"
3939
}
4040
}
4141
api ('org.seleniumhq.selenium:selenium-remote-driver') {
4242
version {
43-
strictly "[${seleniumVersion}, 4.14)"
43+
strictly "[${seleniumVersion}, 5.0)"
4444
prefer "${seleniumVersion}"
4545
}
4646
}
4747
api ('org.seleniumhq.selenium:selenium-support') {
4848
version {
49-
strictly "[${seleniumVersion}, 4.14)"
49+
strictly "[${seleniumVersion}, 5.0)"
5050
prefer "${seleniumVersion}"
5151
}
5252
}
5353
implementation 'com.google.code.gson:gson:2.10.1'
54-
implementation 'org.apache.commons:commons-lang3:3.13.0'
55-
implementation 'commons-io:commons-io:2.14.0'
5654
implementation "org.slf4j:slf4j-api:${slf4jVersion}"
5755

5856
testImplementation 'org.junit.jupiter:junit-jupiter:5.10.0'
@@ -93,16 +91,13 @@ tasks.withType(JacocoReport) {
9391
}
9492
jacocoTestReport.dependsOn test
9593

96-
// Checkstyle requires Java 11 starting from 10.0
97-
if (JavaVersion.current().isJava11Compatible()) {
98-
apply plugin: 'checkstyle'
94+
apply plugin: 'checkstyle'
9995

100-
checkstyle {
101-
toolVersion = '10.12.1'
102-
configFile = configDirectory.file('appium-style.xml').get().getAsFile()
103-
showViolations = true
104-
ignoreFailures = false
105-
}
96+
checkstyle {
97+
toolVersion = '10.12.1'
98+
configFile = configDirectory.file('appium-style.xml').get().getAsFile()
99+
showViolations = true
100+
ignoreFailures = false
106101
}
107102

108103
javadoc {

gradle.properties

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
org.gradle.daemon=true
22

3-
selenium.version=4.9.1
3+
selenium.version=4.14.1
44
# Please increment the value in a release
55
appiumClient.version=8.6.0

src/main/java/io/appium/java_client/AppiumBy.java

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,8 @@
1616

1717
package io.appium.java_client;
1818

19+
import com.google.common.base.Preconditions;
1920
import lombok.Getter;
20-
import org.apache.commons.lang3.Validate;
2121
import org.openqa.selenium.By;
2222
import org.openqa.selenium.By.Remotable;
2323
import org.openqa.selenium.SearchContext;
@@ -27,13 +27,15 @@
2727
import java.util.List;
2828
import java.util.Objects;
2929

30+
import static com.google.common.base.Strings.isNullOrEmpty;
31+
3032
public abstract class AppiumBy extends By implements Remotable {
3133

3234
@Getter private final Parameters remoteParameters;
3335
private final String locatorName;
3436

3537
protected AppiumBy(String selector, String locatorString, String locatorName) {
36-
Validate.notBlank(locatorString, "Must supply a not empty locator value.");
38+
Preconditions.checkArgument(!isNullOrEmpty(locatorString), "Must supply a not empty locator value.");
3739
this.remoteParameters = new Parameters(selector, locatorString);
3840
this.locatorName = locatorName;
3941
}

src/main/java/io/appium/java_client/AppiumClientConfig.java

Lines changed: 23 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,15 @@
1616

1717
package io.appium.java_client;
1818

19+
import io.appium.java_client.internal.filters.AppiumIdempotencyFilter;
20+
import io.appium.java_client.internal.filters.AppiumUserAgentFilter;
1921
import org.openqa.selenium.Credentials;
2022
import org.openqa.selenium.internal.Require;
2123
import org.openqa.selenium.remote.http.ClientConfig;
2224
import org.openqa.selenium.remote.http.Filter;
2325

26+
import javax.annotation.Nullable;
27+
import javax.net.ssl.SSLContext;
2428
import java.net.Proxy;
2529
import java.net.URI;
2630
import java.net.URISyntaxException;
@@ -33,7 +37,10 @@
3337
public class AppiumClientConfig extends ClientConfig {
3438
private final boolean directConnect;
3539

36-
private static final Filter DEFAULT_FILTER = new AppiumUserAgentFilter();
40+
private static final Filter DEFAULT_FILTERS = new AppiumUserAgentFilter()
41+
.andThen(new AppiumIdempotencyFilter());
42+
43+
private static final String DEFAULT_HTTP_VERSION = "HTTP_1_1";
3744

3845
private static final Duration DEFAULT_READ_TIMEOUT = Duration.ofMinutes(10);
3946

@@ -49,17 +56,20 @@ public class AppiumClientConfig extends ClientConfig {
4956
* {@link org.openqa.selenium.remote.http.HttpResponse}.
5057
* @param proxy The client proxy preference.
5158
* @param credentials Credentials used for authenticating http requests
59+
* @param sslContext SSL context (if present)
5260
* @param directConnect If directConnect is enabled.
5361
*/
5462
protected AppiumClientConfig(
5563
URI baseUri,
5664
Duration connectionTimeout,
5765
Duration readTimeout,
5866
Filter filters,
59-
Proxy proxy,
60-
Credentials credentials,
67+
@Nullable Proxy proxy,
68+
@Nullable Credentials credentials,
69+
@Nullable SSLContext sslContext,
70+
@Nullable String version,
6171
Boolean directConnect) {
62-
super(baseUri, connectionTimeout, readTimeout, filters, proxy, credentials);
72+
super(baseUri, connectionTimeout, readTimeout, filters, proxy, credentials, sslContext, version);
6373

6474
this.directConnect = Require.nonNull("Direct Connect", directConnect);
6575
}
@@ -73,9 +83,11 @@ public static AppiumClientConfig defaultConfig() {
7383
null,
7484
DEFAULT_CONNECTION_TIMEOUT,
7585
DEFAULT_READ_TIMEOUT,
76-
DEFAULT_FILTER,
86+
DEFAULT_FILTERS,
87+
null,
7788
null,
7889
null,
90+
DEFAULT_HTTP_VERSION,
7991
false);
8092
}
8193

@@ -92,6 +104,8 @@ public static AppiumClientConfig fromClientConfig(ClientConfig clientConfig) {
92104
clientConfig.filter(),
93105
clientConfig.proxy(),
94106
clientConfig.credentials(),
107+
clientConfig.sslContext(),
108+
clientConfig.version(),
95109
false);
96110
}
97111

@@ -103,6 +117,8 @@ private AppiumClientConfig buildAppiumClientConfig(ClientConfig clientConfig, Bo
103117
clientConfig.filter(),
104118
clientConfig.proxy(),
105119
clientConfig.credentials(),
120+
clientConfig.sslContext(),
121+
clientConfig.version(),
106122
directConnect);
107123
}
108124

@@ -175,6 +191,8 @@ public AppiumClientConfig directConnect(boolean directConnect) {
175191
this.filter(),
176192
this.proxy(),
177193
this.credentials(),
194+
this.sslContext(),
195+
this.version(),
178196
directConnect
179197
);
180198
}

src/main/java/io/appium/java_client/AppiumDriver.java

Lines changed: 19 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,10 @@
2323
import io.appium.java_client.remote.AppiumCommandExecutor;
2424
import io.appium.java_client.remote.AppiumNewSessionCommandPayload;
2525
import io.appium.java_client.remote.AppiumW3CHttpCommandCodec;
26-
import io.appium.java_client.remote.MobileCapabilityType;
2726
import io.appium.java_client.remote.options.BaseOptions;
2827
import io.appium.java_client.service.local.AppiumDriverLocalService;
2928
import io.appium.java_client.service.local.AppiumServiceBuilder;
29+
import lombok.Getter;
3030
import org.openqa.selenium.Capabilities;
3131
import org.openqa.selenium.ImmutableCapabilities;
3232
import org.openqa.selenium.MutableCapabilities;
@@ -53,10 +53,10 @@
5353
import java.util.Map;
5454
import java.util.Set;
5555

56+
import static com.google.common.base.Strings.isNullOrEmpty;
5657
import static io.appium.java_client.internal.CapabilityHelpers.APPIUM_PREFIX;
57-
import static io.appium.java_client.remote.MobileCapabilityType.AUTOMATION_NAME;
58-
import static io.appium.java_client.remote.MobileCapabilityType.PLATFORM_NAME;
59-
import static org.apache.commons.lang3.StringUtils.isBlank;
58+
import static io.appium.java_client.remote.options.SupportsAutomationNameOption.AUTOMATION_NAME_OPTION;
59+
import static org.openqa.selenium.remote.CapabilityType.PLATFORM_NAME;
6060

6161
/**
6262
* Default Appium driver implementation.
@@ -72,6 +72,7 @@ public class AppiumDriver extends RemoteWebDriver implements
7272

7373
private static final ErrorHandler ERROR_HANDLER = new ErrorHandler(new ErrorCodesMobile(), true);
7474
// frequently used command parameters
75+
@Getter
7576
private final URL remoteAddress;
7677
protected final RemoteLocationContext locationContext;
7778
private final ExecuteMethod executeMethod;
@@ -154,7 +155,7 @@ public AppiumDriver(URL remoteSessionAddress, String platformName, String automa
154155
RemoteWebDriver.class, this, "capabilities", new ImmutableCapabilities(
155156
ImmutableMap.of(
156157
PLATFORM_NAME, platformName,
157-
APPIUM_PREFIX + AUTOMATION_NAME, automationName
158+
APPIUM_PREFIX + AUTOMATION_NAME_OPTION, automationName
158159
)
159160
)
160161
);
@@ -177,8 +178,7 @@ public AppiumDriver(URL remoteSessionAddress, String platformName, String automa
177178
* Changes platform name if it is not set and returns merged capabilities.
178179
*
179180
* @param originalCapabilities the given {@link Capabilities}.
180-
* @param defaultName a {@link MobileCapabilityType#PLATFORM_NAME} value which has
181-
* to be set up
181+
* @param defaultName a platformName value which has to be set up
182182
* @return {@link Capabilities} with changed platform name value or the original capabilities
183183
*/
184184
protected static Capabilities ensurePlatformName(
@@ -192,17 +192,16 @@ protected static Capabilities ensurePlatformName(
192192
* Changes automation name if it is not set and returns merged capabilities.
193193
*
194194
* @param originalCapabilities the given {@link Capabilities}.
195-
* @param defaultName a {@link MobileCapabilityType#AUTOMATION_NAME} value which has
196-
* to be set up
195+
* @param defaultName a platformName value which has to be set up
197196
* @return {@link Capabilities} with changed mobile automation name value or the original capabilities
198197
*/
199198
protected static Capabilities ensureAutomationName(
200199
Capabilities originalCapabilities, String defaultName) {
201200
String currentAutomationName = CapabilityHelpers.getCapability(
202-
originalCapabilities, AUTOMATION_NAME, String.class);
203-
if (isBlank(currentAutomationName)) {
201+
originalCapabilities, AUTOMATION_NAME_OPTION, String.class);
202+
if (isNullOrEmpty(currentAutomationName)) {
204203
String capabilityName = originalCapabilities.getCapabilityNames()
205-
.contains(AUTOMATION_NAME) ? AUTOMATION_NAME : APPIUM_PREFIX + AUTOMATION_NAME;
204+
.contains(AUTOMATION_NAME_OPTION) ? AUTOMATION_NAME_OPTION : APPIUM_PREFIX + AUTOMATION_NAME_OPTION;
206205
return originalCapabilities.merge(new ImmutableCapabilities(capabilityName, defaultName));
207206
}
208207
return originalCapabilities;
@@ -213,8 +212,7 @@ protected static Capabilities ensureAutomationName(
213212
* and returns merged capabilities.
214213
*
215214
* @param originalCapabilities the given {@link Capabilities}.
216-
* @param defaultPlatformName a {@link MobileCapabilityType#PLATFORM_NAME} value which has
217-
* to be set up
215+
* @param defaultPlatformName a platformName value which has to be set up
218216
* @param defaultAutomationName The default automation name to set up for this class
219217
* @return {@link Capabilities} with changed platform/automation name value or the original capabilities
220218
*/
@@ -265,10 +263,6 @@ public void addCommand(HttpMethod httpMethod, String url, String methodName) {
265263
((AppiumCommandExecutor) getCommandExecutor()).refreshAdditionalCommands();
266264
}
267265

268-
public URL getRemoteAddress() {
269-
return remoteAddress;
270-
}
271-
272266
@Override
273267
protected void startSession(Capabilities capabilities) {
274268
Response response = execute(new AppiumNewSessionCommandPayload(capabilities));
@@ -293,7 +287,7 @@ protected void startSession(Capabilities capabilities) {
293287
// TODO: remove this workaround for Selenium API enforcing some legacy capability values in major version
294288
rawCapabilities.remove("platform");
295289
if (rawCapabilities.containsKey(CapabilityType.BROWSER_NAME)
296-
&& isBlank((String) rawCapabilities.get(CapabilityType.BROWSER_NAME))) {
290+
&& isNullOrEmpty((String) rawCapabilities.get(CapabilityType.BROWSER_NAME))) {
297291
rawCapabilities.remove(CapabilityType.BROWSER_NAME);
298292
}
299293
MutableCapabilities returnedCapabilities = new BaseOptions<>(rawCapabilities);
@@ -346,4 +340,10 @@ public AppiumDriver markExtensionAbsence(String extName) {
346340
absentExtensionNames.add(extName);
347341
return this;
348342
}
343+
344+
protected HttpClient getHttpClient() {
345+
return ReflectionHelpers.getPrivateFieldValue(
346+
HttpCommandExecutor.class, getCommandExecutor(), "client", HttpClient.class
347+
);
348+
}
349349
}

src/main/java/io/appium/java_client/ComparesImages.java

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -23,11 +23,11 @@
2323
import io.appium.java_client.imagecomparison.OccurrenceMatchingResult;
2424
import io.appium.java_client.imagecomparison.SimilarityMatchingOptions;
2525
import io.appium.java_client.imagecomparison.SimilarityMatchingResult;
26-
import org.apache.commons.io.FileUtils;
2726

2827
import javax.annotation.Nullable;
2928
import java.io.File;
3029
import java.io.IOException;
30+
import java.nio.file.Files;
3131
import java.util.Base64;
3232
import java.util.Map;
3333

@@ -93,8 +93,8 @@ default FeaturesMatchingResult matchImagesFeatures(File image1, File image2) thr
9393
*/
9494
default FeaturesMatchingResult matchImagesFeatures(File image1, File image2,
9595
@Nullable FeaturesMatchingOptions options) throws IOException {
96-
return matchImagesFeatures(Base64.getEncoder().encode(FileUtils.readFileToByteArray(image1)),
97-
Base64.getEncoder().encode(FileUtils.readFileToByteArray(image2)), options);
96+
return matchImagesFeatures(Base64.getEncoder().encode(Files.readAllBytes(image1.toPath())),
97+
Base64.getEncoder().encode(Files.readAllBytes(image2.toPath())), options);
9898
}
9999

100100
/**
@@ -160,8 +160,8 @@ default OccurrenceMatchingResult findImageOccurrence(File fullImage, File partia
160160
default OccurrenceMatchingResult findImageOccurrence(File fullImage, File partialImage,
161161
@Nullable OccurrenceMatchingOptions options)
162162
throws IOException {
163-
return findImageOccurrence(Base64.getEncoder().encode(FileUtils.readFileToByteArray(fullImage)),
164-
Base64.getEncoder().encode(FileUtils.readFileToByteArray(partialImage)), options);
163+
return findImageOccurrence(Base64.getEncoder().encode(Files.readAllBytes(fullImage.toPath())),
164+
Base64.getEncoder().encode(Files.readAllBytes(partialImage.toPath())), options);
165165
}
166166

167167
/**
@@ -227,7 +227,7 @@ default SimilarityMatchingResult getImagesSimilarity(File image1, File image2) t
227227
default SimilarityMatchingResult getImagesSimilarity(File image1, File image2,
228228
@Nullable SimilarityMatchingOptions options)
229229
throws IOException {
230-
return getImagesSimilarity(Base64.getEncoder().encode(FileUtils.readFileToByteArray(image1)),
231-
Base64.getEncoder().encode(FileUtils.readFileToByteArray(image2)), options);
230+
return getImagesSimilarity(Base64.getEncoder().encode(Files.readAllBytes(image1.toPath())),
231+
Base64.getEncoder().encode(Files.readAllBytes(image2.toPath())), options);
232232
}
233-
}
233+
}

0 commit comments

Comments
 (0)