แก้ไข

แชร์ผ่าน


Azure SDK for Go authentication with a service principal

In this tutorial, you use the Azure SDK for Go to authenticate to Azure with an Azure service principal using either a secret or a certificate.

Azure service principals define the access policy and permissions in a Microsoft Entra tenant, enabling core features such as authentication during sign-on and authorization during resource access. They remove the need to use personal accounts to access Azure resources. You can assign a service principal the exact permissions needed for your app and develop against those permissions, rather than using a personal account, which might have more privileges in your tenant than the app requires. You can also use service principals for apps that are hosted on-premises that need to use Azure resources. The Azure SDK for Go Azure Identity module provides a convenient way to authenticate to Azure with a service principal using environment variables, and a secret or a certificate.

Follow this tutorial to create and authenticate with the Azure SDK for Go using a service principal.

Prerequisites

  • Azure subscription: If you don't have an Azure subscription, create a free account before you begin.

1. Create Azure resources

Before you begin, create a new resource group and key vault instance.

az group create --name go-on-azure --location eastus

az keyvault create --location eastus --name <keyVaultName> --resource-group go-on-azure --enable-rbac-authorization

Replace <keyVaultName> with a globally unique name.

Note down the id property from the output of the az keyvault create command. You'll use it in the next section to define the scope of the authorization for the service principal. The id value has the following form: /subscriptions/<subscriptionId>/resourceGroups/go-on-azure/providers/Microsoft.KeyVault/vaults/<keyVaultName>.

2. Create an Azure service principal

Use one of the following techniques to create an Azure service principal and assign it the "Key Vault Secrets Officer" role on the key vault:

To learn more Azure service principals, see Service principal object.

Assigning the "Key Vault Secrets Officer" role to the service principal, authorizes it to create, read, update, and delete secrets in the key vault. To learn more about built-in roles for Azure key vault, see Provide access to Key Vault keys, certificates, and secrets with an Azure role-based access control. To learn more about built-in roles in Azure, see Azure built-in roles.

Option 1: Create an Azure service principal with a secret

Run the following commands to create an Azure service principal and assign it the "Key Vault Secrets Officer" role on the key vault.

az ad sp create-for-rbac --name <servicePrincipalName> --role "Key Vault Secrets Officer" --scope <keyVaultId>

Replace <servicePrincipalName> and <keyVaultId> with the appropriate values.

Note down the password, tenant, and appId properties from the output. You need them in the next section.

After creation, the service principal password can't be retrieved. If you forget the password, you can reset the service principal credentials.

Option 2: Create an Azure service principal with a certificate

Run the following commands to create an Azure service principal that uses a certificate and assign it the "Key Vault Secrets Officer" role on the key vault.

az ad sp create-for-rbac --name <servicePrincipalName> --create-cert --role "Key Vault Secrets Officer" --scope <keyVaultId>

Replace <servicePrincipalName> and <keyVaultId> with the appropriate values.

Note down the fileWithCertAndPrivateKey, tenantId, and appId properties from the output. You need them in the next section.

3. Authenticate to Azure with a service principal

By using DefaultAzureCredential, you can avoid writing environment-specific code to authenticate to Azure. With DefaultAzureCredential, you can configure your service principal credentials by defining environment variables.

Choose one of the following options to configure your service principal credentials:

To learn more about the DefaultAzureCredential, check out Azure authentication with the Azure SDK for Go

Option 1: Authenticate with a secret

Define the following environment variables:

Variable name Value
AZURE_CLIENT_ID Application ID of an Azure service principal
AZURE_TENANT_ID ID of the application's Microsoft Entra tenant
AZURE_CLIENT_SECRET Password of the Azure service principal
export AZURE_TENANT_ID="<active_directory_tenant_id>"
export AZURE_CLIENT_ID="<service_principal_appid>"
export AZURE_CLIENT_SECRET="<service_principal_password>"

Option 2: Authenticate with a certificate

Variable name Value
AZURE_CLIENT_ID Application ID of an Azure service principal
AZURE_TENANT_ID ID of the application's Microsoft Entra tenant
AZURE_CLIENT_CERTIFICATE_PATH Path to a PEM or PKCS12 certificate file including private key. If you followed the steps for the Azure CLI, the file isn't password protected. If you followed the steps for Azure PowerShell, the file is password protected, and you'll also need to set the AZURE_CLIENT_CERTIFICATE_PASSWORD environment variable.
AZURE_CLIENT_CERTIFICATE_PASSWORD The password you entered when you created the service principal. Only needed if you followed the steps for Azure PowerShell.
export AZURE_TENANT_ID="<active_directory_tenant_id>"
export AZURE_CLIENT_ID="<service_principal_appid>"
export AZURE_CLIENT_CERTIFICATE_PATH="<azure_client_certificate_path>"

Use DefaultAzureCredential to authenticate a resource client

After you set the environment variables, you can use DefaultAzureCredential in the Azure Identity module to authenticate a resource client. The following code shows how to get an instance of DefaultAzureCredential.

cred, err := azidentity.NewDefaultAzureCredential(nil)
if err != nil {
    log.Fatalf("failed to obtain a credential: %v", err)
}

4. Create a key vault secret with Go

Use the following code sample to verify that your service principal authenticates to Azure and has the appropriate permissions to the key vault.

  1. Create a new directory called go-on-azure in your home directory.

    mkdir ~/go-on-azure
    
  2. Change to the go-on-azure directory.

    cd ~/go-on-azure
    
  3. Run go mod init to create the go.mod file.

    go mod init go-on-azure
    
  4. Run go get to install the required Go modules.

    go get "github.com/Azure/azure-sdk-for-go/sdk/azidentity"
    go get "github.com/Azure/azure-sdk-for-go/sdk/security/keyvault/azsecrets"
    
  5. Create a file named main.go and add the following code.

    package main
    
    import (
    	"context"
    	"fmt"
    	"log"
    	"os"
    
    	"github.com/Azure/azure-sdk-for-go/sdk/azidentity"
        "github.com/Azure/azure-sdk-for-go/sdk/security/keyvault/azsecrets"
    )
    
    func createSecret(name, value string) {
    	keyVaultName := os.Getenv("KEY_VAULT_NAME")
    	keyVaultUrl := fmt.Sprintf("https://%s.vault.azure.net/", keyVaultName)
    
    	cred, err := azidentity.NewDefaultAzureCredential(nil)
    	if err != nil {
    		log.Fatalf("failed to obtain a credential: %v", err)
    	}
    
    	client, err := azsecrets.NewClient(keyVaultUrl, cred, nil)
    	if err != nil {
    		log.Fatalf("failed to create a client: %v", err)
    	}
    
        params := azsecrets.SetSecretParameters{Value: &value}
        resp, err := client.SetSecret(context.TODO(), name, params, nil)
    	if err != nil {
    		log.Fatalf("failed to create a secret: %v", err)
    	}
    
    	fmt.Printf("Name: %s, Value: %s\n", *resp.ID, *resp.Value)
    }
    
    func main() {
    	createSecret("ExamplePassword", "hVFkk965BuUv")
    }
    
    
  6. Create an environment variable named KEY_VAULT_NAME. Set the environment variable's value to the name of the Azure Key Vault created previously.

    export KEY_VAULT_NAME=<keyVaultName>
    

    Replace <keyVaultName> with the name of your Azure Key Vault instance.

  7. Run the go run command to create the new key vault secret.

     go run main.go
    

    On success, the output is similar to the following:

    Name: https://<keyVaultName>.vault.azure.net/secrets/ExamplePassword/1e697f71d0014761a65641226f2f057b, Value: hVFkk965BuUv
    

5. Clean up resources

If you no longer want to use the Azure resources you created in this article, it's a good practice to delete them. Deleting unused resources helps you avoid incurring ongoing charges and keeps your subscription uncluttered. The easiest way to delete the resources you used in this tutorial is to delete the resource group.

az group delete --name go-on-azure --yes

The --yes argument tells the command not to ask for confirmation.

The preceding command performs a soft delete on the key vault in the resource group. To permanently remove it from your subscription, enter the following command:

az keyvault purge --name <keyVaultName> --no-wait

Replace <keyVaultName> with the name of your key vault.

Finally, you should remove the app registration and service principal.

az ad app delete --id <servicePrincipalAppId>

Replace <servicePrincipalAppId> with the App ID of your service principal.

Next steps