
어떤 모듈인지 알아보려고 합니다.use Test::Version
cpan에서. 그래서 나는 사용했다minicpan
그것을 반영합니다. 내 문제는 다운로드한 아카이브를 반복하고 아카이브 내의 파일을 grep해야 한다는 것입니다. 내가 어떻게 해야 하는지 누가 말해 줄 수 있나요? 아카이브의 어떤 파일이 어느 줄에 있는지 어떻게든 알려주는 것이 더 나을 것입니다.
(참고: 모두 타르볼이 아니며 일부는 zip 파일입니다.)
답변1
좋아요, 유닉스 철학을 적용해 봅시다. 이 작업의 구성 요소는 무엇입니까?
- 텍스트 검색: 파일에서 텍스트를 검색하려면 도구가 필요합니다(예:
grep
. - 재귀: 디렉토리 트리에서 파일을 찾으려면 도구가 필요합니다
find
. - 아카이브: 이를 읽으려면 도구가 필요합니다.
대부분의 UNIX 프로그램은 파일에서 작동합니다. 따라서 아카이브 구성 요소를 쉽게 조작하려면 파일로 액세스해야 합니다. 즉, 디렉터리로 액세스해야 합니다.
이것AVFS/path/to/foo.zip
파일 시스템은 각 아카이브 파일이 디렉터리로 액세스할 수 있는 파일 시스템 보기를 제공합니다 ~/.avfs/path/to/foo/zip#
. AVFS는 가장 일반적인 아카이브 파일 형식에 대한 읽기 전용 액세스를 제공합니다.
mountavfs
find ~/.avfs"$PWD" \( -name '*.zip' -o -name '*.tar.gz' -o -name '*.tgz' \) \
-exec sh -c '
find "$0#" -name "*.pm" -exec grep "$1" {\} +
' {} 'Test::Version' \;
fusermount -u ~/.avfs # optional
설명하다:
- AVFS 파일 시스템을 마운트합니다.
~/.avfs$PWD
현재 디렉토리의 AVFS 보기인 에서 아카이브 파일을 찾습니다 .- 각 아카이브에 대해 지정된 쉘 조각을 실행합니다(
$0
=archive 이름 및$1
=search 패턴 사용). $0#
아카이브의 디렉토리 보기입니다$0
.{\}
{}
내부 매개변수를 외부로 대체하는 경우에는 필요하지 않습니다 (일부는 이를 수행하고 일부는 그렇지 않음).find
{}
-exec ;
- 선택 사항: 마지막으로 AVFS 파일 시스템을 마운트 해제합니다.
또는 zsh ≥4.3에서:
mountavfs
grep 'Test::Version' ~/.avfs$PWD/**/*.(tgz|tar.gz|zip)(e\''
reply=($REPLY\#/**/*.pm(.N))
'\')
설명하다:
~/.avfs$PWD/**/*.(tgz|tar.gz|zip)
현재 디렉터리 및 해당 하위 디렉터리의 AVFS 보기에 있는 아카이브와 일치합니다.PATTERN(e\''CODE'\')
PATTERN이 발생할 때마다 CODE를 적용합니다. 일치하는 파일의 이름은 에 있습니다$REPLY
.reply
배열을 설정하면 일치하는 항목이 이름 목록으로 변환됩니다.$REPLY\#
아카이브의 디렉토리 보기입니다.$REPLY\#/**/*.pm
.pm
아카이브의 파일을 일치시킵니다 .N
일치하는 항목이 없으면 glob 한정자는 패턴을 빈 목록으로 확장합니다.
답변2
이건 할 수 있을 것 같아
find authors/ -type f -exec zgrep "Test::Version" '{}' +
그러나 이는 다음과 같은 결과를 제공합니다.
authors/id/J/JO/JONASBN/Module-Info-File-0.11.tar.gz:Binary file (standard input) matches
이것은 타르볼의 위치에 그다지 구체적이지 않습니다. 누군가가 더 나은 답변을 줄 수 있기를 바랍니다.
답변3
우그레프옵션을 사용하여 압축 파일(gz/Z/bz2/lzma/xz/lz4/zstd) 및 아카이브(cpio/tar/pax/zip)를 반복적으로 검색합니다 -z
. 옵션은 -z --zmax=2
압축 파일 및 압축 파일 및 아카이브 내에 포함된 압축 파일 및 아카이브를 검색합니다(따라서 zmax=레벨 2).
답변4
어쩌면 내 대답이 누군가에게 도움이 될 수도 있습니다.
#!/bin/bash
findpath=$(echo $1 | sed -r 's|(.*[^/]$)|\1/|')
# tarballs to check in
find $findpath -type f | while read tarball; do
# get list of files in tarball (not dirs ending in /):
if [ -n "$(file --mime-type $tarball | grep -e "application/jar")" ]; then
jar tf $tarball | grep -v '/$' | while read file; do
# get contents of file and look for string
grepout=$(unzip -q -c $tarball $file | grep $3 -e "$2")
if [ -n "$grepout" ]; then
echo "*** $tarball has matching file ($file):"
echo $grepout
fi
done
elif tar -tf $tarball 2>/dev/null; then
tar -tf $tarball | grep -v '/$' | while read file; do
# get contents of file and look for string
grepout=$(unzip -q -c $tarball $file | grep $3 -e "$2")
if [ -n "$grepout" ]; then
echo "*** $tarball has matching file ($file):"
echo $grepout
fi
done
else
file=""
grepout=$(grep $3 -e "$2" $tarball)
if [ -n "$grepout" ]; then
echo "*** $tarball has matching:"
echo $grepout
fi
fi
done