【问题标题】:Reading a json file in key value pair in the same order that's given in input以与输入中给出的相同顺序读取键值对中的 json 文件
【发布时间】:2019-12-16 21:26:06
【问题描述】:

我正在编写一个 PowerShell 脚本,它将读取一个具有不同部分的 json 文件,例如 job1、job2 等。现在我的目标是分别读取每个部分并将其作为键值对循环。我还需要维护输入文件的顺序,因为作业是按顺序安排的。这些作业将 json 文件中的值作为输入运行。

我尝试使用 Powershell 5.1 版,我在其中创建了 PSCustomObject,但顺序按字母顺序排序,这是我不想要的。


Json 文件:

{ "Job1": [
        {
    "Ram"                                   : "India",
    "Anthony"                               : "London",
    "Elena"                                 : "Zurich"
    }],

    "Job2": [
            { 
    "Build"                                : "fail",
    "Anthony"                              : "right",
    "Sam"                                  : "left"

    }]}

$json = Get-Content -Path C:\PowershellScripts\config_File.json | 
ConvertFrom-Json

$obj = $json.Job1

$json.Job1 | Get-Member -MemberType NoteProperty | ForEach-Object {

$key = $_.Name
$values  = [PSCustomObject][ordered]@{Key = $key; Value = $obj."$key"}
$values
}

我希望按照 json 文件中提供的顺序分别循环遍历每个部分。例如,遍历 Job1 部分并以与 json 文件中相同的顺序仅获取值。

【问题讨论】:

  • 您会考虑使用经典的 for 循环吗? for($i=0;$i-lt $json.Job1.count;$i++){..your stuff here..}

标签: json powershell powershell-3.0


【解决方案1】:

我保证这不是最好的方法,但它确实有效。

$json = Get-Content -Path C:\PowershellScripts\config_File.json | 
    ConvertFrom-Json
$out = ($json.Job1 | Format-List | Out-String).Trim() -replace "\s+(?=:)|(?<=:)\s+"
$out -split "\r?\n" | ForEach-Object {
    [PSCustomObject]@{Key = $_.Split(":")[0]; Value = $_.Split(":")[1]}
}

说明:

首先使用Format-List 输出JSON 对象以生成Property : Value 格式,然后通过管道传送到Out-String 以使该输出成为单个字符串。 Trim() 用于去除周围的空白。

-replace 删除 : 字符前后的所有空格。

-split \r?\n 将单个字符串拆分为行数组。然后,这些行中的每一行都由: 字符(.Split(":"))分割。 [0] 索引选择: 左侧的字符串。 [1] 选择: 右侧的字符串。

【讨论】:

  • 它工作正常,但对于名称较大的 json 文件,它不起作用。例如,我的 json 文件的一些内容类似于:Serviceability Deployment Package" : "Customer_DeployWestpacServiceabilityDeploymentPackage"。它不适用于此。
  • 对。实际上,每个 Job 大约有 20 个值。在产生问题的值之间输入了新行,删除新行后它工作正常。谢谢老兄..
  • 你能解释一下你在这里使用的正则表达式吗?它的行为非常奇怪。有时它可以正常工作,但有时它会拆分值的最后几个字母。
  • 我在答案中添加了解释。
【解决方案2】:

你能改变 json 架构吗? 在尝试解析它之前,我可能会更改 json 模式(当然,如果可能的话)。 像这样(只改变了Job1):

$json = @"
{ "Job1": [
        {
            "Name": "Ram",
            "Location" : "India"
        },
        {
            "Name": "Anthony",
            "Location": "London"
        },
        {
            "Name": "Elena" ,
            "Location": "Zurich"
        }
    ],

    "Job2": [
            { 
    "Build"                                : "fail",
    "Anthony"                              : "right",
    "Sam"                                  : "left"

    }]}
"@ | convertfrom-json


foreach ($obj in $json.Job1) {

    $key = $obj.Name
    $values = [PSCustomObject][ordered]@{Key = $key; Value = $obj."$key" }
    $values
}

【讨论】:

  • 您的逻辑看起来不错并且按预期工作,但大小/否。的行变得巨大。让我们看看其他人怎么说。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-03-16
  • 1970-01-01
  • 1970-01-01
  • 2017-09-21
  • 2011-06-16
  • 2015-06-17
  • 2014-01-06
相关资源
最近更新 更多