Powershell'de json'dan csv'ye dönüştür

Sep 23 2020

bu benim csv'm:

"name,data
Play,http://{gho}.domain.com/
BDomain,domain.com
Charts,2
Compress,0
CompressJ,0" | ConvertFrom-Csv | ConvertTo-Json

Bana verir:

[
{
    "name":  "Play",
    "data":  "http://{gho}.domain.com/"
},
{
    "name":  "BDomain",
    "data":  "domain.com"
},
{
    "name":  "Charts",
    "data":  "2"
},
{
    "name":  "Compress",
    "data":  "0"
},
{
    "name":  "CompressJ",
    "data":  "0"
}
]

Şimdi o csv'yi json'umdan geri almak istiyorum, ancak | ConvertFrom-Json | ConvertTo-CSV çalışmıyor ve neden olmasın merak ediyorum?

Yanıtlar

1 mklement0 Sep 25 2020 at 05:11

Steven'ın yararlı cevabını kısa ve öz bir özet ve çapraz baskı perspektifiyle tamamlamak için :

  • In PowerShell [Çekirdek] v7 + ' , hiçbir ekstra çaba gereklidir: ekleme | ConvertFrom-Json | ConvertTo-Csvolduğu gibi kodunuzu çalışır.

  • In Windows PowerShell ve PowerShell [Çekirdek] V6.x yapmanız gerekenler kuvvet numaralandırma arasında ConvertFrom-Jsonsırayla bireyin çıktı ConvertTo-CsvPowerShell her zamanki davranışları karşısında, çünkü doğru işe ConvertFrom-Jsonbir JSON dizisi çıktılar bir bütün olarak tek bir nesne olarak, boru hattına .

    • V7 + değişikliğine yol açan bu davranışın olağandışı olması gerçeğidir - arka plan bilgileri için bu yanıta bakın .

    • Kuvvet numaralandırma en basit yolu - bir çıkış-as-a-Bütün dizinin / koleksiyonun elemanları göndermeye yani tek tek boru hattına kullanımına olduğunu (...), gruplama operatörü .

# Works in all PowerShell versions, but in v7+ the (...) is no longer necessary.
(
"name,data
Play,http://{gho}.domain.com/
BDomain,domain.com
Charts,2
Compress,0
CompressJ,0" | ConvertFrom-Csv | ConvertTo-Json |
  ConvertFrom-Json
) | ConvertTo-Csv -NoTypeInformation

Bu, şunları verir:

"name","data"
"Play","http://{gho}.domain.com/"
"BDomain","domain.com"
"Charts","2"
"Compress","0"
"CompressJ","0"
2 Steven Sep 22 2020 at 23:59

Çıktı ConvertFrom-Json, boru hattından bu şekilde geçirilen tek dizidir. Bu, ConvertFrom-Jsonçıktısının nasıl yazıldığının bir sonucudur . Muhtemelen Write-Outputher nesneyi oluşturuldukları sırada ardışık düzen boyunca akışa almak yerine, her şeyi topluyor ve diziyi tek bir komutta (örtük veya başka türlü) çıkarıyor. Muhtemelen cmdlet'in nasıl yazıldığının bir sonucudur ve gerekli olabilir.

Mevcut kodunuz büyük olasılıkla aşağıdaki gibi bir csv oluşturuyor:

"Count","Length","LongLength","Rank","SyncRoot","IsReadOnly","IsFixedSize","IsSynchronized"
"5","5","5","1","System.Object[]","False","True","False"

Bunlar dizinin özellikleridir, içindeki nesneler değil. Etrafından dolaşmanın bir yolu, verileri bir değişkene park etmektir:

$Json = "name,data Play,http://{gho}.domain.com/ BDomain,domain.com Charts,2 Compress,0 CompressJ,0" | ConvertFrom-Csv | ConvertTo-Json # Now you can convert back to csv without issue: $Json = $Json | ConvertFrom-Json $Json | ConvertTo-Csv -NoTypeInformation

Not: Doğrudan $Json | ConvertFrom-Json | ConvertTo-Csv...sizin gibi $ Json gönderirseniz aynı sorunu yaşayabilirsiniz.

Json nesnelerini yinelemek de işe yarıyor gibi görünüyor:

$Json = "name,data Play,http://{gho}.domain.com/ BDomain,domain.com Charts,2 Compress,0 CompressJ,0" | ConvertFrom-Csv | ConvertTo-Json $Json | 
ConvertFrom-Json |
ForEach-Object{ $_ } | 
ConvertTo-Csv -NoTypeInformation

@Notjustme sayesinde, bunu aşağıdaki (...)gibi kısaltabilirsiniz :

($json | ConvertFrom-Json) | ConvertTo-Csv

Not: mklement0'ın cevabı başına düzeltildi .

Bu seçeneklerin tümü, esas olarak diziyi, dahili davranışını atlamak için borunun önüne yerleştiriyor. ConvertFrom-Json

Yine, ConvertFrom-Json'ın neden bu şekilde davrandığından% 100 emin değilim. Daha resmi bir açıklama bulduğumda ek bilgilerle güncelleme yapacağım.