Deploying PowerShell Module from GitHub to a MyGet Feed using VSTS CI/CD Pipeline
Introduction
Lately I have been playing with VSTS and its CI/CD capabilities. Since I have been writing a lot of PowerShell modules and I’m using GitHub and MyGet in this kind of projects, I thought a good scenario to build is to use VSTS CI/CD pipeline to automatically deploy the module from GitHub to my MyGet feed whenever I commit to the master branch for the particular PS module.
In summary, this is the process:
- I commit code changes to master branch
- VSTS starts the build process (CI)
- fetch the artefact
- run pester test making sure the module can be successfully imported
- Zip the artefact
- If the build succeeded, the release process (CD) kicks in
- fetch the zip file created by the build
- unzip the zip file
- publish the module to my MyGet feed
In order to demonstrate the process, I have quickly written a PowerShell module that plays random sound clips from my favorite cartoon South Park. This demo module is located in a Public GitHub repo: https://github.com/tyconsulting/PSSouthPark
I’ll now go through the entire process of setting up the pipeline in VSTS.
Creating and Configure Project in VSTS
Create VSTS Project
- Create a new project in VSTS, make sure use Git version control
- Select ‘build code from an external repository’
Create Build Definition
- Create new build definition
4.Select an empty template
- Select agent queue (I’m using the Hosted agent queue)
- In the ‘Get Sources’ step, connect to the GitHub repo
- Add Pester unit test task (You can add this task to your VSTS account from the market place). Specify test file: ModuleImport.Tests.ps1 (this test file is located in the root folder of the GitHub repo)
- Add a task to publish test results
- Add a task to archive files. Root folder to archive: $(Build.Repository.LocalPath)
- Add a task to publish artifact
- Path to publish: $(Build.ArtifactStagingDirectory)/
- Artifact Name: $(Build.BuildId).zip
- Artifact Type: Server
- Go to Triggers tab and enable the trigger
- Save the build definition to “" folder
Create Release Definition
- Create a new release definition using an empty template
- I named the environment “MyGetFeed_
"
- Add build artifact (from the build definition we created earlier)
- Create several process variables for the release
Name | Value | Scope |
---|---|---|
APIKey | <API Key for my private MyGet feed> | environment |
FeedName | <MyGet feed name> | environment |
ModuleFolderName | <Name of the sub folder that contains the PS module files in GitHub repo> | release |
RepoBaseURI | https://www.myget.org/F/ | release |
- Create a task to Extract files
- Destination folder: $(System.DefaultWorkingDirectory)/output/
- Create a task to execute PowerShell script
- Type: File Path
- Script Path: $(System.DefaultWorkingDirectory)/output/s/DeployToModuleRepo.ps1
- Arguments: -RepoBaseURI $(RepoBaseURI) -FeedName $(FeedName) -APIKey $(APIKey) -ModuleFolderName $(ModuleFolderName)
- Give release definition a name and save the definition
- Enable Continuous Deployment trigger and save again
Testing the Pipeline
Now that I have created the pipeline, I’ll test it by committing the code to the GitHub repo master branch.
Soon after I committed the code to the master branch, I can see that the VSTS build (CI)completed successfully:
and the release (CD) also completed successfully after the build:
When I log on to MyGet, I can see the PSSouthPark module in my private feed:
Conclusion
By creating such VSTS CI/CD pipeline, I no longer need to manually push modules to my MyGet feed (which I use a lot) during development process. The deployment and pester test scripts can be reused with minimum modification. If you want to try this out yourself, please feel free to fork my sample PSSouthPark module repo and give it a try.
Leave a comment