안녕하세요, du 명령의 결과를 구문 분석하려고 하는데 루프 없이 수행하는 방법을 모르겠습니다. 다음 명령을 실행합니다.
du -shm /var/vmail/mailboxes/domain/*/mail
내 결과는 다음과 같은 목록입니다.
80 /var/vmail/mailboxes/domain/USER1/mail
150 /var/vmail/mailboxes/domain/USER2/mail
220 /var/vmail/mailboxes/domain/USER3/mail
위 목록을 다음과 같이 json 객체로 변환하고 싶습니다.
{USER1: 80, USER2:150, USER3:220 }
아니면 최소한 뭔가를 갖고 있어야 합니다:
80 USER1
150 USER2
220 USER3
나는 이것을 시도했지만 sed -e
성공하지 못했습니다. 어떤 아이디어가 있습니까?
답변1
노력하다
du -sm /var/vmail/mailboxes/domain/*/mail |
sed 's:/var/vmail/mailboxes/domain/::; s:/mail::'
어디
s:/mail::
/mail
아무것도 대신하지 않을 것이다
JSON으로 이동
du -sm /var/vmail/mailboxes/domain/*/mail |
sed 's:/var/vmail/mailboxes/domain/::; s:/mail::' |
awk 'BEGIN { sep="{" ;} { printf "%s \"%s\":%s",sep,$2,$1; sep="," } END { printf "}\n"}'
답변2
du -shm /var/vmail/mailboxes/domain/*/mail | awk -F '[ /]' '{ print $1, $7 }'
du
귀하가 제공한 형식으로 입력을 사용하면 다음이 생성됩니다.
80 USER1
150 USER2
220 USER3
프로그램 awk
은 출력에서 적절한 필드를 선택하기만 하면 됩니다 du
. 각 줄은 공백이나 슬래시로 구분된 필드로 해석됩니다.
awk -F '[ /]' '{ print $1, $(NF - 1) }'
작동할 것입니다.
JSON으로 변환하려면 다음을 사용하십시오 jq
.
du -shm /var/vmail/mailboxes/domain/*/mail |
awk -F '[ /]' '{ print $1, $7 }' |
jq -sR 'split("\n")[0:-1] | map(split(" ")) | map({(.[1]):.[0]}) | add'
이것은 생산할 것입니다
{
"USER1": "80",
"USER2": "150",
"USER3": "220"
}
이 jq
표현식은 먼저 입력을 개별 배열 요소(입력 줄당 하나)로 분할한 다음 해당 요소를 공백을 기준으로 다시 하위 배열로 분할합니다. 이 시점에서 우리는
[
[
"80",
"USER1"
],
[
"150",
"USER2"
],
[
"220",
"USER3"
]
]
그런 다음 각 하위 배열의 두 번째 요소를 키로, 첫 번째 요소를 값으로 사용하여 객체를 만듭니다.
[
{
"USER1": "80"
},
{
"USER2": "150"
},
{
"USER3": "220"
}
]
마침내 add
우리에게 최종 결과를주었습니다.
답변3
awk
다음을 사용하여 2열 형식으로 변환 할 수 있습니다 .
$ du -shm | awk -F/ '{print $1" "$(NF - 1)}'
80 USER1
150 USER2
220 USER3
JSON의 경우 다음을 시도해 보세요.
$ du -shm | awk -F/ '{print "\""$(NF - 1)"\":"$1}' | paste -sd, | printf "{$(cat)}" | jq
{
"USER1": 80,
"USER2": 150,
"USER3": 220
}
답변4
이것은 약간 까다롭습니다 sed
. 그러나 GNU sed에 대한 주석이 달린 제안은 다음과 같습니다.
파싱.sed
s|([^ ]+) .*/([^/]+)/.*| "\2" : \1,| # Extract size and name in json-format
1h; 1!H # Correctly add them to hold-space
$ {
z # Clear pattern-space
s/^/\{/ # Prepend start-curly-brace
G # Fetch formatted json from hold-space
s/,$// # Remove last comma
s/$/\n\}/ # Append end-curly-brace
p # Print
}
다음과 같이 실행하세요:
du -shm /var/vmail/mailboxes/domain/*/mail | sed -Enf parse.sed
또는 한 줄로:
du -shm /var/vmail/mailboxes/domain/*/mail |
sed -Ene 's|([^ ]+) .*/([^/]+)/.*| "\2" : \1,|;1h;1!H;${z;s/^/\{/;G;s/,$//;s/$/\n\}/;p}'
두 경우 모두 출력:
{
"USER1" : 80,
"USER2" : 150,
"USER3" : 220
}