Creating Maintainable Selenium Tests for Angular Apps Using C#

Creating Maintainable Selenium Tests for Angular Apps Using C#

Recently our team decided that we needed to implement some end-to-end testing for our Angular application. We could have used protractor and stayed more in that stack but we also have a backend team that uses .NET. In the end, I decided to tackle this task personally and started to look at selenium. More specifically I decided to look at the Selenium IDE Chrome extension. It's a great tool that you can use to record your activity on the page and then export c# scripts (or you can just use that tool to do everything if you are not a programmer). This really intrigued me since as many of you know, I am a big fan of .NET core and specifically c#.

5 Tips for Working with Selenium IDE and Angular with Material

  1. I would recommend not over-thinking it so just start Selenium IDE and record whatever actions you want to automate.
  2. Once you have the actions then I would go back through and fine-tune those actions by specifying the most stable xpath or CSS that you can use to consistently click on or enter the data.
  3. I used another Chrome extension called ChroPath to give me more xpath options to choose from in my scripts. I highly recommend you get this extension.
  4. For our angular app I focused on always targeting the formcontrolname attribute as that should be stable versus the dynamic HTML ID's that our app generates.
  5. Because I am using c# I tended to assert element not present and look for css=.error. Because if the error class is present on the page, that means we have a problem.

One of the other commands that I found useful in Selenium IDE was pause (it does what you think it does) and turns into a thread.sleep() in the exported c# code. That's important to give your angular app enough time to process the prior automated action.

Okay so great, I now had a good grasp on the tool and was ready to start tackling the first of our angular apps. However, I did not want to record huge scripts that would need to be changed every time we made a change to the application. So I decided to treat testing pretty much the same way we develop everything else and I created component test scripts (that's just what I called them). Basically I recorded small actions like login, logout, create an account, edit an account, and delete an account. I then exported these small scripts to c# using the export functionality built into Selenium IDE.

I then decided to create an application that would execute these scripts dynamically. So I decided that I would use CS-Script. Okay, this seemed perfect! I could create the component scripts using Selenium IDE and then execute them on the fly using CS-Script, what could be difficult about that? Famous. Last. Words. One fairly common rule in programming is that things are usually more complicated than you originally think they are going to be.

5 Issues I Encountered with Interpreting the Selenium IDE c# Exports

  1. Remember that pause command I liked so much earlier in this article? Yeah, well when you export that it creates an invalid try/catch around the thread.sleep() that has to be fixed for the script to be executed by CS-Script. So I needed to parse the scripts before executing them dynamically.
  2. I needed to be able to generate unique and valid GUID's to be used for things like emails and other dynamic data. Because I wanted to use those for emails they had to be alphanumeric only GUID's. So before the script gets executed I do a token replace on ${guid} and insert the alphanumeric guids. I also created a JSON file that contains other token/replace values like ${baseurl} and other key/value pairs.
  3. I also needed to extract just the automation portions of each of the scripts that Selenium IDE exported and I wanted to be able to call the components multiple times in the same session so I had to randomize the method names. So a bit more parsing of the exported scripts was required and I put that alaphnumeric guid to use again on the dynamic method names and just prefaced them with the word "code" to make sure they were valid method names.
  4. I also needed a way to tell CS-Script what sequence to execute the component scripts in so I could do things like create an account, edit an account, and delete an account. So I created a JSON structure that the interpreter would read and then sequence the component scripts properly. I called these "Chains" in my application.
  5. Finally, I needed to inject the assemblies that my chains were going to need into the environment before CS-Script could execute them properly. So I used a bit of dynamic assembly loading code to make that happen.

Now, as I am writing this I am beginning to realize that this all sounds incredibly cumbersome and exceptionally over-engineered. After all you can just use selenium grid or other products to execute scripts, etc. Right?

Well ... the interesting part about all of this is that everything executes in one ChromeDriver session. So I went through this long process just to make it possible for me to use component scripts, chained together, and all executing in one session so that it better mimicked a real user of our angular application.

The good news is now when a change is made to our login process or create account process I can simply update the component in one place and every "chain" that uses that component will automatically be updated. It's much more maintainable than just using Selenium IDE by itself to build and execute tests. In the end that was what it was all about. I wanted a reliable framework for creating and executing end-to-end tests of our angular application that wouldn't be a pain to maintain. That's the long story about how I created maintainable selenium tests for our angular app using c#.


Sanjay Kumar

Founder & Creator of SelectorsHub | Testing Daily | TestCase Studio | TestCaseHub | AutoTestData | ChroPath | 160K+ Youtube Subs

3 年

Hi Ken Myers, ChroPath Creator here. I have stopped development and support on ChroPath. Please try my new super advanced xpath tool SelectorsHub. https://selectorshub.com/

回复

Hi Ken: Thanks for sharing this. This is very helpful. I will connect with you to get some more details.

Kenneth Myers

Tech Executive - Improving Lives through Technology

4 年

I always forget to mention that this is using NUnit as well for the asserts

回复

要查看或添加评论,请登录

社区洞察

其他会员也浏览了