Skip to content

Commit 8a59520

Browse files
committed
fix: bring back ability to automatically quote desired capabilities on windows systems
1 parent 9a2124c commit 8a59520

File tree

1 file changed

+60
-0
lines changed

1 file changed

+60
-0
lines changed

src/main/java/io/appium/java_client/service/local/AppiumServiceBuilder.java

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,13 +25,16 @@
2525

2626
import com.google.gson.Gson;
2727
import com.google.gson.GsonBuilder;
28+
import io.appium.java_client.remote.AndroidMobileCapabilityType;
29+
import io.appium.java_client.remote.MobileCapabilityType;
2830
import io.appium.java_client.service.local.flags.ServerArgument;
2931

3032
import org.apache.commons.io.IOUtils;
3133
import org.apache.commons.lang3.StringUtils;
3234
import org.apache.commons.lang3.SystemUtils;
3335
import org.apache.commons.validator.routines.InetAddressValidator;
3436
import org.openqa.selenium.Capabilities;
37+
import org.openqa.selenium.Platform;
3538
import org.openqa.selenium.os.ExecutableFinder;
3639
import org.openqa.selenium.remote.BrowserType;
3740
import org.openqa.selenium.remote.DesiredCapabilities;
@@ -78,6 +81,7 @@ public final class AppiumServiceBuilder
7881
private File node;
7982
private String ipAddress = BROADCAST_IP_ADDRESS;
8083
private DesiredCapabilities capabilities;
84+
private boolean autoQuoteCapabilitiesOnWindows = false;
8185
private static final Function<File, String> APPIUM_JS_NOT_EXIST_ERROR = (fullPath) -> String.format(
8286
"The main Appium script does not exist at '%s'", fullPath.getAbsolutePath());
8387
private static final Function<File, String> NODE_JS_NOT_EXIST_ERROR = (fullPath) ->
@@ -86,6 +90,8 @@ public final class AppiumServiceBuilder
8690
// The first starting is slow sometimes on some environment
8791
private long startupTimeout = 120;
8892
private TimeUnit timeUnit = TimeUnit.SECONDS;
93+
private static final List<String> PATH_CAPABILITIES = ImmutableList.of(AndroidMobileCapabilityType.KEYSTORE_PATH,
94+
AndroidMobileCapabilityType.CHROMEDRIVER_EXECUTABLE, MobileCapabilityType.APP);
8995

9096
public AppiumServiceBuilder() {
9197
usingPort(DEFAULT_APPIUM_PORT);
@@ -239,6 +245,21 @@ public AppiumServiceBuilder withCapabilities(DesiredCapabilities capabilities) {
239245
return this;
240246
}
241247

248+
/**
249+
* Adds a desired capabilities.
250+
*
251+
* @param capabilities is an instance of {@link DesiredCapabilities}.
252+
* @param autoQuoteCapabilitiesOnWindows automatically escape quote all
253+
* capabilities when calling appium.
254+
* This is required on windows systems only.
255+
* @return the self-reference.
256+
*/
257+
public AppiumServiceBuilder withCapabilities(DesiredCapabilities capabilities,
258+
boolean autoQuoteCapabilitiesOnWindows) {
259+
this.autoQuoteCapabilitiesOnWindows = autoQuoteCapabilitiesOnWindows;
260+
return withCapabilities(capabilities);
261+
}
262+
242263
/**
243264
* Sets an executable appium.js.
244265
*
@@ -296,7 +317,46 @@ private void loadPathToMainScript() {
296317
this.appiumJS = findMainScript();
297318
}
298319

320+
private String parseCapabilitiesIfWindows() {
321+
if (capabilities == null) {
322+
return "{}";
323+
}
324+
StringBuilder result = new StringBuilder();
325+
Map<String, ?> capabilitiesMap = capabilities.asMap();
326+
Set<? extends Map.Entry<String, ?>> entries = capabilitiesMap.entrySet();
327+
328+
for (Map.Entry<String, ?> entry : entries) {
329+
Object value = entry.getValue();
330+
331+
if (value == null) {
332+
continue;
333+
}
334+
335+
if (value instanceof String) {
336+
String valueString = (String) value;
337+
if (PATH_CAPABILITIES.contains(entry.getKey())) {
338+
value = "\\\"" + valueString.replace("\\", "/") + "\\\"";
339+
} else {
340+
value = "\\\"" + valueString + "\\\"";
341+
}
342+
} else {
343+
value = String.valueOf(value);
344+
}
345+
346+
String key = "\\\"" + entry.getKey() + "\\\"";
347+
if (result.length() > 0) {
348+
result.append(", ");
349+
}
350+
result.append(key).append(": ").append(value);
351+
}
352+
353+
return "{" + result.toString() + "}";
354+
}
355+
299356
private String capabilitiesToCmdlineArg() {
357+
if (autoQuoteCapabilitiesOnWindows && Platform.getCurrent().is(Platform.WINDOWS)) {
358+
return parseCapabilitiesIfWindows();
359+
}
300360
Gson gson = new GsonBuilder()
301361
.disableHtmlEscaping()
302362
.serializeNulls()

0 commit comments

Comments
 (0)