Automated web testing generally has problems testing sites using Windows Integrated Authentication. This is because the nature of integrated auth is to supply the credentials of the logged-on user – which in the general case is going to be the user running the tests. This may work in some cases, but at the very least it’s likely you want to test using both an admin and non-admin user. This can be done with Selenium, but requires some work to get it set up (I’m assuming we’re using Selenium Server here).
The goal here is to get the browser running as a specific user (I’m not aware of a way to make the browser authenticate using other credentials). The problem is that your browser is spawned by the Selenium Server, so naturally inherits the logon credentials which started the server. Therefore there are two possible paths to take here – fool Selenium into starting the browser under another user or start Selenium itself under another user. I picked the latter option, although I expect it would be possible to do the former (possibly by replacing the browser executable with a custom script before each test?).
Selenium is fairly quick to start up – certainly in comparison to the speed at which it executes tests, so can be started at the beginning of each test without too much impact on overall testing time. (It would also be possible to maintain state and only respawn if the user changes – but this may not be simple to close on the final test – is there a hook for this?) For our testing (which tests using integrated auth), all Selenium tests create their own Selenium Server instance in a SetUp() method from a base test class (note that the tests are C#/NUnit), and close it in the TearDown() method. The C# code is below which uses the .NET API to start the process under another user – this would be marginally more complex in Java, but could be achieved by invoking the runas command to spawn Selenium.

public class SeleniumContainer
{
private readonly Process process = new Process();
private bool started;
public SeleniumContainer(bool asAdmin)
{
process.StartInfo.FileName = “java”;
process.StartInfo.Arguments = “-jar lib/selenium-server.jar”;
process.StartInfo.CreateNoWindow = false;
process.StartInfo.WindowStyle = ProcessWindowStyle.Normal;
process.StartInfo.UseShellExecute = false;
string[] domainAndUser = Config[asAdmin ? ConfigProps.AdminUser : ConfigProps.NonAdminUser].Split(”);
string password = Config[asAdmin ? ConfigProps.AdminPassword : ConfigProps.NonAdminPassword];
process.StartInfo.UserName = domainAndUser[1];
SecureString pw = new SecureString();
foreach (char c in password)
pw.AppendChar(c);
process.StartInfo.Password = pw;
DirectoryInfo currentDir = new DirectoryInfo(Environment.CurrentDirectory);
process.StartInfo.WorkingDirectory = currentDir.Parent.Parent.Parent.Parent.FullName;
if (Config.Exists(ConfigProps.SeleniumFirefoxProfile))
{
process.StartInfo.Arguments += (” -firefoxProfileTemplate ” + Config[ConfigProps.SeleniumFirefoxProfile]);
}
}
public void Start()
{
lock (this)
{
if (started)
throw new InvalidOperationException(“Selenium already started”);
if (!process.Start())
throw new Exception(“Failed to start Selenium process”);
started = true;
}
//give it half a second to start up
Thread.Sleep(500);
}
public void Stop()
{
lock (this)
{
if (!started)
throw new InvalidOperationException(“Selenium not running”);
try
{
process.CloseMainWindow();
}
catch
{
//Ignore
}
//give Selenium 5sec to close before we kill it
if (!process.WaitForExit(5000))
process.Kill();
started = false;
}
}
}

Testing using Firefox
Firefox in general does not send integrated auth credentials, but can be told to. To do this go to the firefox about:config screen and search for ntlm – there should be three options, two of which need changing.
network.ntlm.send-lm-response: enable this (set to true)
network.automatic-ntlm-auth.trusted-uris: set this to a string representing your host (it’s a URL pattern)
Once this is working for firefox you will need to save the profile directory and pass it to Selenium when it starts so that it can use your modified firefox profile (by default it uses it’s own). This is done using the -firefoxProfileTemplate parameter, as you can see in the above code. Oh, and you’ll need at least version 1.0-beta-2 of Selenium if you want to use firefox 3.

Fresh ideas, announcements, and inspiration for your team, delivered weekly.

Subscribe now

Fresh ideas, announcements, and inspiration for your team, delivered weekly.

Subscribe now