grep 및 awk를 사용하여 날짜 필터링

grep 및 awk를 사용하여 날짜 필터링

.bash_aliases내 파일에 다음 별칭을 만들었습니다.

alias auth="grep \"$(date|awk '{print $2,$3}')\" /var/log/auth.log |
            grep -E '(BREAK-IN|Invalid user|Failed|refused|su|Illegal)'"

이것은 아마도 다음과 같습니다:

  • 오늘 날짜를 확인하세요.
  • auth.log오늘의 뉴스를 얻으려면 grep을 사용하세요.
  • grep 오늘의 메시지는 특정 문자열의 경고 메시지를 일치시키는 데 사용됩니다.

그러나 날짜가 2자리인 경우에만 작동합니다. 왜냐하면 일 숫자 < 10에는 앞에 0이 없기 때문입니다.

예를 들어, date결과를 실행하고 .output 으로 파이프한 awk다음 awk는 다음과 같이 이를 캡처 하여 grep에 공급합니다.dateSat Jan 1 04:56:10 GMT 2011$2$3

Jan 1

단, 날짜에 숫자가 포함된 경우에는 auth.log다음과 같은 메시지가 나타납니다.

Jan  1 00:44:57 linux su[21249]: pam_unix(su:session): session closed for user root

Jan따라서 그 뒤에 공백이 두 개 있지만 내 grep 명령에는 auth.log공백이 하나만 있습니다.Jan

추가 공간을 허용하도록 명령을 수정하려면 어떻게 해야 합니까?

답변1

date | awk ...를 사용하는 대신 date 명령과 함께 형식 지정자를 사용하여 원하는 형식을 얻을 수 있습니다. date(1)매뉴얼 페이지 에 따르면 %b는 월 이름의 약어이고 %e는 공백으로 채워진 날짜이며 와 동일합니다 %_d.

다음 날짜 명령은 원하는 형식의 문자열을 제공해야 합니다.

date "+%b %e"

형식 지정자에 다른 문자를 넣을 수도 있으므로 다음을 사용하는 경우:

date "+^%b %e"

줄 시작 부분의 날짜만 일치하는 grep 패턴을 얻게 됩니다. 이렇게 하면 로그 메시지 섹션의 날짜가 잘못 일치하는 것을 방지할 수 있습니다.

Steven D가 지적했듯이 단일 호출로도 이 작업을 수행할 수 있습니다 grep.

auth()
{
    grep -E "$(date '+^%b %e')"'.*(BREAK-IN|Invalid|user|Failed|refused|su|Illegal)' /var/log/auth.log
}

견적 관련 댓글에 언급된 문제를 바탕으로 일부 변경을 가했습니다. 내 인용 규칙은 별도의 단어를 단일 단어로 그룹화할 때 작은 따옴표를 사용하고 메타 문자의 셸 확장을 방지하고 여러 단어 문자열 내에서 확장을 원할 때만 큰 따옴표를 사용하는 것입니다.

원래 답변의 date형식 문자열은 큰따옴표로 묶여 있는데 이는 위의 규칙에 따라 잘못된 것입니다. 나는 이제 그것을 바꾸었습니다. 편집 grep 문자열을 큰따옴표로 묶습니다. 쉘 메타 문자와 grep 정규 표현식(RE) 메타 문자 사이에 중복되는 경우가 많고 거의 항상 RE를 grep으로 작은 따옴표로 묶기를 원하기 때문에 다시 작은따옴표로 묶었습니다. 현재 문자열에는 작은따옴표가 필요하지 않을 수 있지만, 이 셸 함수가 시간이 지남에 따라 발전하면 향후 변경으로 인해 중단될 수 있습니다.

질문은 별칭에 넣을 명령에 대해 묻기 때문에 이 답변에는 추가 수준의 인용이 표시되지 않습니다. 별칭 대신 셸 함수를 사용하는 것이 더 간단하므로 이 추가 참조를 처리할 필요가 없습니다. 중첩된 참조는 금방 혼란스러워질 수 있으므로 이를 방지하기 위해 모든 단계를 수행해야 합니다.

날짜를 흐리게 하는 Gilles의 제안을 사용하여 이것을 쉘 함수로 테스트했는데 "나에게 적합했습니다".

관련 정보