Using profile in Watir and Webdriver - google-chrome

My question is regarding modify default profile settings to allow/deny access of mic and cam by my web app. Here is the code - which seems to be ignored.
#!/usr/bin/ruby
require 'watir-webdriver'
profile = Selenium::WebDriver::Chrome::Profile.new
profile['content_settings.pattern_pairs.*,*.media-stream-mic'] = 1
# if I put mysever.com into here (first asterix), the parsing must fail
# as the '.' is used as delimiter by profile.rb - so *,* should work
browser = Watir::Browser.new :chrome, :profile => profile
browser.goto "http://webaudiodemos.appspot.com/input/index.html"
# here a get media event is fired and the browser should proceed without(!)
# asking the user for permission - but the browser is always asking and
# this element is not accessible for Watir (is it?).
I had a look into profile.rb where just the parsing takes place - which is also somehow problematic (see comment inline).
I also searched the web but could not find anything.
Holger

1. create a profile manually using the cmd :
firefox -profilemanager
set what you want on the browser of the new profile
2.code example
protected void initializeWebDriver() {
LoggerInfo.logger.info("Starting webdriver...");
ProfilesIni allProfiles = new ProfilesIni();
FirefoxProfile profile = allProfiles.getProfile("MyProfile");
// FirefoxProfile profile = new FirefoxProfile();
driver = new DriverBuilder().using(Browser.FIREFOX).withFirefoxProfile(profile).build();
LoggerInfo.logger.info("webdriver is up");
}

Related

Chromecast - How to reconnect to the session after page refresh?

After reloading the page, method
cast.framework.CastContext.getInstance()
returns status 'NOT_CONNECTED' and 'NO_SESSION'
My code example:
const castContext = window.cast.framework.CastContext.getInstance();
castContext.setOptions({
receiverApplicationId:
window.chrome.cast.media.DEFAULT_MEDIA_RECEIVER_APP_ID,
autoJoinPolicy: window.chrome.cast.AutoJoinPolicy.ORIGIN_SCOPED,
resumeSavedSession: true
});
await castContext.requestSession(); // wait for prompt
const castSession = castContext.getCurrentSession();
const mediaInfo = new window.chrome.cast.media.MediaInfo(mediaUrl);
const request = new window.chrome.cast.media.LoadRequest(mediaInfo);
await castSession.loadMedia(request);
window.player = new window.cast.framework.RemotePlayer();
window.playerController = new window.cast.framework.RemotePlayerController(
window.player);
Can you please tell me how to connect to an existing session and receive information about playing media?
I been looking around for answers for a while and your switch of port make me think.
Switching port not a valid solution!
Why does a solution suddenly stop working without any changes to my Chromecast code?
Answer: Chrome got the hiccups. I guess this is either because of several live-refresh or something went wrong during development and it has been cached?!
Solution: I cleared the application storage and deleted my Chrome profile. After a restart of Chrome my solution reconnects with the chromecast as it did before.

Coded UI - Cross browser issue. Not able to identify controls on Chrome

I have a web application hosted on http://localhost/MyWebApplication. And I am using Coded UI as a tool to perform UI Automation on the application
I have to carry out concurrency kind of scenaios where in two different admin users (say user1 & user2) login to http://localhost/MyWebApplication. When user1 performs any operation like edit or delete the same should be reflected on data for user2
To achieve this, I am logging into MyWebAppliction on IE browser as user1 & Chrome browser as user2. And I am able to launch and login to IE & Chrome as user1 & user2 respectively.
Now after I perform some edit, delete operation on user1 in IE, I need to go back & check if it is reflected in user2 in chrome. And I need to do Vise-versa as well (i.e Chrome to IE)
To switch between the browsers, I have writtent below method to bring the required browser (IE or chrome) to foreground
using System.Runtime.InteropServices;
using System.Diagnostics;
[DllImport("user32.dll")]
public static extern bool SetForegroundWindow(IntPtr hWnd);
public void SwitchBrowserForMyWebApp(string browserName)
{
System.Diagnostics.Process[] p = System.Diagnostics.Process.GetProcessesByName(browserName).Where(x => x.MainWindowTitle.Contains("My Web Application")).ToArray();
if (p.Length > 0)
{
SetForegroundWindow(p[0].MainWindowHandle); // bring the desired browser to the front
}
// ========== Till here it works fine & brings the required browser to the front.
BrowserWindow curWindow;
if (browserName == "iexplore")
{
BrowserWindow.CurrentBrowser = "IE";
}
else
{
BrowserWindow.CurrentBrowser = browserName;
Process browserProcess = p[0];
BrowserWindow bwp = BrowserWindow.FromProcess(p[0]); // Here it gives null exception - Object not set to instance of an object
//BrowserWindow.Locate("My Web Application - Google Chrome");
}
}
Problem I am facing here is, If i bring IE to foreground, then I am able to access controls and perform edit or update
But if I bring chrome to foreground, then I am unable to access any of the controls on chrome.
I tried setting CurrentBrowser as "Chrome", used BrowserWindow.Locate("My Web Application - Google Chrome"), Also used BrowserWindow.FromProcess(p[0]);
Not able to find what is the issue. I am using IE 11 & Chrome version: 47.0.2526.111 m
Can any one let me know if I am missing anything. Or any work around to resolve this issue
Thanks in Advance
I haven't tried this, but Setting the "CurrentBrowser" Property does not switch browsers. This property has to be set before you call the Browser.Launch() Method to initialize the browser driver u use. It's defaulted to IE. U will have to use two different Browser Instance and use the one need. May be something like this,
public static BrowserWindow CurrentBrowser= null, Chrome = null, IE = null;
IE = BrowserWindow.Launch(new Uri("http:\\urAppURLHere.COM"));
BrowserWindow.CurrentBrowser = "Chrome"
Chrome = BrowserWindow.Launch(new Uri("http:\\urAppURLHere.COM"));
CurrentBrowser = GetMeTheBrowserIWant("Chrome");
public static BrowserWindow GetMeTheBrowserIWant(string BrowserType)
{
if(BrowserType.ToUpper().Equals("CHROME")
{
return Chrome;
}
if(BrowserType.ToUpper().Equals("IE")
{
return IE;
}
}
You are Switching the Browser, but the Test Object u identified is still instantiated with Chrome.
You will have to re identify the Test Object using IE Again.
Something like,
GmailLogOnButton = new HtmlControl(GetMeTheBrowserIWant("IE"));
GmailLogOnButton.SearchProperties.Add(HtmlControl.PropertyNames.Id, "signIn");
Coded Ui framework is not developed considering Concurrent execution of Same Steps. So when you try concurrency tests, u will end up doing additional steps.
You, may also consider using Threading, but it may create difficulties in how u sync your tests!!

Setting profile/capabilities for chrome and ie8 through selenium

I am automating a test on aws.amazon.com to check whether the resources that i created using aws cli were successfully created or not using selenium webdriver. As the site falls out of my company network, to access the site i need to provide domain user/password in modal pop up that comes before hitting the url for the site.
i am not sure , but solution to this problem is to set profile/capability in the browser settings through the code. before hitting the url.
i have achieved that in firefox as follows
FirefoxProfile profile = new FirefoxProfile();
profile.addExtension(new File(Constants.FIREFOX_ADDON_PATH));
profile.setPreference("extensions.enabledAddons", "FireXPath%40pierre.tholence.com:0.9.7.1,proxyauth%40lammersoft.com:0.1.2,%7B972ce4c6-7e08-4474-a285-3208198ce6fd%7D:37.0.1");
profile.setPreference("extensions.proxyauth.authtoken","c3ViaGFtdDpub3YwNDIwMTQ=");
How to do the same in chrome and ie8 ?
i went through this but not able to comprehend anything.Also what does .xpi and .crx file has to do with all of this ?
This is pop up image for chrome
This is pop up image for IE8
The popup is a Windows Http Authentication popup and cannot be handled by using Selenium Webdriver. You will have to use either Robot Class or AutoIT to handle it.
1. Using Robot Class:
Alert authenticationWindow = driver.switchTo().alert();
// Type the username/email.
authenticationWindow.sendKeys("<username/email address>");
// Shift cursor focus to password input text field.
Robot robot = new Robot();
robot.keyPress(KeyEvent.VK_TAB);
// Type the password in password field. [ Selenium does not know at this point that the cursor focus is shifted, so calling Alert class instance sendKeys() will cause password to be typed in username field. So, we are copying the password first to windows clipboard and then pasting it directly into the password field using Robot class instance ]
StringSelection stringSelection = new StringSelection("<user password>");
Toolkit.getDefaultToolkit().getSystemClipboard().setContents(stringSelection,null); robot.keyPress(KeyEvent.VK_CONTROL);
robot.keyPress(KeyEvent.VK_V);
robot.keyRelease(KeyEvent.VK_CONTROL);
// Accept the authentication window.
robot.keyPress(KeyEvent.VK_ENTER);
2. Using AutoIT:
This link provides good information on how to use AutoIT alongwith Selenium: http://www.toolsqa.com/selenium-webdriver/autoit-selenium-webdriver/
Here is what you have to do:
Download/install AutoIT
You will be able to create .au3 scripts using AutoIT SciTe Editor
Compiling the .au3 script will give you a .exe file
Then you can invoke the .exe file from your Selenium script using
Runtime.getRuntime().exec("D:\AutoIt\AutoItTest.exe");
You can get the properties of a window using the AutoIT Window Info (x86) or (x64). Example, title / status bar of a window.
AutoIT also has Au3 Recorder so that you can record your actions that are related to the remote desktop.
Below is a sample script that automates Http authentication:
WinWaitActive("Web page title","","10")
If WinExists("Web page title") Then
Send("userid{TAB}")
Send("password{Enter}")
EndIf
3. Using AutoITx4Java:
Check this library AutoITx4Java - https://code.google.com/p/autoitx4java/
Download Jacob, AutoIT (refer the above link)
Add jacob.jar and autoitx4java.jar to your library path.
Place the jacob-1.15-M4-x64.dll file in your library path.
Sample Code
File file = new File("lib", "jacob-1.15-M4-x64.dll"); //path to the jacob dll
System.setProperty(LibraryLoader.JACOB_DLL_PATH, file.getAbsolutePath());
AutoItX x = new AutoItX();
String notepad = "Untitled - Notepad";
String testString = "this is a test.";
x.run("notepad.exe");
x.winActivate(notepad);
x.winWaitActive(notepad);
x.send(testString);
Assert.assertTrue(x.winExists(notepad, testString));
x.winClose(notepad, testString);
x.winWaitActive("Notepad");
x.send("{ALT}n");
Assert.assertFalse(x.winExists(notepad, testString));

play DRM content in chrome driver

I'm writing some selenium tests for a HTML5 player playing DRM content, the player works fine in Chrome when I test it manually, but nothing is loaded or played in the latest chrome driver if I run my test cases.
Is it because of the drm content isn't authorized to play in chrome driver or something else?
I have no issues running tests for other functions written in selenium.
Any ideas?
Chromedriver launches Chrome with --disable-component-update switch by default, which disables the NaCl (Native Client) support, which is in turn required to load DRM modules (e.g. Widevine Modular DRM).
To get around this, you need to tell the driver not to launch Chrome with this switch, by building the driver with excludeSwitches option, specifying disable-component-update parameter. For example (JS):
var webdriver = require('selenium-webdriver');
var chrome = require("selenium-webdriver/chrome");
var capabilities = new webdriver.Capabilities.chrome();
var chromeOptions = {
'args': ['--user-data-dir=C:/ChromeProfile'], // start with pre-configured Chrome profile
'excludeSwitches': ['disable-component-update'] // stop breaking Native Client support
};
capabilities.set('chromeOptions', chromeOptions);
var driver = new webdriver.Builder().
withCapabilities(capabilities).
build();
driver.get('http://...');
Or using Python bindings:
from selenium import webdriver
def buildDriver():
options = webdriver.ChromeOptions()
options.add_experimental_option('excludeSwitches', ['disable-component-update'])
options.add_argument('--user-data-dir=C:/Temp/ChromeProfile')
return webdriver.Chrome(chrome_options=options)
Hope that helps..
-- ab1
Issue 886: Enabled PNaCl Components in ChromeDriver - Enhancement
If you cannot get #Chainik's answer to work, try this out. It worked for me.
As per https://bugs.chromium.org/p/chromedriver/issues/detail?id=1140 you can work around this issue by doing a few things.
manually start chrome from terminal/command prompt with these command line arguments --
google-chrome --user-data-dir=/path/to/any/custom/directory/home/user/Desktop/Chromedir --profile-directory="Profile 1" --remote-debugging-port=7878
make sure "Profile 1" is already existing in the same --user-data-dir (make usre Profile 1 has necessary chrome://components/ to run Netflix when launched manually)
you can use any free port in place of 7878
verify that http://localhost:7878 is running and returns value.
now connect to the remote-debugging-port=7878 via chromedriver with code below
Verify chrome://components/
I put mine into a .bat file, but you could do the same for a bash script or whatever:
C:/Program Files (x86)/Google/Chrome/Application/chrome.exe --user-data=c:/temp/chromeprofile --profile-directory="Profile 1" --remote-debugging-port=7878
Then set the debugger address in your code to use the browser:
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
cr_options = Options()
# This line is where the "magic" happens.
cr_options.add_experimental_option('debuggerAddress','127.0.0.1:7878')
browser = webdriver.Chrome(chrome_options=cr_options)
browser.get('https://www.google.com')
browser.get('chrome://components/')
I'm post a java version of Chainik's answer as a reference for those using Java, please let me know if there's anything wrong.
ChromeOptions options = new ChromeOptions();
List<String> list = new ArrayList<String>();
list.add("disable-component-update");
options.setExperimentalOption("excludeSwitches", list);
options.addArguments("user-data-dir=/Users/myname/Library/Application Support/Google/Chrome/Default");
java.lang.System.setProperty("webdriver.chrome.driver","/usr/bin/chromedriver");
Webdriver driver = new ChromeDriver(options);
Here is an article about chromedriver capabilities and options.
This is late but might help someone else. I was able to get around this and play videos by not using a headless browser.
In Python,
options = Options()
options.headless = False
webdriver.Chrome(executable_path='path/to/chromedriver', options=options)

Accept permission request in chrome using selenium

I have a HTML/Javascript file with google's web speech api and I'm doing testing using selenium, however everytime I enter the site the browser requests permission to use my microphone and I have to click on 'ALLOW'.
How do I make selenium click on ALLOW automatically ?
Wrestled with this quite a bit myself.
The easiest way to do this is to avoid getting the permission prompt is to add --use-fake-ui-for-media-stream to your browser switches.
Here's some shamelessly modified code from #ExperimentsWithCode's answer:
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
chrome_options = Options()
chrome_options.add_argument("--use-fake-ui-for-media-stream")
driver = webdriver.Chrome(executable_path="path/to/chromedriver", chrome_options=chrome_options)
#ExperimentsWithCode
Thank you for your answer again, I have spent almost the whole day today trying to figure out how to do this and I've also tried your suggestion where you add that flag --disable-user-media-security to chrome, unfortunately it didn't work for me.
However I thought of a really simple solution:
To automatically click on Allow all I have to do is press TAB key three times and then press enter. And so I have written the program to do that automatically and it WORKS !!!
The first TAB pressed when my html page opens directs me to my input box, the second to the address bar and the third on the ALLOW button, then the Enter button is pressed.
The python program uses selenium as well as PyWin32 bindings.
Thank you for taking your time and trying to help me it is much appreciated.
So I just ran into another question asking about disabling a different prompt box. It seems there may be a way for you to accomplish your goal.
This page lists options for starting chrome. One of the options is
--disable-user-media-security
"Disables some security measures when accessing user media devices like webcams and microphones, especially on non-HTTPS pages"
So maybe this will work for you:
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
chrome_options = Options()
chrome_options.add_argument("--disable-user-media-security=true")
driver = webdriver.Chrome(executable_path="path/to/chromedriver", chrome_options=chrome_options)
Beware of Mohana Latha's answer for JAVA!
The code is only pressing the buttons and NEVER releasing them. This will bring bunch of issues later on.
Use this instead:
// opening new window
Robot robot;
try {
robot = new Robot();
robot.keyPress(KeyEvent.VK_CONTROL);
robot.delay(100);
robot.keyPress(KeyEvent.VK_N);
robot.delay(100);
robot.keyRelease(KeyEvent.VK_N);
robot.delay(100);
robot.keyRelease(KeyEvent.VK_CONTROL);
robot.delay(100);
} catch (AWTException e) {
log.error("Failed to press buttons: " + e.getMessage());
}
Building on the answer from #Shady Programmer.
I tried to send Tab keys with selenium in order to focus on the popup, but as reported by others it didn't work in Linux. Therefore, instead of using selenium keys, I use xdotool command from python :
def send_key(winid, key):
xdotool_args = ['xdotool', 'windowactivate', '--sync', winid, 'key', key]
subprocess.check_output(xdotool_args)
which for Firefox, gives the following approximate sequence :
# Focusing on permissions popup icon
for i in range(6):
time.sleep(0.1)
send_key(win_info['winid'], 'Tab')
# Enter permissions popup
time.sleep(0.1)
send_key(win_info['winid'], 'space')
# Focus on "accept" button
for i in range(3):
time.sleep(0.1)
send_key(win_info['winid'], 'Tab')
# Press "accept"
send_key(win_info['winid'], 'a')
[Java]: Yes there is a simple technique to click on Allow button using Robot-java.awt
public void allowGEOLocationCapture(){
Robot robot = null;
try {
robot = new Robot();
robot.keyPress(KeyEvent.VK_TAB);
robot.keyPress(KeyEvent.VK_ENTER);
robot.delay(600);
} catch (AWTException e) {
getLogger().info(e);
}
}
You can allow using add_experimental_option as shown below.
from selenium.webdriver.chrome.options import Options
chrome_options = Options()
chrome_options.add_experimental_option('prefs',{'profile.default_content_setting_values.notifications':1})
driver = webdriver.Chrome(chrome_options=chrome_options)
Do it
For android chrome it really work!
adb -s emulator-5554 push <YOU_COMPUTER_PATH_FOLDER>/com.android.chrome_preferences.xml /data/data/com.android.chrome/shared_prefs/com.android.chrome_preferences.xml
File config here https://yadi.sk/d/ubAxmWsN5RQ3HA
Chrome 80 x86
or you can save the settings file after ticking the box with your hands, in adb its "pull" - command