question

RoryFeng-2354 avatar image
0 Votes"
RoryFeng-2354 asked RoryFeng-2354 answered

when run a runbook in automation account how to get return code from script of VM OS to runbook

Hello

I am usring a runbook which fuction is to run a script of VM.

The runbook code is here.


param(
[Parameter(Mandatory = $true)]
[string] $ResourceGroupName,

 [Parameter(Mandatory = $true)]
 [string] $VirtualMachineName)

$connectionName = 'AzureRunAsConnection'

$conn = Get-AutomationConnection -Name $connectionName
Connect-AzAccount -ServicePrincipal -Tenant $conn.TenantID `
-ApplicationId $conn.ApplicationID -CertificateThumbprint $conn.CertificateThumbprint

 $GetAcsessToken = Get-AzAccessToken 
 $auth = $GetAcsessToken.token
 $authHeader = @{
     'Content-Type'='application/json'
     'Accept' = 'application/json'
     'Authorization'="Bearer $auth"
 }

$restUri = 'https://management.azure.com/subscriptions/xxxxxxxxxxxxxx/resourceGroups/' + $ResourceGroupName + '/providers/Microsoft.Compute/virtualMachines/' + $VirtualMachineName + '/runCommand?api-version=2019-03-01'

 $a_body = @{
     'commandId' = 'RunShellScript'
     'script' = @( '/tmp/test.sh')
 }


 # Rest API
 $response = Invoke-webrequest -Uri $restUri -Method post -Headers $authHeader -Body $($a_body | ConvertTo-Json) -UseBasicParsing
 $asyncstatus = $($response.headers.'Azure-AsyncOperation')
 $status = 'InProgress'

 While($status -eq 'InProgress')
 {
     Start-Sleep -s 5
     $response = invoke-webrequest -uri $asyncstatus -Headers $authHeader -UseBasicParsing
     $status = $($response.Content | ConvertFrom-Json).status
     Write-Output "Status : $status"

 }


The script code is here named test.sh




!/bin/bash


if [ -d ./foo ]; then
echo "there is an dirctory"
exit 0
else
echo "there is no dirctory"
exit 9
fi


There is no dirctory in the OS.

when i use this runbook how to get the number 9 to runbook.

I want a Failure status when I run this runbook by the return code.

Could someone help me to solve this problem.
If cannot get the return code from script plz let me know the detail.

Thanks so much.

Best regards.

azure-automation
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

AnuragSingh-MSFT avatar image
1 Vote"
AnuragSingh-MSFT answered

Hi @RoryFeng-2354,

Welcome to Microsoft Q&A! Apologies for the delayed response.

I did some tests with the provided scripts and was not able to find a direct way to get the exit code. However, using a driver script (which calls the test.sh script above), we can get the exit code by using $? - exit status of last operation. In my test, I placed the driver.sh in the /tmp directory and its content is:

 /bin/bash /tmp/test.sh
 ret=$?
 echo $ret

In the PowerShell Automation script, the script being called is /tmp/driver.sh. And I can get the result as below:

  #To retrieve the output/result back.
  $result = $response.Content | convertfrom-json
  $result.properties.output.value.message

Here, result.properties.output.value.message contains the complete output of that session in which the script executed, which is as below:

 Enable succeeded:    
 [stdout]
 there is no directory       #---echo message
 9                           #---Exit status when calling /temp/test.sh
    
 [stderr]                    #---Any message in error stream will be below this line

Please let me know if you have any questions.


Please 'Accept as answer' and ‘Upvote’ if it helped so that it can help others in the community looking for help on similar topics.

5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

RoryFeng-2354 avatar image
0 Votes"
RoryFeng-2354 answered AnuragSingh-MSFT commented

@AnuragSingh-MSFT

Thanks so much. Maybe have to way except your proposition·

Could I ask another qusetion.

I made many runbooks but same code like this runbook just want to run with different VM .

I set up same time to run those runbooks.
But I got one warning and an error:
warning: Unable to set default context 'Microsoft.Azure.Commands.Common.Authentication.Abstractions.AzureContext'.
error: System.Collections.Generic.KeyNotFoundException: The given key was not present in the dictionary. at System.Collections.Concurrent.ConcurrentDictionary`2.get_Item(TKey key) at Microsoft.Azure.Commands.Common.Authentication.AzureSession.c_DisplayClass82_0`1. UnregisterComponent b_0() at Microsoft.Azure.Commands.Profile.ConnectAzureRmAccountCommand.EndProcessing() at System.Management.Automation.CommandProcessorBase.Complete() + CategoryInfo : NotSpecified: (:) [Write-Error], WriteErrorException + FullyQualifiedErrorId : Microsoft.PowerShell.Commands.WriteErrorException


I think I did not use AzureRM command in this runbook. I checked use command Get-AzcontextAutosaveSetting. I found The contextFile is AzureRmtext.json

Is it the problem of file AzureRmtext.json. Is it file of AzureRM module. How to solve this problem.

Sorry to ask another question. I already asked Azure support japan but they do not give a good solution.

Hope could see your replay.
Thank you so much.

Best regards.

· 2
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

The result of Get-AzcontextAutosaveSetting

Mode : CurrentUser

ContextDirectory : C:\Users\Client.Azure

ContextFile : AzureRmContext.json

CacheDirectory : C:\Users\Client\AppData\Local.IdentityService

CacheFile : msal.cache

Settings : {}

0 Votes 0 ·

@RoryFeng-2354, thank you for the resonse.

Context Autosave feature is useful when a user consistently uses a set of machines for running Azure Cmdlets/script. For AzureAutomation, if you are not using Hybrid Worker, the execution happens in a sandbox where pre-saved context will not be useful.

Regarding your current issue, I'd suggest using try catch in runbook to retry the connection, if a failure occurs. You may also use clear-AzContext before trying to connect again, so that it removes any corrupt context.

If the suggestions above don’t help, please open a new Q&A thread with relevant information like below, so that the threads are scoped to specific queries to help the community.
1. Script used and where is it executed
2. Cmd/statement for which the failure occurs
3. Does it occur all the time?

In case you are facing this issue on your Local machine, this StackOverflow thread might be useful.
Please let me know if you have any questions. Please 'Accept as answer' and ‘Upvote’ my answer if it helped so that it can help others.

0 Votes 0 ·
RoryFeng-2354 avatar image
0 Votes"
RoryFeng-2354 answered

@AnuragSingh-MSFT

thanks so much for your massage.

I also use try catch in my runbook.

But when execution was happened the runbook will be abnormal termination with write-output an error.
With try catch command not only catch this issue but also catch others.

when catch this issue then use [clear-AzContext] before trying to connect again. But when try to connect again it is also possible to occur a same failure because at 0:00~1:00 this time have many runbook to run.

Thanks you again.

I will make a new Q&A.

Best regards.




5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.