Distributed Testing with Selenium & Docker Containers (Part I)

As seen at TechCrunch Disrupt, the UnifyID Google Chrome extension plays a prominent place in the user’s first impression with the product. As such, it is critical that the experience be smooth, user-friendly, and most important, reliable. In minute 2:10 of the demo, the Amazon login fields are replaced with the UnifyID 1-click login. This requires DOM (document object model) manipulation on the web page which isn’t challenging on a single website; however, when scaling your code across sites in multiple languages and formats, finding the right login form and place to insert our logic is challenging.

How to find the right elements in here?
How to find the right elements in here and generalize well?

Parsing through the noise of variations on HTML structures, CSS naming conventions, and general web development is like the wild west–but despite this, there are ways to gain sanity, namely in testing.

As most UIs are tested, we utilize Selenium and its Javascript binding. For developers who have had some experience with Selenium, it becomes painfully obvious very early on that speed is not its forte. The testing environment must handle testing functionality across dozens, hundreds, and thousands of sites while maintaining the fast, iterative nature of development. If every test case takes an hour to finish, then our continuous integration would lose its magical properties (you know, moving fast without breaking things).

Surfing at speed through the codebase.
Surfing at speed through the codebase, knowing everything will be ok.

The solution to distribute testing across multiple computers will require the following:

  1. Must run multiple instances of the tests with the same code but on different websites.
  2. Must run all of the tests in parallel.
  3. Must collect all results.

In order to simplify my work, I discovered that Selenium has this neat feature called Selenium Grid that allows you to control testing in a remote machine so that the local machine doesn’t have to run the tests itself. You just run the grid in another machine, expose the port, and remote connect to that port by using settings found in your chromedriver.

This was amazing! This meant that we could have machines entirely dedicated to running a bunch of Selenium webdrivers (which are considerably RAM consuming) without killing our CI server. Plus, we could easily scale by just spawning more of these machines and more of these web drivers.

Finally!
Finally! Scalability!

As a result, the design evolved to this:

  1. Set up a Selenium server to run a grid of browsers. Run Chrome.
    1. Package under a Docker image for easy deployment.
    2. Run under an Amazon AWS instance for easy scaling.
  2. The CI server has to be able to send requests to the Grid.
  3. The tests have to run in parallel.
    1. Create a Javascript library to make tests into chunks that can be sent over to the server.
  4. Finally, the results have to be merged together and sent back to the CI server.

For 1, I downloaded selenium-server-standalone-2.53.1.jar from “http://selenium-release.storage.googleapis.com/index.html?path=2.53/” and saved as selenium-server-standalone.jar.

Run hub with:

java -jar selenium-server-standalone.jar\
-role hub

Run node with:

java -jar selenium-server-standalone.jar -role node\
-hub http://localhost:4444/grid/register\
-browser browserName=chrome,version=52.0,\
          chrome_binary='/usr/bin/google-chrome',\
          platform=LINUX,\
          maxInstances=5

Now to connect to the grid, we can run from JavaScript:

Look out for my next post which will delve deeper into parts 2, 3, and 4 above.

Thanks for Hacking!

Interning At UnifyID

As spring semester at Purdue was ending and college was winding down, many of my friends in the computer science program were getting ready for their summer internships. Most of them were at big name companies, and people already had their mentors and projects assigned. My desire to start a company in the future and make a strong impact during the summer led me down a different path. I decided to intern at a startup, one with less than 10 employees, where I hadn’t heard of the product before I applied for the job. The only thing I knew was that this startup, UnifyID, was working on a technology that I believed was the future and really wanted to be a part of.

The first day I got to the office, I knew that I was definitely in for a great summer. I met my mentor (the CEO), a PhD and Stanford Professor and the head Machine Learning Engineer, a dual PhD from Carnegie Mellon. Rather than having to sit through a long orientation, I was told to look through the codebase and made a contribution on the first day! This trend continued throughout the summer, as I was involved in a lot of the product architecture discussions and everything I did went into production.

Some of the interesting projects I got to work on included creating and managing a Cassandra cluster, working with OpenCV for Facial Recognition, and lots of data collection! I also implemented security protocols, registration/login flow and challenge flows. On the non-technical side, I learned a lot about day-to-day company operations, investor relations, hiring teammates, product design, the road to TechCrunch Disrupt Runner-up, and the importance of building great company culture.

Photo by Oren Haskins

The culture at UnifyID is brimming with hard-working, qualified, and interesting people. Everyone understands the startup grind, truly believes in the product, and knows that hard work is the only thing stopping UnifyID from becoming a huge success. Daily news reaffirms how terrible passwords are, and there is a really good chance that they will be replaced, the question is–who is going to build the best solution to do this? After my experience, I am very confident that the team at UnifyID is the right one to solve the problem.

Overall, my decision to work at UnifyID turned out to be an excellent one. I liked it so much that I still work part-time, during college. No where else would I have gotten to work on changing the future of authentication, to sit right next to the COO, or to work directly under a Stanford professor as an undergraduate intern. I also wouldn’t have been able to have discussions with so many highly qualified engineers about state of the art security or machine learning, and then proceed to implement them.

We are hiring and located a few steps away from the ballpark in SoMa, San Francisco!