azureasp.net-web-apiazure-devopsazure-active-directory

How to Replace my PAT for Accessing Azure DevOps API in .NET Web API?


I have a .NET Web API that I use to interact with the Azure DevOps API for creating and updating Work Items on Azure DevOps Boards of various organizations and DevOps projects. Currently, I'm using a Personal Access Token (PAT) from my own account for authentication, but I want to eliminate the use of this PAT for obvious reasons.

I have registered an Application in Azure and given it the vso.work_full permissions. I have also added an Authentication Service to my application.

public class AzureDevOpsAuthService
{
    private readonly IConfidentialClientApplication _clientApp;

    public AzureDevOpsAuthService(string clientId, string clientSecret, string tenantId)
    {
        _clientApp = ConfidentialClientApplicationBuilder.Create(clientId)
            .WithClientSecret(clientSecret)
            .WithAuthority(new Uri($"https://login.microsoftonline.com/{tenantId}"))
            .Build();
    }

    public async Task<string> GetAccessTokenAsync()
    {
        var result = await _clientApp.AcquireTokenForClient(new[] { "499b84ac-1321-427f-aa17-267ca6975798/.default" }).ExecuteAsync();
        return result.AccessToken;
    }
}

This failed to work, giving me the following error:

Microsoft.VisualStudio.Services.Common.VssServiceException: TF401444: Please sign-in at least once as {TENANT ID} in a web browser to enable access to the service. at Microsoft.VisualStudio.Services.WebApi.VssHttpClientBase.HandleResponseAsync(HttpResponseMessage response, CancellationToken cancellationToken) at Microsoft.VisualStudio.Services.WebApi.VssHttpClientBase.SendAsync(HttpRequestMessage message, HttpCompletionOption completionOption, Object userState, CancellationToken cancellationToken) at Microsoft.VisualStudio.Services.WebApi.VssHttpClientBase.SendAsync[T](HttpRequestMessage message, Object userState, CancellationToken cancellationToken) at Microsoft.VisualStudio.Services.Location.Client.LocationHttpClient.GetConnectionDataAsync(ConnectOptions connectOptions, Int64 lastChangeId, CancellationToken cancellationToken, Object userState)

I'm not sure what the problem is. It seems I should add the Application as a User in the organizations? But I can't seem to find it when I try to add a user or give it the Contributor role.

Questions:


Solution

  • Is using an Azure App with multi-tenants the best way

    If you want to access multiple organizations connected to different Microsoft Entra ID, it's suggested to use multi-tenants app.

    How can I add the application as a user to different Azure Tenants, so that I can access their Azure DevOps Boards to create and update Work Items?

    1. Create a service principal using multi-tenant authentication and add a redirect uri https://www.microsoft.com in TenantA. enter image description here

    2. Open the below URL in a private browser for adding it to another tenant, for example TenantB. https://login.microsoftonline.com/<TenantB ID>/oauth2/authorize?client_id=<Application ID of the app in TenantA>&response_type=code&redirect_uri=https%3A%2F%2Fwww.microsoft.com%2F

      It will ask for authorization on behalf of organization , you can accept it.

    3. After the above is done, login to portal of TenantB and go to Enterprise Application you will see it. You can assign it with your needed role.

      enter image description here

    4. Go to the organization connected to TenantB, search and add the app into your org from Organization Settings -> Users ->Add users. enter image description here