[Java] Migrate the String.Format to String.Format(Locale.US) to handle different langauges for Edge, Chrome and Firefox
User description
Description
- This is a contributions to fix: https://github.com/SeleniumHQ/selenium/issues/13930
*Changes Done:
- Migrate the String.Format to Formatter.Format in :
- ChromeDriverSerivce.java
- EdgeDriverService.java
- RemoteWebDriver.java
Motivation and Context
*Issue explaination:
- Having System Date & Language in Arabic caused with driver setup. Using String.Format for ports and some other lines caused them to be localized in the system language and in arabic case it caused the numbers and some other character to be localized in arabic, e.g. the port. And that caused an issues when appending the port to the URL in order to setup the browser
*Fix explaination:
- Now it's utilizing the Formatter.Format and forcing the localization to be in (English.US) ny passing the corresponding Locale in the Formatter Constructor
Types of changes
- [x] Bug fix (non-breaking change which fixes an issue)
- [ ] New feature (non-breaking change which adds functionality)
- [ ] Breaking change (fix or feature that would cause existing functionality to change)
Checklist
- [x] I have read the contributing document.
- [ ] My change requires a change to the documentation.
- [ ] I have updated the documentation accordingly.
- [x] I have added tests to cover my changes.
- [x] All new and existing tests passed.
PR Type
Bug fix
Description
- Updated
ChromeDriverService,EdgeDriverService, andRemoteWebDriverto useFormatter.formatwithLocale.USto ensure consistent formatting across different system locales. - This change addresses issues where system locale settings (like Arabic) affected the formatting of numbers and text in logs and port settings, potentially causing errors in browser setup.
- The use of
Locale.USensures that numbers and text are formatted in a standard way, avoiding issues related to localization.
Changes walkthrough 📝
| Relevant files | |||||||
|---|---|---|---|---|---|---|---|
| Bug fix |
|
💡 PR-Agent usage: Comment
/helpon the PR to get a list of all available PR-Agent tools and their descriptions
PR Description updated to latest commit (https://github.com/SeleniumHQ/selenium/commit/1c526d0055f79762d81a280e3e18616aaa78e155)
- [ ] Copy walkthrough table to "Files Changed" Tab
PR Review 🔍
| ⏱️ Estimated effort to review [1-5] |
2, because the changes are straightforward and localized to string formatting across a few files. The logic is simple, replacing |
| 🧪 Relevant tests |
No |
| ⚡ Possible issues |
Resource Leak: Each |
|
Consistency Issue: In some places, | |
| 🔒 Security concerns |
No |
PR Code Suggestions ✨
| Category | Suggestion | Score |
| Resource management |
✅ Ensure resource management by properly closing
| 9 |
| Performance |
✅ Optimize resource usage by using a single
| 8 |
| Code simplification |
✅ Simplify code and reduce object creation by using direct
| 7 |
| Robustness |
Enhance robustness by handling exceptions in
| 6 |
I think the changes in the PR are not necessary. I looked into this further to realize the findings below:
public static String format(String format, Object... args) {
return new Formatter().format(format, args).toString();
}
This creates a Formatter instance:
public Formatter() {
this(Locale.getDefault(Locale.Category.FORMAT), new StringBuilder());
}
So setting the default using "setDefault(Locale)" should work out of the box without any changes.
Before we close this PR, can you try on your end to double-check if it works as expected using "setDefault"?
@pujagani I just did this to minimize the scope of the affects
But setting the setting the Default to Locale.US should work
You can call it In the same create Args methods once
I will change the fixes to that and give it a try?
@pujagani
Done can you please check and let me know ? (it worked local) Also maybe another pipeline run to make sure everything is working as expected?
@pujagani I revisited the formatting issue
Should be good now
@diemol this look ok?
https://github.com/SeleniumHQ/selenium/pull/13934#issuecomment-2136539473 - I think we don't need to make any changes. Just the tests are sufficient.
@pujagani
But without forcing the localization to be In English, users having their OS default language In arabic will still counter the same issue, won't they?
Is this correct summary?
When a user's default language isn't English, then the code is going to fail unless they add Locale.setDefault(Locale.US).
Then is the question whether we add it to the library itself or whether the user needs to add it to their test? Is there a scenario in which adding that code can cause other problems?
@titusfortner I don't see adding it to Selenium itself causing any issues from My POV tbh
And also many of the users In the middle east are facing start up failures cuz of locale issue
If users are facing a startup problem, it might be good idea to add it on their end. I am not sure if Selenium should assume which default locale to set. Rather the users can themselves add the locale of their choice. What we can do instead is have a test to show how to do that (which a part of this PR does) and have a blog/documentation regarding this. Does that make sense?
I Tested it against some langauges like chinese and japanese, only arabic had this issue because of the url setup
-
Users are getting start up failure exceptions with no indication of What went wrong at all so having a documentation might not be enough for them or at least provide a meaningful error for them
-
Selenium already got Selenium Manager for better drivers handling for the end user by following the Batteries Included approach, isn't that the same? Because having the port set In Arabic will never work, so shouldn't that be handled within Selenium itself?
I understand your point and agree we should have better error handling for this or an informative message. My concern here is that for example if someone wants to use Chinese but now we are setting the locale to US, that is not the expected behavior. Probably, we need to find a different solution or only set the locale to US if it is set to Arabic and probably reset it after start up, not sure what is the correct way to approach this. @titusfortner @diemol
@MustafaAgamy - Just curious. Even the JVM arguments way of setting the locale doesnt help here is it?
@krmahadevan I didn't try to be honest
@pujagani
What if we minimize the scope by moving back to String.format with locale set to en for the required parts only, I guess this way the end user's default locale won't get affected where it's not really needed
@krmahadevan I didn't try to be honest
@MustafaAgamy can you give it a try and post back the results?
@pujagani
What if we minimize the scope by moving back to String.format with locale set to en for the required parts only, I guess this way the end user's default locale won't get affected where it's not really needed
I think this might be the best thing to do. After understanding the issue properly, my thoughts were on the same line. Keep the scope limited to start up. It might also be good to leave a comment in the code as to why it is done.
@MustafaAgamy - Just curious. Even the JVM arguments way of setting the locale doesnt help here is it?
@MustafaAgamy Can you please try this out? If that works, then no code change require and we can document it.
@pujagani sorry I didnt have access to My laptop for the last couple of days
I'll try today and let you know
@MustafaAgamy No rush. We appreciate your contribution and time to Selenium.
Just my 2 cent:
I think calling Locale.setDefault(Locale.US) is a bad idea, this will change propably change alot of things.
Why using String.format here at all, if we do not want Java to format the String?
// users might have a default local with not latin characters set, String.format would break the argument
args.add("--port=" + getPort());
@pujagani The JVM Arguments seems to be working
I added them to the VM Arguments In intelliji and the issue seems to be fixed
But we will have to document it for the users
Thank you for trying it out. Can we close this PR then? Can you help document it too?
We won't need the tests? If yes, then I can Remove the changed code lines and only Keep the test files. Also where should I document it?
Yes, we can only keep the tests. You can help add the documentation by creating a PR in our website repo https://github.com/SeleniumHQ/seleniumhq.github.io.