SeleniumHQ / selenium

A browser automation framework and ecosystem.
https://selenium.dev
Apache License 2.0
30.22k stars 8.11k forks source link

[🚀 Feature]: Release Selenium Manager binaries #11694

Open bonigarcia opened 1 year ago

bonigarcia commented 1 year ago

Feature and motivation

Currently, the Selenium Manager binaries are shipped within the bindings. Maybe we can release it as a separate artifact with each release of Selenium, for standalone usage.

Usage example

n/a

titusfortner commented 1 year ago

I'm a 👎 on releasing this separately for the foreseeable future. The primary value of this feature is that users don't need to know how it works or that it even exists; Selenium just works.

titusfortner commented 11 months ago

Selenium Manager functionality is pretty advanced at this point.

We need to determine what is "feature complete" soon and that is going to depend somewhat on where we go with this issue.

Pros:

Cons:

Alternatives:

diemol commented 11 months ago

There will always be room to add more features and flags because we are in "beta." If we move to a stable release, that would be a point where we consider the group of things we want to support, where we consider most cases to be covered, and where no more flags should be added (an exception always happens).

Now with browser downloads, I perceive we have left that beta, and it is a good time to start releasing SM.

titusfortner commented 8 months ago

Did we agree we wouldn't do this in our meeting in London? Or is this still on the table for Selenium 5 when we upgrade it to stable status?

Now that we have the nightly artifacts, if someone really wants to use it, they can get it, but we have the disclaimer that using it outside of the bindings is not explicitly supported.

diemol commented 8 months ago

We did not precisely decide this; we decided to have a separate repository to stop storing the binary on the principal repository. I would say this is on the table for Selenium 5.

sba923 commented 8 months ago

I used to have my Update-SeleniumDriver.ps1 script (https://gist.github.com/sba923/d5406e7fded598b9c1131ddf9f099564) download from https://github.com/SeleniumHQ/selenium/raw/trunk/common/manager/windows/selenium-manager.exe, and this broke some time ago.

Is there an alternative, even temporary location to get the file from?

One of the features implemented by the script is copying msedgedriver.exe to MicrosoftWebDriver.exe.

titusfortner commented 8 months ago

We no longer store the binaries in the repo, but I'm curious your use case. Why not just have selenium manage it for you at runtime? Why rename it?

sba923 commented 8 months ago

I'm automating Edge using Selenium via the PowerShell Selenium module, and my experience is that this requires the (matching version of the) MicrosoftWebDriver.exe file on the PATH, hence the code I implemented in the Update-SeleniumDriver.ps1 script.

image

titusfortner commented 8 months ago

If it doesn't find the right driver on the path, selenium will now download it for you automatically. For standard use cases, you shouldn't need to use selenium manager directly.

This is why I'm interested in what more complicated use cases exist where this isn't sufficient.

sba923 commented 8 months ago

Given that it doesn't work in my scenario, could it just be that the PowerShell module doesn't use the latest Selenium?

titusfortner commented 8 months ago

Oh, yes selenium-powershell is quite old. Ok, this is a valid use case for having a released Selenium Manager. The latest binaries are built here — https://github.com/SeleniumHQ/selenium_manager_artifacts/releases But the tool is still in beta.

sba923 commented 8 months ago

Great! I have updated Update-SeleniumDriver.ps1 to use

# determine URL for latest selenium-manager.exe
$latestrelease = (((Invoke-WebRequest -Uri 'https://github.com/SeleniumHQ/selenium_manager_artifacts/releases').Content -split "`n" -match '/releases/tag/')[0] -replace '.*href=".*/selenium-manager-(\S+)".*', '$1')
$url = ('https://github.com/SeleniumHQ/selenium_manager_artifacts/releases/download/selenium-manager-{0}/selenium-manager-windows.exe' -f $latestrelease)
sba923 commented 7 months ago

FYI I have updated https://gist.github.com/sba923/d5406e7fded598b9c1131ddf9f099564#file-update-seleniumdriver-ps1 so that it takes into account a recent change in the Selenium Manager that affects its behavior when the driver is present on the PATH.

titusfortner commented 7 months ago

@sba923 Just so you know, what is in that repo is not guaranteed to be production-ready. It only exists because of a limitation in how we are building things for our Selenium releases.

sba923 commented 7 months ago

I do understand, but until everything that I depend on (esp. the PowerShell module) is aligned with the latest Selenium releases, there's nothing I can do but depend on this. Unless you have a better solution, that is 😜.

titusfortner commented 7 months ago

I'd manually pull the one that was most recently released.

titusfortner commented 7 months ago

i.e. — https://github.com/SeleniumHQ/selenium/blob/selenium-4.17.0/common/selenium_manager.bzl#L24

sba923 commented 7 months ago

I think that is what I attempted to do 😋

# make sure selenium-manager is the latest version
$tmpfile = Join-Path -Path $env:TEMP -ChildPath 'selenium-manager.exe'
# determine URL for latest selenium-manager.exe
$latestrelease = (((Invoke-WebRequest -Uri 'https://github.com/SeleniumHQ/selenium_manager_artifacts/releases').Content -split "`n" -match '/releases/tag/')[0] -replace '.*href=".*/selenium-manager-(\S+)".*', '$1')
$url = ('https://github.com/SeleniumHQ/selenium_manager_artifacts/releases/download/selenium-manager-{0}/selenium-manager-windows.exe' -f $latestrelease)
Invoke-WebRequest -Uri $url -OutFile $tmpfile
if (!(Test-Path -LiteralPath $tmpfile))
{
    throw ("Cannot retrieve latest 'selenium-manager.exe' from '{0}'" -f $url)
}
if ((Get-FileHash -Path $tmpfile).Hash -ne ((Get-FileHash -Path $seleniummanager).Hash))
{
    Write-Verbose ("Updating '{0}'..." -f $seleniummanager)
    Copy-Item -Destination $seleniummanager -Path $tmpfile
}
Remove-Item -Path $tmpfile

Write-Verbose ("Using {0}" -f (selenium-manager --version))
sba923 commented 7 months ago

Feel free to give https://gist.github.com/sba923/d5406e7fded598b9c1131ddf9f099564#file-update-seleniumdriver-ps1 a shot and provide feedback!

Here's an example of the execution of the script:

PS> Update-SeleniumDriver.ps1 -Verbose
VERBOSE: Requested HTTP/1.1 GET with 0-byte payload
VERBOSE: Received HTTP/1.1 response of content type text/html of unknown size
VERBOSE: Requested HTTP/1.1 GET with 0-byte payload
VERBOSE: Received HTTP/1.1 3924480-byte response of content type application/octet-stream
VERBOSE: File Name: selenium-manager.exe
VERBOSE: Using selenium-manager 0.4.18
VERBOSE: Updating Selenium driver 'msedgedriver.exe' for browser 'edge'
VERBOSE: Selenium Manager has retrieved 'c:\usr\wbin\msedgedriver.exe'
VERBOSE: 'c:\usr\wbin\msedgedriver.exe' is already up to date: version 121.0.2277.83
VERBOSE: Performing the operation "Copy File" on target "Item: C:\usr\wbin\msedgedriver.exe Destination: C:\usr\wbin\MicrosoftWebDriver.exe".
VERBOSE: Updating Selenium driver 'geckodriver.exe' for browser 'firefox'
VERBOSE: selenium-manager has emitted the 'it is advised to delete the driver in PATH and retry' warning, deleting 'C:\Users\steph\geckodriver.exe' and retrying
VERBOSE: Performing the operation "Remove File" on target "C:\usr\wbin\geckodriver.exe".
VERBOSE: Selenium Manager has retrieved 'C:\Users\steph\geckodriver.exe'
Installing 'geckodriver.exe' as 'c:\usr\wbin\geckodriver.exe'
VERBOSE: Performing the operation "Copy File" on target "Item: C:\Users\steph\geckodriver.exe Destination: C:\usr\wbin\geckodriver.exe".
VERBOSE: Updating Selenium driver 'chromedriver.exe' for browser 'chrome'
VERBOSE: selenium-manager has emitted the 'it is advised to delete the driver in PATH and retry' warning, deleting 'C:\Users\steph\chromedriver.exe' and retrying
VERBOSE: Performing the operation "Remove File" on target "C:\usr\wbin\chromedriver.exe".
VERBOSE: Selenium Manager has retrieved 'C:\Users\steph\chromedriver.exe'
Installing 'chromedriver.exe' as 'c:\usr\wbin\chromedriver.exe'
VERBOSE: Performing the operation "Copy File" on target "Item: C:\Users\steph\chromedriver.exe Destination: C:\usr\wbin\chromedriver.exe".
titusfortner commented 7 months ago

I'm saying your $latestrelease value based on the tags in the artifacts repo is not actually the latest release, but the latest built, which is not necessarily production ready. You can get the latest actually released at the URL referenced in the Selenium repo.

sba923 commented 7 months ago

That should do the trick:


# make sure selenium-manager is the latest version
$tmpfile = Join-Path -Path $env:TEMP -ChildPath 'selenium-manager.exe'
# determine URL for latest production-ready, released selenium-manager.exe
# (see https://github.com/SeleniumHQ/selenium/issues/11694#issuecomment-1927884476)
$url = @(((Invoke-WebRequest -Uri 'https://github.com/SeleniumHQ/selenium/blob/selenium-4.17.0/common/selenium_manager.bzl').Content -split "`n") -match '\.exe' -replace '.*(https://[^"]+selenium-manager-windows\.exe).*','$1')[0]
Invoke-WebRequest -Uri $url -OutFile $tmpfile
if (!(Test-Path -LiteralPath $tmpfile))
{
    throw ("Cannot retrieve latest 'selenium-manager.exe' from '{0}'" -f $url)
}
if ((Get-FileHash -Path $tmpfile).Hash -ne ((Get-FileHash -Path $seleniummanager).Hash))
{
    Write-Verbose ("Updating '{0}'..." -f $seleniummanager)
    Copy-Item -Destination $seleniummanager -Path $tmpfile
}
Remove-Item -Path $tmpfile

Write-Verbose ("Using {0}" -f (selenium-manager --version))
diemol commented 4 months ago

During the May 2024 Selenium Summit, we made the decision to implement this.

nvborisenko commented 4 months ago

We might also consider packing binaries as a tool. So users will be able to npx install ... or dotnet tool install ....

sba923 commented 4 months ago

We might also consider packing binaries as a tool. So users will be able to npx install ... or dotnet tool install ....

and of course winget install ...

titusfortner commented 4 months ago

@nvborisenko the JS piece is being tracked here - https://github.com/SeleniumHQ/selenium/issues/11378

cum8197 commented 3 months ago

3b57079

gitissuepost commented 2 days ago

@bonigarcia - I have seen the behavior of selenium-manager is not properly aligned for MsEdge. Unlike Chrome, MsEdge has a specific webdriver for each version of Ms Edge (Chromium). However, selenium-manager is not downloading that specific version. E.g. The Edge Version I have in my laptop is V128.0.2739.67 and to keep the driver fully aligned with my browser, I expect the driver of this exact version. image

However, selenium-manager downloaded driver of V128.0.2739.79. In earlier implementations of webdrivermanager (prior Selenium 4), I had seen that it refers to a remote file to fetch the latest version. If that's not accessible, it refers the properties list shipped along with the library. The content in both may not be aligned with the browser version one has in their machine.

If I am not wrong, the similar implementation has been extended to Selenium 4 making it an executable.

I had also encountered the issue where my Edge was in V97 and the driver got downloaded was V110 (as the remote file and the the one in jar was pointing to latest version as 110). This was not invoking my driver due to version mismatch. Upon debugging I found the above rationale but couldn't figure out how to override this to download a specific driver even when it is out-dated. For Chrome, this may also be applicable, but I never tried this on Chrome.

Please suggest if I need to log this as an issue in any issue tracker?

For us, the only applicable browser is Edge and due to 1-1 mapping, we download the driver of that version directly.

bonigarcia commented 12 hours ago

@gitissuepost Selenium Manager discovers the proper msedgedriver version to be used by requesting the online metadata endpoint maintained by Microsoft. See an example I just executed on my machine (Linux):

./selenium-manager --browser edge --debug

[2024-09-19T13:18:02.634Z DEBUG] msedgedriver not found in PATH
[2024-09-19T13:18:02.634Z DEBUG] edge detected at /usr/bin/microsoft-edge
[2024-09-19T13:18:02.638Z DEBUG] Running command: /usr/bin/microsoft-edge --version
[2024-09-19T13:18:02.730Z DEBUG] Output: "Microsoft Edge 128.0.2739.67 "
[2024-09-19T13:18:02.735Z DEBUG] Detected browser: edge 128.0.2739.67
[2024-09-19T13:18:02.735Z DEBUG] Reading msedgedriver version from https://msedgedriver.azureedge.net/LATEST_RELEASE_128_LINUX
[2024-09-19T13:18:02.909Z DEBUG] Required driver: msedgedriver 128.0.2739.81
[2024-09-19T13:18:02.920Z DEBUG] Downloading msedgedriver 128.0.2739.81 from https://msedgedriver.azureedge.net/128.0.2739.81/edgedriver_linux64.zip
[2024-09-19T13:18:04.285Z INFO ] Driver path: /home/boni/.cache/selenium/msedgedriver/linux64/128.0.2739.81/msedgedriver

My Edge version is, at this moment, 128.0.2739.67. So, Selenium Manager requests the following endpoint to discover the proper msedgedriver version to be used by Selenium:

https://msedgedriver.azureedge.net/LATEST_RELEASE_128_LINUX

At this moment, it is msedgedriver 128.0.2739.81.

According to your 1-1 idea, Selenium Manager should use msedgedriver 128.0.2739.67. But if you try to download that release, you will discover it is not even published:

https://msedgedriver.azureedge.net/128.0.2739.67/edgedriver_linux64.zip

gitissuepost commented 11 hours ago

@bonigarcia - But I see it available in Edge Driver directory https://msedgewebdriverstorage.z22.web.core.windows.net/?prefix=128.0.2739.67/ and it is available for download and consume. This directory link is available under the official page where we download the drivers manually for edge.

image It's not available for Linux, but other OS users can utilize this. If I am using Windows/Mac, I should get this version as 1st preference rather getting a driver meant for a later version.

Moreover, I may not be aware, do we have any option to pass proxy details along with credential to manager to download the files? In couple of my earlier firms, the request should be chained with proxy and credential to download any third party code via code/api. Otherwise, the firewall used to block the request failing the download.

bonigarcia commented 10 hours ago

Yes, but there is no Linux release there, which the one I needed in the example before. The point is that 1-1 compatibility is not always possible. And for the best of my knowledge, not required for driving Edge properly with Selenium.