Home > database >  How do I use Service Principal authentication with an Azure Machine Learning Pipeline Endpoint in C#
How do I use Service Principal authentication with an Azure Machine Learning Pipeline Endpoint in C#

Time:10-16

I'm trying to call an Azure Machine Learning Pipeline Endpoint I've set up using C# & the Machine Learning REST api.

I am certain that I have the Service Principal configured correctly, as I can successfully authenticate & hit the endpoint using the azureml-core python sdk:

sp = ServicePrincipalAuthentication(
    tenant_id=tenant_id,
    service_principal_id=service_principal_id,
    service_principal_password=service_principal_password)
ws =Workspace.get(
    name=workspace_name, 
    resource_group=resource_group, 
    subscription_id=subscription_id, 
    auth=sp)

endpoint = PipelineEndpoint.get(ws, name='MyEndpoint')
endpoint.submit('Test_Experiment')

I'm using the following example in C# to attempt to run my endpoint: https://docs.microsoft.com/en-us/azure/machine-learning/how-to-deploy-pipelines#run-a-published-pipeline-using-c

I'm attempting to fill auth_key with the following code:

var clientId = Environment.GetEnvironmentVariable("AZURE_CLIENT_ID");
var clientSecret = Environment.GetEnvironmentVariable("AZURE_CLIENT_SECRET");
var tenantId = Environment.GetEnvironmentVariable("AZURE_TENANT_ID");

var cred = new ClientSecretCredential(tenantId, clientId, clientSecret);
var auth_key = cred.GetToken(new Azure.Core.TokenRequestContext(new string[] {".default" }));

I receive a 401 (unauthorized).

What am I am doing wrong?

  • UPDATE *

I changed the 'scopes' param in the TokenRequestContext to look like:

var auth_key = cred.GetToken(new Azure.Core.TokenRequestContext(new string[] { "http://DataTriggerApp/.default" }));

http://DataTriggerApp is one of the servicePrincipalNames that shows up when i query my Service Principal from the azure CLI.

Now, when I attempt to use the returned token to call the Machine Learning Pipeline Endpoint, I receive a 403 instead of a 401. Maybe some progress?

CodePudding user response:

Ok, through a lot of trial-and-error I was able to come up with two ways of acquiring a token that allows me to hit my Azure Machine Learning Pipeline Endpoint through the REST api. One uses Microsoft.Identity.Client & one uses Azure.Identity.

using Microsoft.Identity.Client;

...

public static async Task<string> GetAccessToken()
{
      var clientId = Environment.GetEnvironmentVariable("AZURE_CLIENT_ID");
      var clientSecret = Environment.GetEnvironmentVariable("AZURE_CLIENT_SECRET");
      var tenantId = Environment.GetEnvironmentVariable("AZURE_TENANT_ID");

   
      var app = ConfidentialClientApplicationBuilder.Create(clientId)
                                                .WithClientSecret(clientSecret)                                                
                                                .WithAuthority(AzureCloudInstance.AzurePublic, tenantId)
                                                .Build();
      var result = await app.AcquireTokenForClient(new string[] { "https://ml.azure.com/.default" }).ExecuteAsync();
      return result.AccessToken;
}

Or:

using Azure.Identity;
...

public static async Task<string> GetAccessToken()
{
      var clientId = Environment.GetEnvironmentVariable("AZURE_CLIENT_ID");
      var clientSecret = Environment.GetEnvironmentVariable("AZURE_CLIENT_SECRET");
      var tenantId = Environment.GetEnvironmentVariable("AZURE_TENANT_ID");


      var cred = new ClientSecretCredential(tenantId, clientId, clientSecret);
      var token =  await cred.GetTokenAsync(new Azure.Core.TokenRequestContext(new string[] { "https://ml.azure.com/.default" }));
      return token.Token;
}
  • Related