Bash 변수를 JSON 키 및 값으로 객체에 추가

Bash 변수를 JSON 키 및 값으로 객체에 추가

이와 같은 JSON 개체 배열이 있습니다.

[
  {
    "id" : "tmp1387816934708382026",
    "owner" : "john",
    "x11-display" : ":5",
    "x11-authority" : "/run/user/john/dcv/tmp1387816934708382026.xauth",
    "num-of-connections" : 1,
    "creation-time" : "2019-05-14T14:12:14.989287Z",
    "last-disconnection-time" : "2019-05-31T18:58:42.851223Z"
  },
  {
    "id" : "tmp4241942441012516520",
    "owner" : "mike",
    "x11-display" : ":10",
    "x11-authority" : "/run/user/mike/dcv/tmp4241942441012516520.xauth",
    "num-of-connections" : 0,
    "creation-time" : "2019-05-17T16:23:05.891531Z",
    "last-disconnection-time" : "2019-05-19T11:23:30.844797Z"
  }
]

days-idleBash 스크립트에서 계산된 모든 객체에 값 이름의 키를 추가 해야 합니다 . 이것이 제가 모든 JSON 객체에서 찾고 있는 것입니다.

{
    "id" : "tmp1387816934708382026",
    "owner" : "mike",
    "x11-display" : ":5",
    "x11-authority" : "/run/user/mike/dcv/tmp1387816934708382026.xauth",
    "num-of-connections" : 1,
    "creation-time" : "2019-05-14T14:12:14.989287Z",
    "last-disconnection-time" : "2019-05-31T18:58:42.851223Z",
    "days-idle" : "$daysIdle"
  }

키를 추가할 수 있다는 것을 알고 있지만 jq값이 bash 변수인 키, 값 쌍을 추가하는 방법을 잘 모르겠습니다.

답변1

특정 값을 가진 요소 에 새 키를 추가한다고 가정해 보겠습니다 .id.$id

jq --arg id "$id" --arg idle "$daysIdle" \
    '( .[] | select(.id == $id)."days-idle" ) |= $idle' file

.id이는 수정하려는 배열 요소를 선택한 다음 추가합니다(실제로는고쳐 쓰다) ."days-idle"우리가 원하는 특정 값을 가진 요소의 키입니다.

."days-idle"타임스탬프와 타임스탬프 사이의 시간 이어야 하는 경우."last-disconnection-time"지금, 다음과 같이 JSON의 모든 요소를 ​​업데이트할 수 있습니다.

jq 'def dayssince: ((now - (sub("[.].*"; "Z") | fromdate))/86400) | round;
    map(. += { "days-idle": (."last-disconnection-time" | dayssince) })' file

sub()호출은 해당 지점의 타임스탬프를 자르고 끝 부분을 Z. fromdate이는 구문 분석할 수 있는 타임스탬프 유형이 다소 제한되어 있고 원시 타임스탬프 문자열의 1초 미만 정밀도를 처리하지 않기 때문입니다 .

나는 코드를 깔끔하게 유지하기 위해 jq타임 스탬프 이후의 일수를 실제로 계산하기로 결정했습니다 .dayssince

생성된 JSON(2021년 6월 28일 런타임):

[
  {
    "id": "tmp1387816934708382026",
    "owner": "john",
    "x11-display": ":5",
    "x11-authority": "/run/user/john/dcv/tmp1387816934708382026.xauth",
    "num-of-connections": 1,
    "creation-time": "2019-05-14T14:12:14.989287Z",
    "last-disconnection-time": "2019-05-31T18:58:42.851223Z",
    "days-idle": 759
  },
  {
    "id": "tmp4241942441012516520",
    "owner": "mike",
    "x11-display": ":10",
    "x11-authority": "/run/user/mike/dcv/tmp4241942441012516520.xauth",
    "num-of-connections": 0,
    "creation-time": "2019-05-17T16:23:05.891531Z",
    "last-disconnection-time": "2019-05-19T11:23:30.844797Z",
    "days-idle": 771
  }
]

답변2

먼저 Bash 변수에 JSON 개체 배열이 있다고 가정하고 시작해 보겠습니다.

bash$ object='[
  {
    "id" : "tmp1387816934708382026",
    "owner" : "john",
    "x11-display" : ":5",
    "x11-authority" : "/run/user/john/dcv/tmp1387816934708382026.xauth",
    "num-of-connections" : 1,
    "creation-time" : "2019-05-14T14:12:14.989287Z",
    "last-disconnection-time" : "2019-05-31T18:58:42.851223Z"
  },
  {
    "id" : "tmp4241942441012516520",
    "owner" : "mike",
    "x11-display" : ":10",
    "x11-authority" : "/run/user/mike/dcv/tmp4241942441012516520.xauth",
    "num-of-connections" : 0,
    "creation-time" : "2019-05-17T16:23:05.891531Z",
    "last-disconnection-time" : "2019-05-19T11:23:30.844797Z"
  }
]'

$daysIdle다음으로, 변경 가능하며 숫자를 포함한다고 가정합니다 .

bash$ daysIdle=3

이제 해당 변수를 추가하여 에코할 수 $object있습니다 jq.

bash$ echo "$object" | jq --arg daysIdle "$daysIdle" '.[]."days-idle" = ($daysIdle | tonumber)'

이에 대한 몇 가지 중요한 참고 사항입니다. 개체가 실제로 파일에 있거나 다른 스트림(예: cURL)에서 오는 경우 echo $object적절한 콘텐츠를 바꾸면 됩니다. 둘째, 일반적으로 생성된 문자열이 아닌 JSON 숫자를 원한다고 가정하므로 --arg이를 수정하기 위한 필터가 있습니다. 마지막으로 --arg옵션을 사용하여 값을 전달한다는 점에 유의하세요 jq. 이는 JSON 필터 문자열 자체에 값을 삽입하는 것보다 훨씬 더 좋고 안전하며 구문 오류가 발생하지 않습니다. 숫자로 변환할 수 없으면 오류가 발생하지만 필터 문자열의 임의 주입은 허용되지 않습니다. 그렇다면 출력을 살펴보겠습니다.

[
  {
    "id": "tmp1387816934708382026",
    "owner": "john",
    "x11-display": ":5",
    "x11-authority": "/run/user/john/dcv/tmp1387816934708382026.xauth",
    "num-of-connections": 1,
    "creation-time": "2019-05-14T14:12:14.989287Z",
    "last-disconnection-time": "2019-05-31T18:58:42.851223Z",
    "days-idle": 3
  },
  {
    "id": "tmp4241942441012516520",
    "owner": "mike",
    "x11-display": ":10",
    "x11-authority": "/run/user/mike/dcv/tmp4241942441012516520.xauth",
    "num-of-connections": 0,
    "creation-time": "2019-05-17T16:23:05.891531Z",
    "last-disconnection-time": "2019-05-19T11:23:30.844797Z",
    "days-idle": 3
  }
]

관련 정보