Why does powershell give different result in one-liner than two-liner when converting JSON?

json, powershell

Solution

The solution is to wrap the first two operations with parenthesis:

PS C:\> ($orig | ConvertFrom-JSON) | ConvertTo-JSON
[
    {
        "Type":  "1",
        "Name":  "QA"
    },
    {
        "Type":  "2",
        "Name":  "DEV"
    }
]

The parenthesis allow you to grab the output of the first two operations all at once. Without them, powershell will attempt to parse any objects its gets separately. The collection of `PSCustomObject` resulting from `$orig | ConvertFrom-JSON` contains two `PSCustomObjects` for the 1/QA and 2/DEV pairs, so by piping the output of that collection powershell attempts to handle the key/value pairs one-at-a-time.

Using parenthesis is a shorter way of "grouping" that output and allows you to operate on it without making a variable.

Problem

Overview From a powershell 3 prompt,, I want to call a RESTful service, get some JSON, and pretty-print it. I discovered that if I convert the data to a powershell object, and then convert the powershell object back to json, I get back a nice pretty-printed string. However, if I combine the two conversions into a one-liner with a pipe I will get a different result. TL;DR: this: ``` PS> $psobj = $orig | ConvertFrom-JSON PS> $psobj | ConvertTo-JSON ``` ... gives me different result than this: ``` PS> $orig | ConvertFrom-JSON | ConvertTo-JSON ``` Original data ``` [ { "Type": "1", "Name": "QA" }, { "Type": "2", "Name": "whatver" } ] ``` Doing the conversion in two steps I'm going to remove the whitespace (so it fits on one line...), convert it to a powershell object, and then convert it back to JSON. This works well, and gives me back the correct data: ``` PS> $orig = '[{"Type": "1","Name": "QA"},{"Type": "2","Name": "DEV"}]' PS> $psobj = $orig | ConvertFrom-JSON PS> $psobj | ConvertTo-JSON [ { "Type": "1", "Name": "QA" }, { "Type": "2", "Name": "DEV" } ] ``` Combining the two steps with a pipe However, if I combine those last two statements into a one-liner, I get a different result: ``` PS> $orig | ConvertFrom-JSON | ConvertTo-JSON { "value": [ { "Type": "1", "Name": "QA" }, { "Type": "2", "Name": "DEV" } ], "Count": 2 } ``` Notice the addition of the keys "value" and "Count". Why is there a difference? I'm sure it has something to do with the desire to return JSON object rather than a JSON array, but I don't understand why the way I do the conversion affects the end result.

Original source