Azure DevOps Integration Setup Guide

Azure DevOps Integration Setup Guide

This guide walks you through connecting Lathe Studio to Azure DevOps for CI/CD pipeline integration.


Prerequisites#

  • Azure DevOps account (Azure DevOps Services or Azure DevOps Server)
  • Azure DevOps project with build pipelines
  • Project admin access in Lathe Studio

Overview#

The Azure DevOps integration enables:

  • CI/CD Webhooks: Automatically receive build completion events via Service Hooks
  • Work Item Push: Push a failed test execution to Azure DevOps as a Bug work item
  • Work Item Sync: Receive workitem.* Service Hook events to mirror status and comments on linked executions

Connecting Azure DevOps#

Step 1: Connect Your Azure DevOps Organization

  1. In Lathe Studio, go to Settings → Integrations → Azure DevOps
  2. Click Connect
  3. Choose your authentication method — a Personal Access Token (PAT) or Microsoft Entra ID (OAuth)
  4. Enter your Azure DevOps organization URL (e.g., https://dev.azure.com/your-org)

Step 2: Map a Project

  1. After connecting, click Map Project
  2. Choose your Lathe Studio project and the matching Azure DevOps project
  3. Lathe Studio automatically creates the Service Hook subscription for workitem.created events — no manual webhook configuration is needed

The Service Hook sends an X-ADO-Signature header on every request, which Lathe Studio verifies against your connection's webhook secret.

Step 3: Test the Integration

  1. On the mapped project, click Test Push to push a sample Bug work item
  2. Check that the Bug appears in your Azure DevOps project
  3. Confirm the webhook path by creating or commenting on a work item and checking the linked execution in Lathe Studio

Authentication#

Two layers of authentication are involved:

  • Connection: Lathe Studio connects to your Azure DevOps organization with a Personal Access Token (PAT) or Microsoft Entra ID (OAuth). Tokens are stored encrypted and refreshed automatically when they expire.
  • Inbound webhooks: Every Service Hook request carries an X-ADO-Signature header, verified against your connection's webhook secret (HMAC-SHA256 of the request body).

How It Works#

Inbound (Service Hooks):

  1. Event occurs → Azure DevOps sends a Service Hook event to /api/webhooks/azure-devops
  2. Signature check → The X-ADO-Signature header is verified against your connection's webhook secret
  3. Project lookup → The Azure DevOps project ID is matched to your mapped Lathe Studio project
  4. Processing:
    • workitem.created / workitem.updated → work item status syncs to linked executions
    • workitem.commented → comments mirror back to execution notes
    • build.complete → recorded as a CI build result in Lathe Studio

Outbound (bug push):

  1. Open a failed execution in a run and push it as a bug
  2. Lathe Studio creates a Bug work item in the mapped Azure DevOps project
  3. The work item key is stored on the execution for tracking

Build Queue UI#

The Build Queue on the Releases page holds builds that arrived without a project or release assignment (for example, from the Bitbucket webhook). From the queue you can:

  • Assign to Release: Select an active release for the project
  • Select Project: Navigate to projects if the project was not auto-detected
  • Reject: Remove the build from the queue (no build created)

Azure Pipelines Example#

To report test results back to Lathe Studio, create an API key (Settings > Organization > API Keys) with the results:submit scope, add it to your pipeline as the PT_API_KEY variable (mark it secret), then add this to your azure-pipelines.yml:

The example below posts JSON directly. To send a generated file, use lathe report <file> --project <code> with JUnit XML, TestNG XML (testng-results.xml), NUnit 3 XML, xUnit.net v2 XML, or Cucumber JSON. The CLI detects the format from its contents; use --format to specify one. Cypress, Playwright, Postman (Newman), pytest, and Appium-based suites already produce JUnit XML. The ingest API accepts JSON payloads, not raw files.

trigger:
  branches:
    include:
      - main
      - develop

stages:
  - stage: Test
    jobs:
      - job: RunTests
        pool:
          vmImage: 'ubuntu-latest'
        steps:
          - script: npm test
            displayName: 'Run tests'

          - script: |
              curl -X POST https://lathe.studio/api/v1/results/ingest \
                -H "Authorization: Bearer $(PT_API_KEY)" \
                -H "Content-Type: application/json" \
                -d '{
                  "build": {
                    "identifier": "Build $(Build.BuildNumber)",
                    "branch": "$(Build.SourceBranchName)",
                    "commit_sha": "$(Build.SourceVersion)"
                  },
                  "source": { "pipeline": "azure_pipelines" },
                  "results": [
                    { "test_identifier": "TC-MOB-0042", "name": "Login works", "status": "passed", "duration_ms": 1200 }
                  ]
                }'
            displayName: 'Report results to Lathe Studio'

If your API key is org-scoped (not tied to one project), also include "project_key": "YOUR-PROJECT-CODE" at the top level of the payload.


Azure DevOps Server (On-Premises)#

For on-premises Azure DevOps Server:

  1. Ensure your server is accessible from the internet (or use reverse proxy)
  2. Use the same webhook URL: https://lathe.studio/api/webhooks/azure-devops
  3. Configure SSL certificates properly
  4. Allowlist Lathe Studio IP addresses if using a firewall:
    • Contact support for current IP ranges

Work Item Integration#

Once a project is mapped, you can push any failed execution to Azure DevOps as a Bug work item:

  1. Open a submitted or completed test run
  2. Find a failed test case and click the push button
  3. A Bug work item is created in the mapped Azure DevOps project and the work item ID is stored on the execution

Bug creation uses a fixed field mapping — there is no per-field configuration and no automatic creation; pushes are always manual.

Field Mappings

Lathe StudioAzure DevOps
Test Case TitleTitle
Test StepsRepro Steps
Tester Notes / EnvironmentDescription / System Info
PriorityPriority

Troubleshooting#

Webhook events not arriving

  1. Check service hook delivery in Azure DevOps (Project Settings > Service Hooks > History)
  2. Verify the subscription was created — re-map the project in Lathe Studio to recreate it
  3. Confirm the X-ADO-Signature header secret matches your connection

Work items not creating

  1. Verify the Azure DevOps connection is active (check for credential health warnings in Lathe Studio)
  2. Ensure the Lathe Studio project is mapped to an Azure DevOps project
  3. Check that your PAT/OAuth grant has permission to create work items in the target project

Rate limiting

Results-ingest API keys are limited to 60 requests per minute by default. Contact support to increase limits.


Security#

  • Azure DevOps access tokens are stored encrypted in the database and refreshed automatically
  • Webhook secrets are stored encrypted and used for HMAC-SHA256 signature verification
  • Results-ingest API keys are hashed using SHA-256 before storage; only the first 12 characters are kept for identification
  • Keys can be revoked at any time
  • All webhook communications use HTTPS

Unlinking Azure DevOps#

To disconnect:

  1. Go to Settings → Integrations → Azure DevOps in Lathe Studio
  2. Click Disconnect
  3. Optionally delete the Lathe Studio subscriptions in Azure DevOps (Project Settings > Service Hooks)

Note: Previously pushed work items remain linked. New pushes will not be possible until reconnected.


Advanced Configuration#

Token Refresh

Connections authenticated with Microsoft Entra ID (OAuth) refresh their tokens automatically. PAT connections never expire on the Lathe Studio side, but if the PAT is revoked in Azure DevOps, reconnect with a new PAT.

Handling Expired Credentials

If a push or webhook fails because credentials expired, Lathe Studio records the auth failure on the integration settings page so the problem is visible instead of failing silently.


For additional help, contact support.