Automatic updates in cloud-native platforms has its own advantages and disadvantages. When we are not in responsible of the updates how can we ensure that the environments are still compliant with internal rules and procedures? In this post, we will see how we can create a job to get all Power Platform settings and how we can identify drifts in the configuration.
To create the job I opt to use Azure Container App Jobs due to its low cost and performance. You may consider other alternatives such as Automation Accounts or Scheduled tasks in a Virtual Machine.
Docker Image
Container app jobs are a bit more difficult to configure than other alternatives such as Azure Runbooks, as container jobs required to have a Docker Image that defines all the dependencies such as software, scripts, directories (among others) that will be used by the container. This gives a lot of flexibility to easily replicate the container in different environments independently of the cloud platform used.
Below, you can see the Docker Image I used to install the following dependencies:
- .NET
- PowerShell
- Power Platform CLI
- Azure CLI
# .NET SDK image
FROM mcr.microsoft.com/dotnet/sdk:10.0
# Install dependencies, Microsoft package repository, PowerShell, and Azure CLI
RUN wget -q https://packages.microsoft.com/config/debian/12/packages-microsoft-prod.deb && \
dpkg -i packages-microsoft-prod.deb && \
rm packages-microsoft-prod.deb && \
apt-get update && \
apt-get install -y powershell
# Install Azure CLI
RUN curl -sL https://aka.ms/InstallAzureCLIDeb | bash
# Install Power Platform CLI
RUN dotnet tool install --global Microsoft.PowerApps.CLI.Tool
# Make PAC CLI available in PATH
ENV PATH="${PATH}:/root/.dotnet/tools"
# Set working directory
WORKDIR /app
# Copy scripts into container
COPY Scripts ./Scripts
# Execute script when container starts
ENTRYPOINT ["pwsh", "-File", "/app/Scripts/GetPowerPlatformSettings.ps1"]
Create Azure Container Registry
To be able to use the Docker image we have to push it to an Azure Container Registry, you may refer to the following article to have a step by step guide on how to create one in Azure:
Once your Azure Container Registry is created you will be able to push it as follow:
docker build -t power-platform-settings:1.0 . docker login mycontainerregistry.azurecr.io docker tag power-platform-settings:1.0 mycontainerregistry.azurecr.io/governance/power-platform-settings docker push mycontainerregistry.azurecr.io/governance/power-platform-settings
Create Azure Container App Job
Once the Azure Container Registry is created and the docker image is pushed and available in there, you can create the Azure Container App Job by applying the following steps:
- In Azure Portal search for “Container App Job” and click on “New”
- Select the Subscription and Resource Group where the container app job will be created
- Important: If you foresee to have in your container app job secure connections towards other Azure Resources using Virtual Private Network, make sure to click on “create new environment” and in the Network tab select “Use your own virtual network”, if you don’t select this option and you need a virtual private network you need to create the Container App Job from scratch
- Select the trigger type
- In the next tab (Container) make sure to select the Container Registry created in the previous chapter and select the docker image we have uploaded. In this step you will also be able to define Environment Variables in case you use them in your scripts, in my example I defined 2 (STORAGE_ACCOUNT_NAME, STORAGE_CONTAINER_NAME)
Set-up Managed Identity
The example provided makes a connection to Azure Storage Blob Container, I decided to use managed identity as the authentication method to the Azure Blob Container
- In the Container App job navigate to Settings > Identity and enable a System assigned identity. By enabling this option, Azure willc reate automatically an app registration you can use to assign permissions over the Azure Storage Container
- In the Azure Storage Container you can navigate to Access Controls (IAM) and assign the managed identity the role “Storage Blob Data Contributor”, this will allow the job to add and read files from the Blob Container
- To authenticate to Power Platform CLI using the managed identity, we should register an admin management application as described in the following article Creating a service principal application using API – Power Platform | Microsoft Learn
- From PowerShell execute the following commands
Connect-AzAccount
$TenantId = ""
$secureToken = (Get-AzAccessToken -TenantId $TenantId -ResourceUrl "https://api.bap.microsoft.com").Token
$AccessToken = [System.Net.NetworkCredential]::new("", $secureToken).Password
$headers = @{ 'Authorization' = 'Bearer ' + $AccessToken }
$headers.Add('Content-Type', 'application/json')
Invoke-RestMethod -Method Put -Uri "https://api.bap.microsoft.com/providers/Microsoft.BusinessAppPlatform/adminApplications/[CLIENTID]?api-version=2020-10-01" -Headers $headers
The PowerShell should return the application ID registered.
You can query all application ID registered as admin Applications:
Invoke-RestMethod -Method Get -Uri "https://api.bap.microsoft.com/providers/Microsoft.BusinessAppPlatform/adminApplications?api-version=2020-10-01" -Headers $headers
You will find the source code I’m using for the script and the docker image in my Github repo:
https://github.com/Brank/powerplatform-governance-jobs
References:
https://learn.microsoft.com/en-us/power-platform/admin/powerplatform-api-create-service-principal
