1
votes

Say I have a release pipeline in Azure DevOps written in yaml which has two tasks, one for reading json from a file and the second one for setting a key into a different json file using the json read in the first task. I have the following pipeline.yml -

trigger:
- master

pool:
  vmImage: 'ubuntu-latest'

steps:
- task: PowerShell@2
  name: ReadMetadataJson
  inputs:
    filePath: 'MetadataReader.ps1'
    arguments: 'Run MetadataReader.ps1 -pathToMetadata metadata.json'
- task: PowerShell@2
  name: SetAppSetting
  inputs:
    filePath: 'AppSettingSetter.ps1'
    arguments: 'Run AppSettingSetter.ps1 -pathToAppSetting SomeApp/Data.json -appSettingKey testkey -appSettingValue $($(ReadMetadataJson)).testkey'
- script: echo $(ReadMetadataJson.metadata)

Below are the Powershell scripts being called from each tasks -

Powershell 1

# Read From the Metadata.json
param ($pathToMetadata)

echo $pathToMetadata
$metadata = Get-content $pathToMetadata | out-string | ConvertFrom-Json

Write-Output "Metadata Json from metadata reader ps script - $metadata"
echo "##vso[task.setvariable variable=metadata;]$metadata"

Powershell 2

# For now just accept the values in parameter and log them
param ($pathToAppSetting, $appSettingKey, $appSettingValue)

echo "pathToAppSetting : $pathToAppSetting"
echo "appSettingKey : $appSettingKey"
echo "appSettingValue : $appSettingValue"

# Code to set in another file. I have this working, so omitting for brevity

And these are the json files -

Metadata.json

{
  "testkey": "TestValueFromMetadata",
  "testkey1": "TestValueFromMetadata1"
}

appSetting.json

{
  "testkey": "TestValueInAppSetting",
  "testkey1": "TestValueInAppSetting1"
}

The problem is when I want to return the json data as output from the first task and use it in the second task to pass the parameter to the second powershell script. Below is a screenshot of the pipeline result after I run it.

enter image description here

As can be seen, it says ReadMetadataJson.metadata: command not found. I have been following the Microsoft document as a reference and have searched for other articles, but all I could find was handling values like string or integer, but not a json object. What is it that I am missing or doing wrong.

2
May I know how's the status of this before the weekend? Did you figure out this trouble now? Does my method is work for you? - Merlin Liang
@MerlinLiang-MSFT - Thank you for your answer. Though it kinda worked, but had some more scenarios coming in so came up with a different solution. May be I will include the structure in the question and then also provide my solution... - gkb
Sure! Looking forward to your solution shared:-) - Merlin Liang

2 Answers

2
votes

You can convert your JSON object to string (ConvertTo-Json) and pass it as variable to the second script.

Then on the second script, you just parse the string to JSON object again, using the ConvertFrom-Json method.

2
votes

Except the method that Hugo mentioned above, there has another solution can achieve what you want without any additional step added.

Just add one line into your MetadataReader.ps1:

param ($pathToMetadata)

echo $pathToMetadata
$metadata = Get-content $pathToMetadata | out-string | ConvertFrom-Json

$metadata | Get-Member -MemberType NoteProperty | % { $o = $metadata.($_.Name); Write-Host "##vso[task.setvariable variable=$($_.Name);isOutput=true]$o" }

Then, it will parse those json objects into corresponding variables after the json file contents get.

(I make use of the work logic of terroform outputs here)


Then you can directly use {reference name}.{object name} to call corresponding json value.

- task: PowerShell@2
  name: ReadMetadataJson
  inputs:
    filePath: 'MetadataReader.ps1'
    arguments: 'Run MetadataReader.ps1 -pathToMetadata metadata.json'

- task: PowerShell@2
  name: SetAppSetting
  inputs:
    filePath: 'AppSettingSetter.ps1'
    arguments: 'Run AppSettingSetter.ps1 -pathToAppSetting Data.json -appSettingKey testkey -appSettingValue $(ReadMetadataJson.testkey)'

- script: echo $(ReadMetadataJson.testkey)

Note: I made changes here: -appSettingValue $(ReadMetadataJson.testkey)

enter image description here