Deploy and Test Your App using VSTS, Azure, and Ghost Inspector

Ghost Inspector is an automated web testing tool that helps QA testers and engineers to easily build, edit, and run low-code/no-code web tests. Start a free trial.
Deploy and Test Your App using VSTS, Azure, and Ghost Inspector

Visual Studio Team Services is a one-stop-shop for managing source code, custom packages, agile workflow, and continuous integration. Having recently released our VSTS extension for Ghost Inspector I thought it would be a fun idea to test and deploy an app with a Microsoft toolchain, namely Visual Studio Team Services, Microsoft Azure, and Ghost Inspector using our new extension.

Getting started

We are going to need a few things before we get started, so we may as well do that now:

Our node app

Before we get into any of the infrastructure configuration, let’s take a quick look at our sample application. If you don’t have an existing application you can use our demo app on GitHub to get you started.

The HTML under test

The HTML structure of this app is pretty basic, and will be easy to test against:

<!DOCTYPE html>
<html>
  <head>
    <title>Express</title>
    <link rel="stylesheet" href="/stylesheets/style.css" />
  </head>

  <body>
    <h1>Express</h1>
    <p>Welcome to Express</p>
  </body>
</html>

This output is just the main view from a basic boilerplate Express app created with the Express generator, however, in order to run this as a Web App on Azure, we are going to need to modify a few things.

Boilerplate modifications

First, double-check your package.json has version 2.0.3 of pug or newer, earlier versions don’t seem to install well on Windows.

My package.json looks like this:

{
  "name": "azure-demo-app",
  "version": "0.0.1",
  "private": true,
  "scripts": {
    "start": "node serve.js"
  },
  "engines": {
    "node": "8.x"
  },
  "dependencies": {
    "body-parser": "~1.13.2",
    "cookie-parser": "~1.3.5",
    "debug": "~2.2.0",
    "express": "~4.13.1",
    "morgan": "~1.6.1",
    "pug": "2.0.3",
    "serve-favicon": "~2.3.0"
  }
}

Next, we’re going to need to move one of the files in our boilerplate application. Typically we would serve our application from ./bin/www, however the bin namespace is reserved in Azure and we won’t be able to access it for our webserver, so I’ve actually copied the file to serve.js and placed it in the root of my project.

I’ve also made one code change for it to work from the new location, I’ve changed line 7 from this:

var app = require('../app')

to this:

var app = require('./app')

This change just makes sure our relocated serve.js can find our app.js which is the heart of our application.

Azure Node.js configuration

Last, we are going to need a specific file to tell Azure how to run our application. We need to place a new XML file in the root of our project called web.config that will look like this:

<configuration>
  <system.webServer>
        <handlers>
          <!-- indicates that the file is a node.js application to be handled by the
            iisnode module -->
          <add name="iisnode" path="serve.js" verb="*" modules="iisnode"/>
        </handlers>
        <rewrite>
          <rules>

            <!-- First we consider whether the incoming URL matches a physical file in
              the /public folder -->
            <rule name="StaticContent">
              <action type="Rewrite" url="public{REQUEST_URI}"/>
            </rule>

            <!-- All other URLs are mapped to the Node.js application entry point -->
            <rule name="DynamicContent">
              <conditions>
                <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="True"/>
              </conditions>
              <action type="Rewrite" url="serve.js"/>
            </rule>

          </rules>
        </rewrite>
  </system.webServer>
</configuration>

This is going to instruct our Web Apps server (IIS) that we are a Node.js app and also instruct the server how it can find dynamic content like images and style sheets.

With those changes in place, we’re ready to take a look at our Ghost Inspector test suite.

Our test suite

Back in my Ghost Inspector account I’ve created a new test suite called Test Azure demo app and then created a single test called Test my app. The test consists of 2 steps:

  1. Test that the h1 element contains the text “Express”.
  2. Test that the p element contains the text “Welcome to Express”.

Our application test

It’s pretty simple (and maybe a little contrived) but it should work for now. Let’s move on to some infrastructure.

Setting up Azure

Azure is a cloud platform from Microsoft, similar to Amazon Web Services or Rackspace Cloud. Platforms like this give us the ability to develop and deploy new resources in minutes with a few clicks of a button. In order to get started we will want to set up our first Web App resource

Web Apps

Web Apps are one of the quickest ways to get up and running in Azure; they give use all the boilerplate we need to start our application.

To provision our first Web App, click + Create a resource and then type “node” in the search box and hit Enter. If we scroll down the list a little bit we should see “Node JS Empty Web App”, select that option and hit Create.

Create an empty Node.js app

Web Apps get a namespace on the azurewebsites.net so we will have to give our app a unique name, I’ll use “my-azure-demo-app”. I’ll select my subscription as well as my Resource Group. If you do not have a Resource Group already, go ahead and create one that is the same name as your app. Resource Groups are how costs are tracked in Azure, so if we delete the app down the road, we will delete the Resource Group as well to stop incurring charges. Since you’re probably on the Free Trial, it should be fine for now.

I’ll also select Pin to Dashboard so I get a handy shortcut to my new app. I’ll click Create and we can watch the progress as the new app is deployed.

Create our web app resource

Before we move on to our CI configuration, we’ll need to tweak two more setting for our Application to run in Azure. Go to Application settings and modify the following:

  • Application settings: we need to add an entry to tell Azure what version of Node.js we want to run, enter a key of WEBSITE_NODE_DEFAULT_VERSION and a value of 8.9.4 (currently LTS).
  • Default documents: remove all the extra entries and add a single entry of serve.js, the entrypoint of our application.

Don’t forget to hit Save.

Configure our default document in Azure

Visual Studio Team Services

If you haven’t already, let’s get your application source code committed and pushed up to your favorite repo provider and then we’ll tie into VSTS.

Our first project

One of the nice features of having a Microsoft Account is that you can access the majority of their products using the same account. Head on over to the VSTS home page and sign in with your Microsoft account. We will be prompted to create a VSTS account as soon as we’re signed in.

Create a new account in Visual Studio Team Services

Next you’ll need to pick a unique name for our project (I’ll use azure-demo-app) and set Manage code using to git, assuming you’re using Github. If you wish, change the location where your projects will be hosted.

Set up a new Project in VSTS

Setting up the build definition

With a brand new project, we need to set up our first Build Definition. This is basically the set of actions that will comprise our application’s build, test, and deploy steps.

To do that, go to Build and Release > Builds and click on + New definition. By default VSTS Git will be selected as our SCM provider, but I am going to select External Git since I am using Github. Next I’ll need to add Github as a Service in VSTS, so I’ll click Add Connection and paste in the URL of my repository. Because my repo is public I don’t need any credentials to access it, but if you are using a private repository, you will need to enter them now. Click Okay and then Continue. Next we’ll be asked to select a template for our build, however I will simple select Empty process to continue.

Set up a new build defintion in VSTS

Adding build steps

With the build definition created, we now need to add some build steps. We can see at the top of our Task list a new task phase called Phase 1. Let’s click the + icon to bring up a list of available tasks.

Archive the application files

Before we can deploy to Azure, we need to zip up our app files. At the top of the process list we can see we already have a source code checkout step, so let’s bundle things up for deployment. In the search box on the right, let’s search for the Archive extension and add it.

Configuring our archive task

Let’s take a look at our options:

  • Display name: Set this to whatever you wish the step to appear like in the task list on the left. I’ll use Archive azure-demo-app.
  • Root folder or file to archive: This is what we are archiving. I want the entire application so I’m going to use .. If your app was inside a build directory or something like that you could change this value. I’m also going to uncheck “Prepend root folder name to archive paths”, I don’t want any additional folder structure in my archive.
  • Archive type: This should be zip.
  • Archive file to create: This is the name of our zip file, I’m going to use azure-demo-app.zip.

The rest of the options I will leave as is.

Deploy to Azure task

Now we can move on to our deploy step. Let’s click the + again on the left and type Azure App in the search. Next add the task Azure App Service Deploy.

Add the Azure App Service Deploy task

Here’s our configuration breakdown:

  • Display name: Set this to whatever you wish the step to appear like in the task list on the left. I’ll use Deploy azure-demo-app.
  • Azure subscription: If you are still logged into Azure you should be able to elect the subscription you set up earlier with Azure and then click Authorize. You will be walked through the process of connecting your Azure account.
  • App type: Select Web App.
  • App Service name: This is the App Registration that we set up when we were setting things up in Azure. Select your application from the dropdown, in my case it is azure-demo-app. If you don’t see your app listed, you may need to hit the refresh button on the right.
  • Virtual application: Change this to / to coincide with the root application in Azure.
  • Package or folder: change this to our zip file, azure-demo-app.zip.
  • Virtual application: Change this to / to coincide with the root application in Azure.
  • Post Deployment Action: Change this to Inline Script and then change the script to: npm install . This will be executed on the Azure instance after the code has been transferred.
  • Output: The App Service Deploy extension has one single output variable which is the URL of the deployed application. Let’s put myAppUrl in the App Service URL box, which we will use in just a minute.

I will leave the rest of the config alone and move on.

Ghost Inspector VSTS extension

We’re getting close! This is the last little bit of configuration we need before we run our build. Click the + on the left one more time to add another step. This time we will search for ghost. If you haven’t added it already, you’ll see our VSTS extension under Marketplace. Click on the Get it free button and walk through the process of installing it into your VSTS environment.

Install the Ghost Inspector extension for VSTS

With our extension installed, we just need to add a bit of configuration:

  • Display name: Again, change this to whatever you like.
  • Suite ID: This is the Ghost Inspector test suite ID you’d like to run against your application.
  • API Key: Your Ghost Inspector API key from your account.
  • Advanced > Start URL: We will set this to the output of the last task, $(myAppUrl), this will execute the suite with a startUrl of our deployed Azure app.

I don’t have any additional parameters to send off to my test, so I’m finished with this config.

Configure the Ghost Inspector extension in VSTS

With that we’ll click Save & queue, select Hosted and then Save & queue. We should see a green confirmation bar at the top with a link to our build job where we can view the logs. Let’s go there now.

The build output

Now our job is queued and should be picked up by the next free agent. If you clicked through to the build job output, we should see the output in the panel on the right. This is where we will receive any errors or messages that might be necessary for debugging our build. With any luck all the little checkboxes will turn green and we can go check out our new app!

The VSTS build logs

It looks like our first build passed!

Checking our test suite

Just for good measure I’ll go back and check on my test suite to see that it grabbed what was expected from the application:

Our Ghost Inspector test has passed!

And there we go! We have successfully created a Node.js application, deployed it to Azure, and tested it using Ghost Inspector and Visual Studio Team Services build!

Troubleshooting and tips

This has been a pretty involved look at some advanced tools, if you run into trouble along the way, there are a couple things you can try to find out what’s wrong:

  • Check the logs – application logging is not enabled by default in Azure, to enabled logging for your app, go to Diagnostic logs and set Application Logging to On. You will then see a log stream under Log stream, and errors will appear when you visit your application in the browser. This can be helpful when diagnosing cryptic HTTP responses.
  • Check the Console – though a bit limited in functionality, there is enough features in the Azure application console to try a few things. Go to Console and once the terminal comes up, you can try npm install . or node serve.js to see if there are any errors with your application. Also double-check that the proper version of Node is being run with node --version, if everything is set up properly, it should be 8.9.4 (or whatever version you’re using).
  • NPM errors / permissions issues – I did run into a couple scenarios where I had changed a dependency in package.json and I would get an error like Error: npm ERR! path D:\home\site\wwwroot\node_modules\.staging or something similar in the log stream. Azure doesn’t give you permissions to the node_modules folder, so I found that I could fix the problem by going to Application Settings > Application Settings, changing the version of Node.js under WEBSITE_NODE_DEFAULT_VERSION to something different, Save, and then change it back and Save again. Although I couldn’t find an official reference to support this, my theory is that the node_modules folder gets wiped out if you specify a new version of Node.js in the Azure Application Settings.

Wrapping up

That wraps up our post for today, we definitely hope this is helpful to you down the road should you happen to be trying to connect these services together, or just get Ghost Inspector integrated into your VSTS build.

As always, should you run into any issues along the way, feel free to reach out to our support team and we’ll be happy to assist you on your way.

Happy Ghosting!