10

I have json that looks like this:

{
    "Workflow": [
        {
            "Parameters": {
                "Project": "/Path/To/File",
                "OtherParam": "True"
            }
        }
    ],
    "Overrides": [
        {
            "Special": {
                "Parameters": {
                    "NewParam": "NewStuffGoesHere",
                    "OtherParam": "False"
                }
            }
        }
    ]
}

... where I want to use the Overrides.Special section to add or update fields in the workflow object. In other words, given the json above, I want to do something like this:

$config = Get-Content workflow.json | out-string | ConvertFrom-Json
$configWithOverrides = Merge-Object $config.Workflow $config.Overrides.Special

And end up with something like this:

$configWithOverrides

Parameters
----------
@{Project=/Path/To/File; NewParam=NewStuffGoesHere; OtherParam=False}

I can certainly write the Merge-Object function above to add or update values as needed based on what's in the override section, but it seems there should (could?) be a built-in or one-liner way to handle this.

I tried this:

$test = $config.Workflow + $config.Overrides.Special

...but that doesn't quite work.

$test
Parameters
----------
@{Project=/Path/To/File; OtherParam=True}
@{NewParam=NewStuffGoesHere; OtherParam=False}

This enables adding parameters:

>$test.Parameters.NewParam
NewStuffGoesHere

...but it's not so great for updating them

>$test.Parameters.OtherParam
True
False

Note - in this example, I'm choosing to handle the merge after converting the json to a psobject, but that's not a requirement.

5
  • Possible: stackoverflow.com/questions/29670111/… Commented May 20, 2015 at 20:24
  • That solution doesn't work (actually not convinced it works for the problem described there either). I added some more information above to make it clear why a straight '+' of the nodes is inadequate. Commented May 20, 2015 at 20:59
  • Last time I will try: stackoverflow.com/questions/29330627/… perhaps is more what you were leaning to. Although it's a function based answer which you stated you were capable of doing Commented May 20, 2015 at 21:04
  • I have a hunch this is the answer, and is pretty much what I was thinking. I'll go ahead and write (continue) writing this merge while I wait to see if something else exists. Thanks! Commented May 20, 2015 at 21:07
  • It is not build-in (maybe it should) but using this Join-Object cmdlet: $config.Workflow.Parameters | Merge $config.Overrides.Special.Parameters | ConvertTo-Json{"Project":"/Path/To/File","OtherParam":"False","NewParam":"NewStuffGoesHere"} (see also: Merge two json objects) Commented Nov 18, 2019 at 10:26

1 Answer 1

7

I have a one-liner to do what you're asking for. Notice that, as far as I know, PowerShell does not deal directly with json strings. But, once converted to PowerShell objects, it's like any other object.

So, firstly, define your json file, and read it as a single string:

# Requires -Version 4
$jsonFile='c:\temp\jsonfile.json'
$jsonObj=@(gc $jsonFile -raw)|ConvertFrom-Json

Define the property upon which you want to merge the json's objects, and the 1st and 2nd objects:

$property='Parameters'
$1=$jsonObj.Workflow.$property
$2=$jsonObj.Overrides.Special.$property

Now, see the one-liner (which I've splitted in 3, for the sake of clarity):

$MergedJson=[pscustomobject]@{
    $property=$2.psobject.properties|%{$11=$1}{$11|add-member $_.name   $_.value -ea Ignore}{$11}
}|ConvertTo-Json

You see? $MergedJson holds the following string (using your json string):

{
    "Parameters":  {
                       "Project":  "/Path/To/File",
                       "OtherParam":  "True",
                       "NewParam":  "NewStuffGoesHere"
                   }
}

Is that what you're looking for?

P.S.: if you swap the roles of $1 and $2, the common parameters' (like OtherParam) values that prevail, change.

Sign up to request clarification or add additional context in comments.

2 Comments

Marked as answer - I wrote a longer version in the meantime, but will refactor to this solution shortly. Thanks
Can you share the longer version please!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.