skip to Main Content

I’m using an Azure runbook within an automation account and encountering an issue. I’ve already downloaded all the necessary modules and applied the necessary permissions as well. Below is the code and the error.

Code:

<#
.Synopsis
Automation Account Script

.DESCRIPTION
This script process and creates the Azure Resource Inventory Excel sheet running on an Azure Automation Account and saving the file to a StorageAccount. 

.Link
https://github.com/microsoft/ARI/Automation/ARI_Automation.ps1

.COMPONENT
This powershell Script is part of Azure Resource Inventory (ARI)

.NOTES
Version: 3.1.7
Authors: Claudio Merola

Core Steps:
1 ) Create System Identity
2 ) Give Read Permissions to the System Identity in the Management Group
3 ) Create Blob Storage Account
4 ) Create Container
5 ) Give "Storage Blob Data Contributor" Permissions to the System Identity on the Storage Account
6 ) Create Runbook Powershell with Runtime 7.2
7 ) Add modules "ImportExcel", "Az.ResourceGraph", "Az.Storage", "Az.Account" and "ThreadJob" (Runtime 7.2)

#>

<######################################################### VARIABLES ######################################################################>

#StorageAccount Name
$STGACC = "aristorageautomation"

#Container Name
$STGCTG = 'arireports'

#Include Tags
$InTag = $false

#Lite
$RunLite = $true

#Debug
$RunDebug = $true


<######################################################### SCRIPT ######################################################################>

if($RunDebug)
    {
        Write-Output ('Debugging Enable.')
    }

# Ensures you do not inherit an AzContext in your runbook
$null = Disable-AzContextAutosave -Scope Process

# Connect using a Managed Service Identity
try {
    $AzureConnection = (Connect-AzAccount -Identity).context
}
catch {
    Write-Output "There is no system-assigned user identity. Aborting." 
    exit
}

# set and store context
$AzureContext = Set-AzContext -SubscriptionName $AzureConnection.Subscription -DefaultProfile $AzureConnection

$Context = New-AzStorageContext -StorageAccountName $STGACC -UseConnectedAccount

$aristg = $STGCTG

$TableStyle = "Light20"

$Date = get-date -Format "yyyy-MM-dd_HH_mm"
$DateStart = get-date

$File = ("ARI_Automation_Report_"+$Date+".xlsx")


$Resources = @()
$Advisories = @()
$Subscriptions = ''

$Repo = 'https://api.github.com/repos/microsoft/ari/git/trees/main?recursive=1'
$RawRepo = 'https://raw.githubusercontent.com/microsoft/ARI/main'

<######################################################### ADVISORY EXTRACTION ######################################################################>

Write-Output 'Extracting Advisories'

    $AdvSize = Search-AzGraph -Query "advisorresources | summarize count()"
    $AdvSizeNum = $AdvSize.'count_'

    if ($AdvSizeNum -ge 1) {
        $Loop = $AdvSizeNum / 1000
        $Loop = [math]::ceiling($Loop)
        $Looper = 0
        $Limit = 1

        while ($Looper -lt $Loop) 
            {
                $Looper ++
                $Advisor = Search-AzGraph -Query "advisorresources | order by id asc" -skip $Limit -first 1000
                $Advisories += $Advisor
                Start-Sleep 2
                $Limit = $Limit + 1000
            }
    } 


$Subscriptions = Get-AzSubscription | Where-Object {$_.State -ne 'Disabled'}
$Subscriptions = $Subscriptions
if($RunDebug)
{
    $Subcount = $Subscriptions.count
    Write-Output ("Subscriptions found: $Subcount")
}

<######################################################### RESOURCE EXTRACTION ######################################################################>

Write-Output 'Extracting Resources'

    Foreach ($Subscription in $Subscriptions) {

        if($RunDebug)
            {
                Write-Output ('DEBUG - extracting resources for the subscription: '+$Subscription)
                Write-Output ('')
            }
        $SUBID = $Subscription.id
        Set-AzContext -Subscription $SUBID | Out-Null
                    
        $EnvSize = Search-AzGraph -Query "resources | where subscriptionId == '$SUBID' and strlen(properties) < 123000 | summarize count()"
        $EnvSizeNum = $EnvSize.count_
                        
        if ($EnvSizeNum -ge 1) {
            $Loop = $EnvSizeNum / 1000
            $Loop = [math]::ceiling($Loop)
            $Looper = 0
            $Limit = 1
    
            while ($Looper -lt $Loop) {
                $Resource0 = Search-AzGraph -Query "resources | where subscriptionId == '$SUBID' and strlen(properties) < 123000 | order by id asc" -skip $Limit -first 1000
                $Resources += $Resource0
                Start-Sleep 2
                $Looper ++
                $Limit = $Limit + 1000
            }
        }        
    }   
    
$ExtractionRunTime = get-date

$ModuSeq = (New-Object System.Net.WebClient).DownloadString($RawRepo + '/Extras/Support.json')
$Unsupported = $ModuSeq | ConvertFrom-Json


<######################################################### ADVISORY JOB ######################################################################>


Write-Output ('Starting Advisory Job')

$ModuSeq = (New-Object System.Net.WebClient).DownloadString($RawRepo + '/Extras/Advisory.ps1')

$ScriptBlock = [Scriptblock]::Create($ModuSeq)

Start-ThreadJob -Name 'Advisory' -ScriptBlock $ScriptBlock -ArgumentList $Advisories, 'Processing' , $File


<######################################################### SUBSCRIPTIONS JOB ######################################################################>

Write-Output ('Starting Subscription Job')

$ModuSeq = (New-Object System.Net.WebClient).DownloadString($RawRepo + '/Extras/Subscriptions.ps1')

$ScriptBlock = [Scriptblock]::Create($ModuSeq)

Start-ThreadJob -Name 'Subscriptions' -ScriptBlock $ScriptBlock -ArgumentList $Subscriptions, $Resources, 'Processing' , $File


<######################################################### RESOURCES ######################################################################>


Write-Output ('Starting Resources Processes')

$OnlineRepo = Invoke-WebRequest -Uri $Repo
$RepoContent = $OnlineRepo | ConvertFrom-Json
$Modules = ($RepoContent.tree | Where-Object {$_.path -like '*.ps1' -and $_.path -notlike 'Extras/*' -and $_.path -ne 'AzureResourceInventory.ps1' -and $_.path -notlike 'Automation/*'}).path

foreach ($Module in $Modules) 
    {
        $SmaResources = @{}

        if($RunDebug)
            {
                Write-Output ''
                Write-Output ('DEBUG - Running Module: '+$Module)
            }

        $Modul = $Module.split('/')
        $ModName = $Modul[2].Substring(0, $Modul[2].length - ".ps1".length)
        $ModuSeq = (New-Object System.Net.WebClient).DownloadString($RawRepo + '/' + $Module)

        $ScriptBlock = [Scriptblock]::Create($ModuSeq)

        $SmaResources[$ModName] = Invoke-Command -ScriptBlock $ScriptBlock -ArgumentList $PSScriptRoot, $Subscriptions, $InTag, $Resources, 'Processing', $true

        Write-Output ('Resources ('+$ModName+'): '+$SmaResources[$ModName].count)

        Invoke-Command -ScriptBlock $ScriptBlock -ArgumentList $PSScriptRoot,$null,$InTag,$null,'Reporting',$File,$SmaResources,$TableStyle,$Unsupported | Out-Null

    }


<######################################################### ADVISORY REPORTING ######################################################################>

if($RunDebug)
    {
        Write-Output ('DEBUG - Reporting Advisories.')
    }

get-job -Name 'Advisory' | Wait-Job | Out-Null

$Adv = Receive-Job -Name 'Advisory'

$ModuSeq = (New-Object System.Net.WebClient).DownloadString($RawRepo + '/Extras/Advisory.ps1')

$ScriptBlock = [Scriptblock]::Create($ModuSeq)

Invoke-Command -ScriptBlock $ScriptBlock -ArgumentList $null,'Reporting',$file,$Adv,$TableStyle

<######################################################### SUBSCRIPTIONS REPORTING ######################################################################>


if($RunDebug)
    {
        Write-Output ('DEBUG - Reporting Subscription .')
    }

get-job -Name 'Subscriptions' | Wait-Job | Out-Null

$AzSubs = Receive-Job -Name 'Subscriptions'

$ModuSeq = (New-Object System.Net.WebClient).DownloadString($RawRepo + '/Extras/Subscriptions.ps1')

$ScriptBlock = [Scriptblock]::Create($ModuSeq)

Invoke-Command -ScriptBlock $ScriptBlock -ArgumentList $null,$null,'Reporting',$file,$AzSubs,$TableStyle

<######################################################### CHARTS ######################################################################>

if($RunDebug)
    {
        Write-Output ('DEBUG - Reporting Charts.')
    }

$ReportingRunTime = get-date

$ExtractionRunTime = (($ExtractionRunTime) - ($DateStart))

$ReportingRunTime = (($ReportingRunTime) - ($DateStart))

$ModuSeq = (New-Object System.Net.WebClient).DownloadString($RawRepo + '/Extras/Charts.ps1')

$ScriptBlock = [Scriptblock]::Create($ModuSeq)

$FileFull = ((Get-Location).Path+''+$File)

Invoke-Command -ScriptBlock $ScriptBlock -ArgumentList $FileFull,'Light20','Azure Automation',$Subscriptions,$Resources.Count,$ExtractionRunTime,$ReportingRunTime,$RunLite

<######################################################### UPLOAD FILE ######################################################################>

Write-Output 'Uploading Excel File to Storage Account'

Set-AzStorageBlobContent -File $File -Container $aristg -Context $Context | Out-Null
if($Diagram){Set-AzStorageBlobContent -File $DDFile -Container $aristg -Context $Context | Out-Null}

Write-Output 'Completed'

Error:

System.Management.Automation.CommandNotFoundException: The 'New-AzStorageContext' command was found in the module 'Az.Storage', but the module could not be loaded. For more information, run 'Import-Module Az.Storage'.
   at System.Management.Automation.CommandDiscovery.TryModuleAutoDiscovery(String commandName, ExecutionContext context, String originalCommandName, CommandOrigin commandOrigin, SearchResolutionOptions searchResolutionOptions, CommandTypes commandTypes, Exception& lastError)
   at System.Management.Automation.CommandDiscovery.LookupCommandInfo(String commandName, CommandTypes commandTypes, SearchResolutionOptions searchResolutionOptions, CommandOrigin commandOrigin, ExecutionContext context)
   at System.Management.Automation.CommandDiscovery.LookupCommandInfo(String commandName, CommandOrigin commandOrigin, ExecutionContext context)
   at System.Management.Automation.CommandDiscovery.LookupCommandInfo(String commandName, CommandOrigin commandOrigin)
   at System.Management.Automation.CommandDiscovery.LookupCommandProcessor(String commandName, CommandOrigin commandOrigin, Nullable`1 useLocalScope)
   at System.Management.Automation.ExecutionContext.CreateCommand(String command, Boolean dotSource)
   at System.Management.Automation.PipelineOps.AddCommand(PipelineProcessor pipe, CommandParameterInternal[] commandElements, CommandBaseAst commandBaseAst, CommandRedirection[] redirections, ExecutionContext context)
   at System.Management.Automation.PipelineOps.InvokePipeline(Object input, Boolean ignoreInput, CommandParameterInternal[][] pipeElements, CommandBaseAst[] pipeElementAsts, CommandRedirection[][] commandRedirections, FunctionContext funcContext)
   at System.Management.Automation.Interpreter.ActionCallInstruction`6.Run(InterpretedFrame frame)
   at System.Management.Automation.Interpreter.EnterTryCatchFinallyInstruction.Run(InterpretedFrame frame)
   at System.Management.Automation.Interpreter.EnterTryCatchFinallyInstruction.Run(InterpretedFrame frame)

System.Management.Automation.RuntimeException: You cannot call a method on a null-valued expression.
   at CallSite.Target(Closure , CallSite , Object , String )
   at System.Dynamic.UpdateDelegates.UpdateAndExecute2[T0,T1,TRet](CallSite site, T0 arg0, T1 arg1)
   at System.Management.Automation.Interpreter.DynamicInstruction`3.Run(InterpretedFrame frame)
   at System.Management.Automation.Interpreter.EnterTryCatchFinallyInstruction.Run(InterpretedFrame frame)
Uploading Excel File to Storage Account
System.Management.Automation.CommandNotFoundException: The 'Set-AzStorageBlobContent' command was found in the module 'Az.Storage', but the module could not be loaded. For more information, run 'Import-Module Az.Storage'.
   at System.Management.Automation.CommandDiscovery.TryModuleAutoDiscovery(String commandName, ExecutionContext context, String originalCommandName, CommandOrigin commandOrigin, SearchResolutionOptions searchResolutionOptions, CommandTypes commandTypes, Exception& lastError)
   at System.Management.Automation.CommandDiscovery.LookupCommandInfo(String commandName, CommandTypes commandTypes, SearchResolutionOptions searchResolutionOptions, CommandOrigin commandOrigin, ExecutionContext context)
   at System.Management.Automation.ExecutionContext.CreateCommand(String command, Boolean dotSource)
   at System.Management.Automation.PipelineOps.AddCommand(PipelineProcessor pipe, CommandParameterInternal[] commandElements, CommandBaseAst commandBaseAst, CommandRedirection[] redirections, ExecutionContext context)
   at System.Management.Automation.PipelineOps.InvokePipeline(Object input, Boolean ignoreInput, CommandParameterInternal[][] pipeElements, CommandBaseAst[] pipeElementAsts, CommandRedirection[][] commandRedirections, FunctionContext funcContext)
   at System.Management.Automation.Interpreter.ActionCallInstruction`6.Run(InterpretedFrame frame)
   at System.Management.Automation.Interpreter.EnterTryCatchFinallyInstruction.Run(InterpretedFrame frame)

System.Management.Automation.RuntimeException: Cannot index into a null array.
   at CallSite.Target(Closure , CallSite , Object , String )
   at System.Dynamic.UpdateDelegates.UpdateAndExecute2[T0,T1,TRet](CallSite site, T0 arg0, T1 arg1)
   at System.Management.Automation.Interpreter.DynamicInstruction`3.Run(InterpretedFrame frame)
   at System.Management.Automation.Interpreter.EnterTryCatchFinallyInstruction.Run(InterpretedFrame frame)
System.Management.Automation.RuntimeException: Cannot index into a null array.
   at CallSite.Target(Closure , CallSite , Object , String )
   at System.Dynamic.UpdateDelegates.UpdateAndExecute2[T0,T1,TRet](CallSite site, T0 arg0, T1 arg1)
   at System.Management.Automation.Interpreter.DynamicInstruction`3.Run(InterpretedFrame frame)
   at System.Management.Automation.Interpreter.EnterTryCatchFinallyInstruction.Run(InterpretedFrame frame)
System.Management.Automation.RuntimeException: You cannot call a method on a null-valued expression.
   at CallSite.Target(Closure , CallSite , Object , String )
   at System.Dynamic.UpdateDelegates.UpdateAndExecute2[T0,T1,TRet](CallSite site, T0 arg0, T1 arg1)
   at System.Management.Automation.Interpreter.DynamicInstruction`3.Run(InterpretedFrame frame)
   at System.Management.Automation.Interpreter.EnterTryCatchFinallyInstruction.Run(InterpretedFrame frame)

2

Answers



  1. Need to check below:

    This type of error throws when a specific resource module is not being loaded properly.

    • Add Import-Module Az.Storage command before executing storage related commands.
    • Check the module you have installed matches with the version of the PowerShell runbook and script.
    • Check that you added an Automation contributor role for an automation account under Access control.

    enter image description here

    If still the issue persists, delete the installed module and install it again. Refer blog by @Bas Wijdenes for relevant information.

    I tried below code in an automation account as you and it worked as expected.

    $STGACC = "newaccs"
    $cont = "latest"
    $InTag = $false
    $RunLite = $true
    $RunDebug = $true
    if($RunDebug)
        {
            Write-Output ('Debugging Enable.')
        }
    $null = Disable-AzContextAutosave -Scope Process
    try {
        $AzureConnection = (Connect-AzAccount -Identity).context
    }
    catch {
        Write-Output "There is no system-assigned user identity. Aborting." 
        exit
    }
    Import-Module Az.Storage
    $AzureContext = Set-AzContext -SubscriptionName $AzureConnection.Subscription -DefaultProfile $AzureConnection
    $Context = New-AzStorageContext -StorageAccountName $STGACC -UseConnectedAccount
    Write-Output context is $Context
    

    Output:

    enter image description here

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search