Retreives the results of a Syft/Grype container/dependency vulnerability scan from a build artifact in Azure DevOps and pushes this to a InFluxDB bucket. This also includes a Grafana dashboard definition to display these vulnerabilities.
-
Install .NET SDK:
- Ensure you have the .NET SDK installed on your machine. You can download it from the .NET download page.
-
Verify Installation:
- Open a terminal or command prompt and run the following command to verify the installation:
dotnet --version
- This should output the version of the .NET SDK installed.
- Open a terminal or command prompt and run the following command to verify the installation:
Docker is required to run the Syft/Grype container scans. Follow the steps below to install Docker on your system.
-
Download Docker Desktop: Visit the Docker Desktop for Windows page and download the installer.
-
Run the Installer: Follow the on-screen instructions to complete the installation.
-
Verify Installation: Open PowerShell and run the following command to verify that Docker is installed correctly:
docker --version
Alternatively, you can install Docker using PowerShell:
-
Open PowerShell as Administrator: Right-click on the PowerShell icon and select "Run as administrator".
-
Run the Installation Command: Execute the following command to install Docker:
Invoke-WebRequest -Uri https://desktop.docker.com/win/stable/Docker%20Desktop%20Installer.exe -OutFile DockerDesktopInstaller.exe Start-Process -FilePath .\DockerDesktopInstaller.exe -ArgumentList "/quiet", "/norestart" -Wait Remove-Item -Force DockerDesktopInstaller.exe
-
Start Docker Desktop: After installation, start Docker Desktop from the Start menu.
-
Verify Installation: Run the following command to verify that Docker is installed correctly:
docker --version
For more detailed instructions, refer to the official Docker documentation.
-
Start the Containers: Open a terminal in your project directory and run the following command to start the InfluxDB and Grafana containers:
docker-compose up -d
The
-d
flag runs the containers in detached mode. -
Access InfluxDB and Grafana:
- InfluxDB: Open your browser and go to
http://localhost:8086
to access the InfluxDB UI. - Grafana: Open your browser and go to
http://localhost:3000
to access the Grafana UI. Log in with the credentials specified in thedocker-compose.yml
file.
- InfluxDB: Open your browser and go to
For more detailed instructions on using Docker Compose, refer to the official Docker Compose documentation.
The actual creation of the of the vulnerability scanning of all dependencies is done in Azure DevOps. There need to be one or more pipelines that perform the scan using Syft and Grype. An example of a pipeline can be found here:
trigger:
- main
pool:
vmImage: 'ubuntu-latest'
variables:
CONTAINER_IMAGE: '[your_container_registry].azurecr.io/[containername]:latest'
jobs:
- job: ScanContainer
displayName: 'Scan Container for Vulnerabilities'
steps:
- task: AzureCLI@2
inputs:
azureSubscription: '[your_service_connection]'
scriptType: 'bash'
scriptLocation: 'inlineScript'
inlineScript: |
echo "Installing Syft"
curl -sSfL https://raw.githubusercontent.com/anchore/syft/main/install.sh | sh -s -- -b /usr/local/bin
echo "Installing Grype"
curl -sSfL https://raw.githubusercontent.com/anchore/grype/main/install.sh | sh -s -- -b /usr/local/bin
displayName: 'Install Syft and Grype'
- task: AzureCLI@2
inputs:
azureSubscription: '[your_service_connection]'
scriptType: 'bash'
scriptLocation: 'inlineScript'
inlineScript: |
echo "Logging into Azure Container Registry"
az acr login --name [your_container_registry]
displayName: 'Login to Azure Container Registry'
- task: AzureCLI@2
inputs:
azureSubscription: '[your_service_connection]'
scriptType: 'bash'
scriptLocation: 'inlineScript'
inlineScript: |
echo "Generating SBOM with Syft"
syft $CONTAINER_IMAGE -o json > sbom.json
displayName: 'Generate SBOM with Syft'
- task: AzureCLI@2
inputs:
azureSubscription: '[your_service_connection]'
scriptType: 'bash'
scriptLocation: 'inlineScript'
inlineScript: |
echo "Scanning for vulnerabilities with Grype"
grype sbom:sbom.json
# Save results in JSON format
grype sbom:sbom.json -o json > grype-scan-results.json
displayName: 'Scan for Vulnerabilities with Grype'
- task: PublishBuildArtifacts@1
inputs:
PathtoPublish: 'grype-scan-results.json'
ArtifactName: 'GrypeScanResults'
publishLocation: 'Container'
displayName: 'Publish Grype Scan Results as Build Artifact'
⚠️ NOTICE That the name of this pipeline must correspond with the postfix as configured in the appsettings.json. You can create as many pipelines for different services as needed as long as the postfix corresponds the results wil be picked up and pushed to Influx and eventualy displayed in grafana.
Once this is done, this app needs to able to access the Azure DevOps api's. Therefor you need to create a PAT token in Azure DevOps.
A Personal Access Token (PAT) is required to authenticate and access Azure DevOps APIs. Follow the steps below to create a PAT:
-
Sign in to Azure DevOps:
- Go to Azure DevOps and sign in with your account.
-
Navigate to User Settings:
- Click on your profile picture in the top right corner.
- Select "Security" from the dropdown menu.
-
Create a New Token:
- In the "Personal Access Tokens" section, click on "New Token".
-
Configure the Token:
- Name: Enter a descriptive name for the token (e.g., "SyftGrypeScraper Access Token").
- Organization: Select the organization for which the token will be used.
- Scopes: Choose the scopes required for your application. For accessing build artifacts and pipelines, you typically need:
- Build (Read): To read build information.
- Artifacts (Read): To read artifacts.
- Project and Team (Read): To read project and team information.
- Expiration: Set the expiration date for the token. Choose a duration that balances security and convenience.
-
Create the Token:
- Click on "Create" to generate the token.
-
Copy the Token:
- Important: Copy the token and store it securely. You will not be able to see the token again once you close the window.
- Use this token in your application to authenticate API requests.
Add the PAT token to your appsettings.json
file:
{
"AzureDevOps": {
"Org": "[ORGANIZATION_NAME]",
"Project": "[PROJECT_NAME]",
"Pat": "[PESRONAL_ACCESS_TOKEN]",
"PipelinePostfix": "Scan",
"ArtifactName": "GrypeScanResults",
"ApiVersion": "6.0"
},
"InfluxDb": {
"Url": "http://localhost:8086/",
"Token": "[INFLUXDB_TOKEN]",
"Org": "GrypeScanOrg",
"Bucket": "GrypeScanResults"
},
"ApplicationInsights": {
"InstrumentationKey": "[INSTRUMENTATION_CONNECTION_STRING]"
}
}
-
Access InfluxDB UI:
- Open your web browser and go to
http://localhost:8086
.
- Open your web browser and go to
-
Sign In:
- Sign in with your InfluxDB credentials.
-
Create a Bucket:
- Navigate to the "Buckets" section in the left-hand menu.
- Click on "Create Bucket".
- Name: Enter a name for your bucket (e.g., "GrypeScanResults").
- Retention Rules: Set the retention period for the data in the bucket. You can choose a specific duration or keep it as "Infinite".
- Click on "Create" to create the bucket.
-
Create a Token:
- Navigate to the "Tokens" section in the left-hand menu.
- Click on "Generate Token" and select "Read/Write Token".
- Description: Enter a description for the token (e.g., "GrypeScanResults Token").
- Bucket Permissions: Select the bucket you created (e.g., "GrypeScanResults") and set the permissions to Read/Write.
- Click on "Save" to generate the token.
- Important: Copy the token and store it securely. You will not be able to see the token again once you close the window.
Add the InfluxDB URL, token, organization, and bucket to your appsettings.json
file:
{
"AzureDevOps": {
"Org": "your_organization",
"Project": "your_project",
"Pat": "your_pat_token",
"ApiVersion": "6.0",
"PipelinePostfix": "your_pipeline_postfix"
},
"InfluxDb": {
"Url": "http://localhost:8086",
"Token": "your_influxdb_token",
"Org": "your_influxdb_org",
"Bucket": "GrypeScanResults"
}
}
-
Navigate to the Project Directory:
- Open a terminal or command prompt.
- Navigate to the directory containing your .NET project. For example:
cd path/to/your/project
-
Run the Application:
- Use the
dotnet run
command to run the application:dotnet run
- Use the
When you run the application, you should see output similar to the following:
Pipeline: Service-******* VulnerabilityScan, Latest Build Number: *****
Writing vulnerability GHSA-m5vv-6r4h-3vj9 to InfluxDB
Writing vulnerability GHSA-x674-v45j-fwxw to InfluxDB
Writing vulnerability GHSA-59j7-ghrg-fj52 to InfluxDB
Writing vulnerability GHSA-6qmf-mmc7-6c2p to InfluxDB
Writing vulnerability GHSA-g3q9-xf95-8hp5 to InfluxDB
If setting up grafana to run in Azure Container Apps you need a storage for the grafana configuration. There are multiple options, a relative simple way is a volume mapping unsing SQLite. If you want to to this follow this blog: https://blog.rishabkumar.com/grafana-on-azure-web-app-containers#heading-initiate-an-empty-sqlite-database
-
Access InfluxDB UI:
- Open your web browser and go to
http://localhost:8086
.
- Open your web browser and go to
-
Sign In:
- Sign in with your InfluxDB credentials.
-
Create a Token:
- Navigate to the "Tokens" section in the left-hand menu.
- Click on "Generate Token" and select "Read/Write Token".
- Description: Enter a description for the token (e.g., "Grafana Access Token").
- Bucket Permissions: Select the bucket you want to use (e.g., "GrypeScanResults") and set the permissions to Read/Write.
- Click on "Save" to generate the token.
- Important: Copy the token and store it securely. You will not be able to see the token again once you close the window.
-
Add Data Source:
- In Grafana, click on the "Configuration" (gear icon) in the left-hand menu.
- Select "Data Sources".
- Click on "Add data source".
-
Configure InfluxDB Data Source:
- Select "InfluxDB" from the list of data sources.
- HTTP:
- URL:
http://influxdb:8086
- URL:
- Auth:
- Token: Paste the PAT token you generated in InfluxDB.
- InfluxDB Details:
- Organization: Enter your InfluxDB organization name.
- Bucket: Enter the bucket name (e.g., "GrypeScanResults").
- Click on "Save & Test" to verify the connection.
- Import Dashboard:
- In Grafana, click on the "+" icon in the left-hand menu and select "Import".
- Upload JSON File:
- Click on "Upload JSON file" and select the
GrafanaDashboard/Dashboard.json
file from your project directory.
- Click on "Upload JSON file" and select the
- Load:
- Click on "Load" to load the dashboard configuration.
- Select Data Source:
- Select the InfluxDB data source you configured earlier.
- Click on "Import" to add the dashboard.
- Azure Subscription: Ensure you have an active Azure subscription.
- Azure DevOps Account: Ensure you have an Azure DevOps account and a project created.
- Service Connection: Create a service connection in Azure DevOps to your Azure subscription.
- Clone the Repository:
- Clone the repository to your local machine or directly to your Azure DevOps project.
- Navigate to Pipelines:
- In your Azure DevOps project, navigate to Pipelines > Pipelines.
- Create a New Pipeline:
- Click on New Pipeline.
- Select the repository where your code is hosted (e.g., Azure Repos Git, GitHub, etc.).
- Follow the prompts to configure the pipeline.
- Configure the Pipeline:
- When prompted to configure the pipeline, select Existing Azure Pipelines YAML file.
- Choose the
azure-pipelines.yml
file located in the pipelines folder of your repository.
- Review and Run the Pipeline:
- Review the pipeline configuration.
- Click on Run to start the pipeline.
- Monitor the Pipeline:
- Monitor the pipeline execution in the Azure DevOps portal.
- Ensure all steps complete successfully.
The azure-pipelines.yml
file includes steps to:
- Build the Docker image.
- Push the Docker image to Azure Container Registry (ACR).
- Deploy the container to Azure Container Apps.
By following these steps, you will have set up AzureDevOps with vulnerability scanners, psuh this data to InfluxDB, and setup Grafana on localhost:3000
, created a PAT in InfluxDB, added InfluxDB as a data source in Grafana, and imported a dashboard from a JSON file.