Skip to content
GitHub Copilot is now available for free. Learn more

Coding peace of mind: A guide to testing

Say goodbye to accidentally deleted data and faulty committed changes with this GItHub Actions framework.

Artwork: Susan Haejin Lee

Photo of Chrissy LeMaire
dbatools logo

Chrissy LeMaire // Automation Engineer, dbatools

The ReadME Project amplifies the voices of the open source community: the maintainers, developers, and teams whose contributions move the world forward every day.

There are so many different ways to use GitHub Actions it can be hard to decide where to start. You can automate tasks like documentation updates and compatibility checks, schedule tweets to announce new builds, or run a whole range of different tests—just to name a few use cases.

Testing is a great place to start, especially for DBAs (Database Administors), because testing can help us sleep better at night, knowing that all committed code changes will work as expected and not unexpectedly delete data.


In this Guide you will learn:

How to use GitHub Actions to test an SQL Server deployment on a Linux container. In the code section of this article, you will use a Linux container to setup and run an SQL database in order to test new code that is pushed to your repository.


Actions make testing SQL Server accessible and easy, especially if you're using PowerShell, which is built into each of the runners along with its popular testing framework, Pester.

GitHub runners are especially SQL Server-friendly and come with a number of built-in SQL Server tools, as seen in the table below.

Nine SQL server tools found in GitHub runners, their OS system, and its details

Testing against SQL Server

SQL Server professionals may see some similarities between Actions tasks and tasks accomplished by SQL triggers or SQL Server Agent and Windows Task Scheduler. Actions run in Windows, Ubuntu, and macOS virtual machines are called runners. And all of this happens entirely in one place: your GitHub repository (repo).

You can use runners to install SQL Server containers with each commit. 🤯 This is useful for tasks like:

While testing can be performed in nearly every language, this article will focus on PowerShell. PowerShell can also be used to launch alternative testing frameworks such as tSQLt

The code

In the code below, the following steps will be performed each time a change is pushed to the repository

To get started:

  • Download and run the SQL Server on a Linux container. TIP: Set the SA Password to: Admin123, and expose the default SQL Server port, 1433.

  • Install dbatools from the PowerShell gallery

  • Connect to the container, including these steps: Listing the current databases; Creating a new database; executing a query that creates a new table; and confirming that a new table exists using dbatools.

Then, copy and paste the block below and save it as a .yml file (I named mine main.yml) in the directory .github\workflows within the root directory of your repository.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
name: Actions Workflow
on: [push]
jobs:
  run-sql:
    runs-on: ubuntu-latest
    steps:
      - name: 🐋 Startup Container
        shell: bash
        run: |
          # In this scenario with a fresh container used for testing,
          # it is acceptable to use a plain-text password
          docker run -e "ACCEPT_EULA=Y" -e "SA_PASSWORD=Admin123" \
          -p 1433:1433 -d mcr.microsoft.com/mssql/server:2019-latest
      - name: 🚀 Install required PowerShell module
        uses: potatoqualitee/psmodulecache@v4.5
        with:
          modules-to-cache: dbatools
      - name: 🛢️ Get all databases, create new database, execute query
        shell: pwsh
        run: |
          # Create a PowerShell credential object that can login to the container
          $password = ConvertTo-SecureString Admin123 -AsPlainText -Force
          $cred = New-Object System.Management.Automation.PSCredential("sa", $password)
          # View available databases
          Get-DbaDatabase -SqlInstance localhost -SqlCredential $cred
          # Create new objects and perform queries
          New-DbaDatabase -SqlInstance localhost -SqlCredential $cred -Name testdb
          $sql = "CREATE table test (id int, artist nvarchar(50))"
          Invoke-DbaQuery -SqlInstance localhost -SqlCredential $cred -Database testdb -Query $sql
          Get-DbaDbTable -SqlInstance localhost -SqlCredential $cred -Database testdb

Push the file to your repository then click on the Actions tab on GitHub to watch the workflow run.

Inline2_eGuide_dbatools

Prefer to use native SQL Server tools such as sqlcmd and bcp? Linux and Windows runners include mssql tools by default!

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
name: Actions Workflow
on: [push]
jobs:
  run-sql:
    # Use an explicit version of ubuntu, as it will be referenced below
    runs-on: ubuntu-18.04
    steps:
      - name: 🐋 Startup Container
        run: |
          # In this scenario with a fresh container used for testing,
          # it is acceptable to use a plain-text password
          docker run -e "ACCEPT_EULA=Y" -e "SA_PASSWORD=Admin123" \
          -p 1433:1433 -d mcr.microsoft.com/mssql/server:2019-latest
      
      - name: 🛢️ Query the server to see the server version
        run: |
          # Give the container a moment to startup
          sleep 5
          # Execute SQL a query
          /opt/mssql-tools/bin/sqlcmd -S localhost -U sa -P Admin123 -q "SELECT @@VERSION"

The two examples provided run the workflows with every push to GitHub by using on: [push], but there are currently 30 different events that can initiate a workflow. Check out GitHub's documentation on events that trigger workflows for more information.

Usage limitations

While the usage allotment is generous, there is a limit to the number of free minutes you can use per month. Per GitHub's documentation:

A table displaying the number of free minutes you can use on each GitHub product, each month, including Free, Pro, GitHub Free for organizations, GitHub Team, and GitHub Enterprise Cloud.

Have a private repository and need more minutes? You can implement act , which allows you to execute runners locally.

Next steps

There’s plenty more you can do with this powerful and flexible tool. To dive right into using GitHub Actions for your SQL Server projects, you can:

  • Create a SQL Server-centric PowerShell module, complete with a build process and integration tests against a live SQL Server container. Once the module is built and tested, publish it to the PowerShell Gallery.

  • Gather data using an API or screenscraper, import the results into a SQL Server container then export the results to a DACPAC and save it as an artifact to your workflow runs.

  • Write T-SQL queries and test to ensure the syntax is valid using tSQLt.

 If you have any questions, I'm @cl on Twitter, feel free to reach out there or in the comments below.

Hi, I'm Chrissy! I'm an author, SQL Server expert, and the creator and maintainer of dbatools, a toolset that enables enterprises to manage SQL Server at scale. If you want to learn more about dbatools, you can read my book 📖, Learn dbatools in a Month of Lunches. Originally from Louisiana, I currently work and live in Europe.

About The
ReadME Project

Coding is usually seen as a solitary activity, but it’s actually the world’s largest community effort led by open source maintainers, contributors, and teams. These unsung heroes put in long hours to build software, fix issues, field questions, and manage communities.

The ReadME Project is part of GitHub’s ongoing effort to amplify the voices of the developer community. It’s an evolving space to engage with the community and explore the stories, challenges, technology, and culture that surround the world of open source.

Follow us:

Nominate a developer

Nominate inspiring developers and projects you think we should feature in The ReadME Project.

Support the community

Recognize developers working behind the scenes and help open source projects get the resources they need.

Thank you! for subscribing