Functions/Backup-BsgPbiTenant.ps1

<#
    .SYNOPSIS
        Backup a Power BI tenant to a local directory.
         
    .DESCRIPTION
        The workspaces, objects and data from a Power BI Service tenant are saved to files in a local directory.
 
    .PARAMETER Path
        The path to the root folder, where the temporary files will be saved.
        Subfolders will be created automatically.
 
    .PARAMETER MetadataOnly
        Backup only Metadata excluding actual Dataset files (PBIX Files).
 
    .EXAMPLE
        # Backup Tenant
        Backup-BsgPbiTenant -Path "C:\temp\BSG PBI Administration"
         
    .INPUTS
 
    .OUTPUTS
 
    .NOTES
        This script uses the Power BI Management module for Windows PowerShell.
        If this module is not installed, install it by using the command 'Install-Module -Name MicrosoftPowerBIMgmt -Scope CurrentUser'.
#>


function Backup-BsgPbiTenant{

    param
    (
        [Parameter(Mandatory=$true)][string]$Path,
        [Parameter(Mandatory=$false)][switch]$MetadataOnly = $false,
        [Parameter(Mandatory=$false)][switch]$GetActivity = $false
    )

    try {
        Write-Host
        Write-Host
        Write-PSFHostColor -Level Host -DefaultColor white -String "---------------------------------------------------------------------------------------------"
        Write-Host
        Write-PSFHostColor -Level Host -DefaultColor gray -String " <c='green'>Backup tenant...</c>"
        Write-Host
        Write-PSFHostColor -Level Host -DefaultColor white -String "---------------------------------------------------------------------------------------------"
        Write-Host
        Write-Host


        # Login and confirm tenant
        Write-PSFHostColor -Level Host -DefaultColor gray -String "Choose the tenant and user to start the backup..."
        Write-PSFHostColor -Level Host -DefaultColor gray -String "You need to be a <c='white'>Power BI Administrator</c> to backup the tenant."
        try{
            Logout-PowerBI
            $PbiLogin = Login-PowerBI -ErrorAction Stop
        } catch{
            throw "Error trying to connect to Power BI tenant."
        }
        $TenantId = $PbiLogin.TenantId
        $UserName = $PbiLogin.UserName
        Write-Host
        Write-PSFHostColor -Level Host -DefaultColor gray -String "You are logged in as user <c='white'>$userName</c> in tenant <c='white'>$TenantId</c>." 
        Write-PSFHostColor -Level Host -DefaultColor gray -String "<c='white'>Would you like to start the backup? [y/n]: </c>"
        $confirmTenant = Read-Host
        Write-Host
        if ($confirmTenant -eq 'y'){
            # continue...
        } else{
            Write-PSFHostColor -Level Host -DefaultColor gray -String "Backup stopped."
            Exit
        }

        
        # Define path to workspaces
        $Path_Backup = Join-Path -Path $Path -ChildPath "Backup"
        $Path_Workspaces = Join-Path -Path $Path_Backup -ChildPath "Workspaces"
        $Path_Gateways = Join-Path -Path $Path_Backup -ChildPath "Gateways"

        # ===
        # Delete old workspace backups if exists?
        # =
        if (Test-Path $Path_Workspaces){
            Write-Warning "A workspace backup already exists."
            Write-PSFHostColor -Level Host -DefaultColor gray -String "Location: <c='white'>$Path_Workspaces</c>"
            Write-PSFHostColor -Level Host -DefaultColor gray -String "It is recommended to delete old backups to have a clean backup."
            Write-Host
            Write-PSFHostColor -Level Host -DefaultColor gray -String "<c='white'>Would you like to delete the old workspace backups? [y/n]: </c>"
            $confirmation = Read-Host
            Write-Host
            if ($confirmation -eq 'y'){
                Remove-Item -Path $Path_Workspaces -Force -Recurse
            } else{
                Write-PSFHostColor -Level Host -DefaultColor gray -String "Backup stopped."
                Exit
            }
        }

        # ===
        # Delete old gateway backups if exists?
        # =
        if (Test-Path $Path_Gateways){
            Write-Warning "A gateway backup already exists."
            Write-PSFHostColor -Level Host -DefaultColor gray -String "Location: <c='white'>$Path_Gateways</c>"
            Write-PSFHostColor -Level Host -DefaultColor gray -String "It is recommended to delete old backups to have a clean backup."
            Write-Host
            Write-PSFHostColor -Level Host -DefaultColor gray -String "<c='white'>Would you like to delete the old gateway backups? [y/n]</c>."
            $confirmation = Read-Host
            Write-Host
            if ($confirmation -eq 'y'){
                Remove-Item -Path $Path_Gateways -Force -Recurse
            } else{
                Write-PSFHostColor -Level Host -DefaultColor gray -String "Backup stopped."
                Exit
            }
        }

        # Define base URLs for API requests
        $RequestUrlBase = "https://api.powerbi.com/v1.0/myorg"


        # ===
        # Get gateways
        # =

        try{
            $RequestUrl = "$RequestUrlBase/gateways"
            $Source_Gateways = Invoke-PowerBIRestMethod -Url $RequestUrl -Method Get | ConvertFrom-Json
        } catch{
            throw "Error after calling request URL: `"$RequestUrl`"."
        }


        # ===
        # Export every gateway
        # =

        foreach ($Gateway in $Source_Gateways.value) {
            $Source_GatewayId = $Gateway.id
            Export-BsgPbiGateway -Source_GatewayId $Source_GatewayId -Path $Path
        }


        # ===
        # Get workspaces (API-Request)
        # =

        try{
            $RequestUrl = "$RequestUrlBase/groups"
            $Source_Workspaces = Invoke-PowerBIRestMethod -Url $RequestUrl -Method Get | ConvertFrom-Json
        } catch{
            throw "Error after calling request URL: `"$RequestUrl`"."
        }


        # ===
        # Backup every workspace
        # =

        foreach ($Workspace in $Source_Workspaces.value) {
            $Source_WorkspaceName = $Workspace.name
            Backup-BsgPbiWorkspace -Source_WorkspaceName $Source_WorkspaceName -Path $Path -PbiConnection $PbiLogin -MetadataOnly:$MetadataOnly.IsPresent
        }


        # ===
        # Get Activity Events
        # =
        if ($GetActivity.IsPresent){
            Get-BsgPbiActivity -Path $Path
        }

        Write-Host
        Write-Host
        Write-PSFHostColor -Level Host -DefaultColor white -String "---------------------------------------------------------------------------------------------"
        Write-Host
        Write-PSFHostColor -Level Host -DefaultColor gray -String " <c='green'>Tenant backup finished.</c>"
        Write-Host
        Write-PSFHostColor -Level Host -DefaultColor gray -String " Location: <c='white'>$Path</c>"
        Write-Host
        Write-PSFHostColor -Level Host -DefaultColor gray -String " Developed by <c='white'>BSGroup Data Analytics AG</c>"
        Write-PSFHostColor -Level Host -DefaultColor white -String "---------------------------------------------------------------------------------------------"
        Write-Host
        Write-Host

    } catch{
        Write-Host
        Stop-PSFFunction -Message "Failed to backup the tenant." -EnableException $False -Errorrecord $_
    }
}