체크섬을 비교하는 빠른 스크립트

체크섬을 비교하는 빠른 스크립트

파일이 너무 많아서 체크섬을 확인해야 합니다. 다음과 같은 텍스트 파일이 있습니다.

체크섬 <tab>파일 이름<new line>

나는 이것을 쉘 스크립트를 개선하기 위한 연습으로 사용할 수 있다고 생각했습니다. 이것이 제가 생각해낸 것이고 효과가 있었습니다. 더 좋은 방법이 있는지 궁금했습니다. 유연성이 별로 없다는 것을 알고 있습니다(예: 파일 형식과 알고리즘이 256이라고 가정). 하지만 피하려고 노력하고 있어요 cat... echo:)

감사해요!

#!/bin/sh

workingDir="/path/to/directory/"
textFile="checksums.txt"
filePath="$workingDir$textFile"

while read a b; do
    shasumOutput=$(/usr/bin/shasum -a 256 "$workingDir$b" | /usr/bin/awk '{ print $1 }')
    if [ "$a" = "$shasumOutput" ]; then
        /usr/bin/printf "$b checksum matches: "$a", "$shasumOutput"\n"
    else
        /usr/bin/printf "$b checksum doesn't match: "$a", "$shasumOutput"\n"
    fi
done < "$filePath" 

답변1

~처럼고후가 지적했다shasum귀하의 의견에는 해당 플래그에 대해 이미 완료된 확인을 복사하고 있습니다 -c.

입력은 shasum -c결과 콘텐츠여야 합니다 shasum.

이것을 무시하십시오 ...

귀하의 스크립트는 좋아 보이지만 일부에 대해 언급할 수 있습니다.

이 줄은 예를 들어 대신 printf에 로 작성하는 것이 더 좋습니다.printf 'format string' "$var1" "$var2" "etc."

/usr/bin/printf "$b checksum matches: "$a", "$shasumOutput"\n"

사용

printf '%s checksum matches: %s, %s\n' "$b" "$a" $shasumOutput"

사용의 요점 printf은 정적 형식 문자열과 형식 문자열 템플릿에 들어가는 몇 가지 변수 데이터가 있다는 것입니다.

또한 $( shasum ... )외부 유틸리티에 대한 호출 수를 피하고 줄이기 위해 다음을 수행합니다.

#!/bin/sh

checkdir='/some/path'
checkfile="$checkdir/checksums.txt"

while read -r checksum filename; do
    if [ ! -f "$checkdir/$filename" ]; then
        printf 'Not found: %s\n' "$filename"
        continue
    fi

    gsha256sum "$checkdir/$filename" |  {
        read -r realsum name
        if [ "$realsum" != "$checksum" ]; then
            printf 'Mismatch for "%s":\n\t%s != %s\n' \
                "$filename" "$checksum" "$realsum"
        else
            printf '%s OK\n' "$filename"
        fi
    }
done <"$checkfile" >&2

이렇게 하면 외부 유틸리티 호출(대부분의 셸에서) 수가 단 한 번(SHA256 유틸리티)으로 줄어듭니다.

내 OpenBSD 시스템에서 SHA256 체크섬을 생성하는 GNU coreutils 유틸리티는 gsha256sum. 나는 그 출력이 shasum -a 256귀하의 시스템과 동일하다고 가정합니다.

몇 가지 참고사항:

  • /나는 보통 디렉토리 이름 끝에 넣지 않습니다 . 대신 변수를 사용할 때 구분 기호를 삽입합니다. 이렇게 하면 이것이 $checkdir/checksum.txt파일에 대한 경로라는 것을 직접 볼 수 있지만 ${checkdir}checksum.txt(또는 이와 유사하게) 더 모호합니다.

  • 체크섬을 확인하기 전에 파일이 실제로 존재하는지 확인합니다.

  • SHA256을 구문 분석하는 프로그램의 출력을 사용하는 대신 awk체크섬 파일에서 체크섬과 파일 이름을 읽는 것과 같은 방식으로 읽습니다. 나는 상황에 따라 이 작업을 수행합니다 { ...; }.

  • 나는 치료 중이야모두루프의 출력은 "진단 메시지" 역할을 하며 >&2이후에 모든 메시지를 표준 오류로 리디렉션하는 데 사용됩니다 done.

  • 나는 실제적인 이유가 없는 한 스크립트에서 유틸리티에 대한 절대 경로를 사용하지 않는 경향이 있습니다. 예를 들어, 유틸리티는 거의 항상 셸에 내장되어 있으며 이를 명시적으로 사용할 printf이유가 거의 없습니다 ./usr/bin/printf

입력 파일의 모든 파일 이름을 사용하여 SHA256 유틸리티를 호출한 다음 해당 호출의 체크섬을 비교하여 SHA256 유틸리티를 한 번(또는 아주 적은 호출) 호출할 수 있지만 코드는 아마도 좀 더 복잡할 것입니다. 작업량이 엄청날 것이다. 이것이 일회성 작업이고 입력 파일이 그다지 크지 않다면 그럴 가치가 없습니다.

관련 정보