How to install firefox add-on using Capybara & Selenium? - ruby

I am trying to install an add-on on Firefox, however, I couldn't achieve it with whatever I've tried.
require 'capybara'
require 'selenium-webdriver'
Capybara.register_driver :selenium_proxy do |app|
desired_caps = Selenium::WebDriver::Remote::Capabilities.firefox
options = Selenium::WebDriver::Firefox::Options.new
profile = Selenium::WebDriver::Firefox::Profile.new
# Here is the add-on I am trying to install.
profile.add_extension('/home/user/Downloads/try_xpath-1.3.5-fx.xpi')
options.profile = profile
Capybara::Selenium::Driver.new(app, {
browser: :firefox,
desired_capabilities: desired_caps,
options: options
})
end
browser = Capybara::Session.new(:selenium_proxy)
browser.visit 'https://google.com'
What am I doing wrong here? The browser visits the URL without installing any add-on. I am able to install an add-on manually from the file.
Moreover, when I want to add a profile I get the error below:
Errno::ENOENT: No such file or directory # rb_file_s_stat - /tmp/webdriver-rb-profilecopy20200815-25523-ie6apk/lock
from /home/burak/.rbenv/versions/2.6.3/lib/ruby/gems/2.6.0/gems/rubyzip-2.2.0/lib/zip/entry.rb:405:in `stat'

Well, since noone has answered yet I will share how I've overcome this problem in case you want to install extensions.
If anyone else has a better answer then I can accept their answer, so please answer if you have a better solution.
1st Method
I was just messing around with the Firefox profile folders and I figured that I could use an already existing profile folder with only the extensions folder in it. So I've deleted all the other files/folders in the profile folder that I wanted to use.
So basically the steps are:
Create a Firefox profile or use an existing one.
Install your desired add-on using the browser with the same profile.
Close the browser.
Navigate to the same Firefox profile folder and delete all the other files/folders in the profile folder.
Then use the path to that Firefox profile folder when you are instantiating a Selenium::WebDriver::Firefox::Profile like so:
Capybara.register_driver :selenium_proxy do |app|
desired_caps = Selenium::WebDriver::Remote::Capabilities.firefox
options = Selenium::WebDriver::Firefox::Options.new
profile = Selenium::WebDriver::Firefox::Profile.new '/path/to/firefox/profile/folder/'
options.profile = profile
Capybara::Selenium::Driver.new(app, {
browser: :firefox,
desired_capabilities: desired_caps,
options: options
})
end
browser = Capybara::Session.new(:selenium_proxy)
browser.visit 'https://google.com'
I've tried to create a folder named profile and inside that folder I've created another folder named extensions the same way Firefox does and moved all the add-ons I wanted to upload into that extensions folder but that didn't work.
I guess Firefox changes the add-on file when installing the add-on so downloading an add-on from their website and trying to use it in the profile folder doesn't work. This is my guess of course.
2nd Method
You could alternatively use:
browser = Capybara::Session.new(:selenium_proxy)
browser.driver.browser.install_addon '/path/to/addon.xpi'
I know this looks messy so you could just stop using Capybara and use selenium directly but Capybara has some cool methods as well.

Related

Wrong download directory for Selenium Firefox Geckodriver

I've been trying to get Selenium to download a file to a specific folder, but to no avail.
Here is my current driver setup with lots of simultaneous attempts to influence the download directory:
#<Selenium::WebDriver::Firefox::Options:0x00007f94374c0bd0 #debugger_address=nil,
#options={
:browser_name=>"firefox",
:args=>[],
:prefs=>{
"download.folderList"=>2,
"download.dir"=>"./downloads",
"download.directory_upgrade"=>true,
"download.prompt_for_download"=>false,
"download.default_directory"=>"./downloads",
"plugins.plugins_disabled"=>"Chrome PDF Viewer",
"browser.helperApps.neverAsk.saveToDisk"=>"application/pdf, application/vnd.openxmlformats-officedocument.spreadsheetml.sheet, application/vnd.ms-excel, text/csv"
}
},
#profile=#<Selenium::WebDriver::Firefox::Profile:0x00007f94374c0e28 #model=nil,
#additional_prefs={
"browser.download.folderList"=>2,
"browser.download.manager.showWhenStarting"=>false,
"browser.download.downloadDir"=>"./downloads",
"browser.download.dir"=>"./downloads",
"browser.download.directory_upgrade"=>true,
"browser.download.prompt_for_download"=>false,
"browser.download.default_directory"=>"./downloads"
}, #extensions={}>>
I have tried:
Download directory (I'm using Mac):
/lib/downloads
downloads
./downloads
Lots of combinations of the above attempts to set the download directory.
I went through the selenium-webdriver docs and Mozilla Webdriver docs, but I cannot find references to set the download directory.
Try this and let me know whether it works.
profile = Selenium::WebDriver::Firefox::Profile.new(ENV['APPDATA'] + '\Mozilla\Firefox\Profiles\3deyh6ub.default-release')
profile['browser.download.dir'] = custom_download_dir
profile['browser.download.folderList'] = 2
options = Selenium::WebDriver::Firefox::Options.new(profile: profile)
driver = Selenium::WebDriver.for :firefox, options: options
and check out this path Mozilla\Firefox\Profiles\3deyh6ub.default-release and see what's the folder name and give the folder name accordingly and it will work.
The custom directory path has to be absolute, formed as shown:
On Mac, ~Downloads folder would be /Users/[me]/Downloads.
In Rails, say you want to put the downloads in lib/custom_downloads, the directory specified should be Dir.pwd + '/lib/custom_downloads'.
The code that worked for me:
profile = Selenium::WebDriver::Firefox::Profile.new
profile['browser.download.folderList'] = 2
profile['browser.download.dir'] = Dir.pwd + '/forecastsdir'
profile['browser.helperApps.neverAsk.saveToDisk'] = ('application/vnd.openxmlformats-officedocument.spreadsheetml.sheet, application/vnd.ms-excel')
options = Selenium::WebDriver::Firefox::Options.new(profile: profile, args: ['-headless'])
driver = Selenium::WebDriver.for :firefox, options: options
Many thanks to #Rajagopalan (+1) for assistance.

how to download file to a specific location on .click of watir?

when I click on a link of a web page in chrome web browser with ruby watir
ie.input(:id, "c_ImageButton_Text").click
.text file start downloading. I want to download it to a specific location.I tried this code,but still getting.text file in default download location.How can I download .text file to specific location?
download_directory = "#{Dir.pwd}/downloads"
download_directory.gsub!("/", "\\") if Selenium::WebDriver::Platform.windows?
profile = Selenium::WebDriver::Chrome::Profile.new
profile['download.prompt_for_download'] = false
profile['download.default_directory'] = download_directory
b = Watir::Browser.new :chrome, :profile => profile
click here for this code
For latest watir version 6.6.1
prefs = {
prompt_for_download: false,
default_directory: Rails.root.join('tmp').to_s
}
options = Selenium::WebDriver::Chrome::Options.new
options.add_preference(:download, prefs)
browser = Watir::Browser.new :chrome, options: options
As the old saying goes, "There is more than one way to skin a cat":
You can certainly try to skin it the way you are attempting to do in your example code. However, there are a number of issues with this course of action. Namely, it is browser specific.
I really like how Elemental Selenium suggests achieving valid tests and assertions on downloading files by using the rest-client gem to curl the file's URI and assert the expectations of the file from from there: http://elemental-selenium.com/tips/8-download-a-file-revisited

Automatic downloading stopped due to the proper MIME type mismatch

I have written one script to download files automatically from the web as below:
#Automatically download files to a given folder profile settings
#---------------------------------------------------------------
profile = Selenium::WebDriver::Firefox::Profile.new
profile['browser.download.dir'] = 'C:\Documents and Settings\My Documents\userdata\Rubydownloads'
profile['browser.download.folderList'] = 2
profile['browser.helperApps.neverAsk.saveToDisk'] = "application/pdf,application/x-pdf,application/acrobat,application/vnd.pdf,text/pdf,text/x-pdf,image/jpeg,image/pjpeg,image/gif,image/bmp,image/x-windows-bmp,image/tif,image/x-tif,image/tiff,image/x-tiff,application/tif,application/x-tif,application/tiff,application/x-tiff"
profile['browser.download.manager.showWhenStarting'] = false
driver = Selenium::WebDriver.for :firefox, :profile => profile
But my bad, some of the .tif,.tiff and .pdf still missed without being download. Can it be done, say - if proper mime type not found in the above profile settings,then the script should add that mime to the browser settings,to continue downloading ?
Please help me here.
I'm working through a similar problem.
I'm not sure if you're missing mime-types in your neverAsk.saveToDisk list (it doesn't look like it), but I'll suggest that the following may help:
profile['browser.helperApps.alwaysAsk.force'] = 'false'

How to check the location of download folder programmatically in browsers like Safari, Firefox etc on Mac?

I am a part of Automation testing and I am downloading and installing the files programmatically with Selenium and Applescript on Mac. Is their any way to check the location of download folder on browsers programmatically?? if so pls suggest and also ways to change the location of download folder in Java or Applescript.
may be you can try like this on firefox:
profile = Selenium::WebDriver::Firefox::Profile.new
profile['browser.download.dir'] = "/tmp/webdriver-downloads"
profile['browser.download.folderList'] = 2
profile['browser.helperApps.neverAsk.saveToDisk'] = "application/pdf"
b = Watir::Browser.new :firefox, :profile => profile
Safari has a preference for it in ~/Library/Preferences/com.apple.Safari.plist:
defaults read com.apple.Safari DownloadsPath
You can also change it by modifying the property list, but the changes aren't applied until Safari is reopened.
defaults write com.apple.Safari DownloadsPath "~/Desktop"

Watir Changing Mozilla Firefox Preferences

I'm running a Ruby script using Watir to automate some things for me. I'm attempting to automatically save some files to a certain directory. So, in my Mozilla settings I set my default download directory to say the desktop and choose to automatically save files.
These changes, however, are not reflected when I begin to run my script. It seems like the preferences revert back to default. I've included the following
require "rubygems" # Optional.
require "watir-webdriver" # For web automation.
require "win32ole" # For file save dialog.
and open a new firefox instance with:
browser = Watir::Browser.new(:firefox)
Any ideas on why the preferences would be set back by this? Or any alternative ideas for what I am trying to do? (Automatically save files).
Thanks
WebDriver uses a clean profile for each browser instance, which is why the preferences appear to be "reset". You can tell it to use your default profile:
Watir::Browser.new :firefox, :profile => "default"
or tweak profile preferences programatically before launching the browser:
profile = Selenium::WebDriver::Firefox::Profile.new
profile['some.preference'] = true
profile.add_extension "/path/to/some/extension.xpi"
Watir::Browser.new :firefox, :profile => profile
For an example of configuring automatic file downloads, see this section on the Selenium wiki.
change default Watir preferences for download location
for chrome
profile = Selenium::WebDriver::Chrome::Profile.new
download_dir = File.join(Rails.root, 'lib', 'assets')
profile['download.default_directory'] = download_dir
profile[download.prompt_for_download] = false
#b = Watir::Browser.new :chrome, :profile => profile
for firefox
profile = Selenium::WebDriver::Firefox::Profile.new
download_dir = File.join(Rails.root, 'lib', 'assets')
profile['browser.download.dir'] = download_dir
profile['browser.helperApps.neverAsk.saveToDisk'] = "text/csv,application/pdf"
#b = Watir::Browser.new. :firefox, :profile => profile
note: to be be able to access the Rails.root/lib folder easily from within your rails app, you'll need to add this code or something like it to your config/application.rb file:
config.autoload_paths += Dir["#{config.root}/lib/**/"]
for more information: http://watirwebdriver.com/browser-downloads/

Resources