我有两个命令,如下:
这给出了存储库名称:
az acr repository list -n registry -o tsv
输出看起来像:
name1
name2
...
这给出了一个存储库的摘要代码:
az acr manifest list-metadata -r ${REGISTRY} --name ${REPO} --query "[?tags[0]==null].digest" -o tsv
输出看起来像:
digest1
digest2
...
我想输出存储库名称和摘要代码。
尝试过:
az acr repository list -n registry -o tsv \
| xargs -I% az acr manifest list-metadata -r ${REGISTRY} --n % --query "[?tags[0]==null].digest" -o tsv \
| xargs -I% echo "%: %"
实际输出:
digest_code: digest_code
预期输出:
repo_name: digestcode
答案1
你需要类似的东西:
export REPO
az acr repository list -n registry -o tsv |
while IFS= read -r REPO; do
az acr manifest list-metadata -r "$REGISTRY" --n "$REPO" --query '[?tags[0]==null].digest' -o tsv |
awk '{print ENVIRON["REPO"]": "$0}'
done
调用awk
以相应的存储库名称为每个清单命令的输出添加前缀。
或者,如果您需要在每个存储库/摘要对上运行其他命令:
az acr repository list -n registry -o tsv |
while IFS= read -r repo; do
az acr manifest list-metadata -r "$REGISTRY" --n "$repo" --query '[?tags[0]==null].digest' -o tsv |
while IFS= read -r digest; do
other-cmd --repo "$repo" --digest "$digest"
done
done
使用zsh
,您还可以执行以下操作:
for repo ( ${(f)"$(az acr repository list -n registry -o tsv)"} ) {
digests=( ${(f)"$(az acr manifest list-metadata -r $REGISTRY --n $repo --query '[?tags[0]==null].digest' -o tsv)"})
print -rC1 -- $repo': '$^digests
}
for repo ( ${(f)"$(az acr repository list -n registry -o tsv)"} )
for digest ( ${(f)"$(az acr manifest list-metadata -r $REGISTRY --n $repo --query '[?tags[0]==null].digest' -o tsv)"})
other-cmd --repo $repo --digest $digest
在 a 中Makefile
,看起来像:
target:
az acr repository list -n registry -o tsv | \
while IFS= read -r repo; do \
az acr manifest list-metadata -r "$$REGISTRY" --n "$$repo" --query '[?tags[0]==null].digest' -o tsv | \
while IFS= read -r digest; do \
other-cmd --repo "$$repo" --digest "$$digest"; \
done; \
done
虽然它位于 Makefile 中的几行中,但这些行被连接在一起,\
删除了尾部 s,并且在将结果传递给 之前$$
将 s 更改为s ,因此需要添加几个s 来在内联 shell 脚本中分隔命令。$
sh -c
;
您可能希望将代码放入脚本中以使其更清晰。
答案2
我猜测,通过对您尝试的解决方案和您想要的其他答案进行逆向工程n₁ + n2 + …输出行,例如
blue: sky
blue: berry
blue: jay
red: stop sign
red: cardinal
red: tomato
red: fire
green: grass
green: beans
斯特凡·查泽拉斯的回答很好,特别是当您不知道存储库名称中可能包含哪些字符时。但是,它不适用于非常旧版本的 Awk。
这个非常相似的答案使用 sed 而不是 Awk。 sed 的资源密集程度较低,并且运行速度可能更快。
az acr repository list -n registry -o tsv |
while IFS= read -r REPO; do
az acr manifest list-metadata -r "$REGISTRY" --name "$REPO" \
--query "[?tags[0]==null].digest" -o tsv |
sed "s/^/$REPO: /"
done
(export
不需要)这应该与 Stéphane 的答案相同,除非存储库名称可能包含/
或 &
。是 /
一个常用但任意的分隔符。如果您确定存储库名称不包含 &
或 , 那么您可以通过将命令更改为来|
使其更安全sed
sed "s|^|$REPO: |"
如果存储库名称可能包含 &
,则处理起来会有些困难。
请注意,如果任何存储库名称或摘要代码可能包含:
.
如果存储库名称或摘要代码都不包含空格,您可以通过将输出通过管道传输到column -t
.