使用bash中的jq对json doc进行链式选择和max_by

时间:2016-09-07 00:30:02

标签: json bash jq

我想获取具有最大SnapshotCreateTime的快照的SnapshotIdentifier,并通过ClusterIdentifier对其进行过滤。这是我正在使用的命令:

aws redshift describe-cluster-snapshots --region us-west-2 |
  jq -r '.Snapshots[]
         | select(.ClusterIdentifier == "dev-cluster")
         | max_by(.SnapshotCreateTime) 
         | .SnapshotIdentifier '

这是json

{
    "Snapshots": [        
        {
                "EstimatedSecondsToCompletion": 0, 
                "OwnerAccount": "45645641155", 
                "CurrentBackupRateInMegaBytesPerSecond": 6.2857, 
                "ActualIncrementalBackupSizeInMegaBytes": 22.0, 
                "NumberOfNodes": 3, 
                "Status": "available", 
                "VpcId": "myvpc", 
                "ClusterVersion": "1.0", 
                "Tags": [], 
                "MasterUsername": "ayxbizops", 
                "TotalBackupSizeInMegaBytes": 192959.0, 
                "DBName": "dev", 
                "BackupProgressInMegaBytes": 22.0, 
                "ClusterCreateTime": "2016-09-06T15:56:08.170Z", 
                "RestorableNodeTypes": [
                    "dc1.large"
                ], 
                "EncryptedWithHSM": false, 
                "ClusterIdentifier": "dev-cluster", 
                "SnapshotCreateTime": "2016-09-06T16:00:25.595Z", 
                "AvailabilityZone": "us-west-2c", 
                "NodeType": "dc1.large", 
                "Encrypted": false, 
                "ElapsedTimeInSeconds": 3, 
                "SnapshotType": "manual", 
                "Port": 5439, 
                "SnapshotIdentifier": "thismorning"
        }
    ]
}

1 个答案:

答案 0 :(得分:4)

  1. max_by期望数组作为输入。因此,您的过滤器的以下变体将起作用:

    [.Snapshots[] | select(.ClusterIdentifier == "dev-cluster")]
    | max_by(.SnapshotCreateTime)
    | .SnapshotIdentifier
    
  2. 根据您的口头描述,您似乎希望在max_by之前运行select

    .Snapshots
    | max_by(.SnapshotCreateTime)
    | select(.ClusterIdentifier == "dev-cluster")
    | .SnapshotIdentifier
    
  3. 如果可能有多个最大对象,您可能希望使用maximal_by而不是max_by

    def maximal_by(f):
      (map(f) | max) as $mx
      | .[] | select(f == $mx);