Bash Script에는 하나의 명령만 쓰는 것이 아니라
한 명령의 출력을 파일로 보내거나, 다른 명령의 입력으로 넘기거나, 에러만 따로 저장하는 식으로
입력과 출력의 흐름을 조합하며 사용한다.
이 글에서는 Bash의 표준 입출력과 명령어 연결에 대해 정리한다.
표준 입출력
명령어는 실행될 때 입력을 받고, 결과를 출력한다.
리눅스는 이 입출력 경로를 기본적으로 세 가지로 나눠 관리한다.
표준 입력(stdin)
표준 입력은 명령어가 입력을 받는 기본 통로다.
보통은 키보드 입력이 표준 입력으로 연결된다.
표준 출력(stdout)
표준 출력은 명령어가 정상적인 실행 결과를 내보내는 기본 통로다.
대부분의 명령어 결과는 기본적으로 터미널 화면에 출력되는데,
이때 화면에 보이는 일반 결과가 바로 표준 출력이다.
표준 에러(stderr)
표준 에러는 오류 메시지를 출력하는 별도의 통로다.
에러 메시지도 화면에 보이기 때문에 stdout과 같아 보일 수 있지만, 내부적으로는 다른 경로이다.
예를 들어 존재하지 않는 파일을 읽으려고 하면:
$ cat notexist.txt
cat: notexist.txt: No such file or directory이 에러 메시지는 일반 출력이 아니라 stderr로 전달된다.
이렇게 stdout과 stderr가 분리되어 있기 때문에,
정상 결과는 파일로 저장하고 에러는 따로 남기는 식의 처리가 가능하다.
파일 디스크립터
리눅스는 표준 입출력을 숫자로도 구분한다.
이 숫자를 파일 디스크립터(file descriptor) 라고 한다.
기본 표준 입출력은 다음과 같이 정해져 있다.
0: 표준 입력 (stdin)1: 표준 출력 (stdout)2: 표준 에러 (stderr)
아래 두 표현은 같은 의미다.
ls > out.txt
ls 1> out.txt에러만 따로 저장하려면 2>를 사용할 수 있다.
ls 2> error.txt리다이렉션
리다이렉션은 명령어의 입력 또는 출력을 기본 경로가 아닌 다른 곳으로 보내는 것이다.
- 화면으로 나가던 출력을 파일로 보내거나
- 키보드로 받던 입력을 파일에서 받도록 바꾸는 방식이다.
출력 리다이렉션
출력 리다이렉션은 주로 표준 출력(stdout)이나 표준 에러(stderr)를 파일로 보내기 위해 사용한다.
>
>는 출력을 파일로 덮어써서 저장한다.
echo "hello" > output.txt이 명령은 hello를 output.txt에 저장한다.
이미 파일이 있다면 기존 내용은 사라지고 새로 덮어써진다.
>>
>>는 출력을 파일 끝에 이어서 추가한다.
echo "hello" >> output.txt
echo "world" >> output.txt결과:
hello
world로그를 계속 누적해서 저장할 때 자주 사용한다.
입력 리다이렉션
입력 리다이렉션은 표준 입력(stdin)을 파일이나 다른 입력원으로 바꾸는 것이다.
<
<는 파일 내용을 명령어의 입력으로 전달한다.
wc -l < input.txt이 명령은 input.txt의 내용을 표준 입력으로 받아 줄 수를 센다.
here document
here document는 여러 줄 입력을 직접 스크립트 안에서 표준 입력으로 전달하는 방식이다.
cat <<EOF
hello
world
EOF출력:
hello
world이 방식으로 임시로 Script를 만들어서 실행할 수 있다.
화면에 출력을 표시하는 대신 > 연산자를 사용하여 파일로 리디렉션할 수 도 있다.
아래처럼 하면 여러 줄 내용을 파일로 한 번에 저장할 수 있다.
환경변수, 변수 참조도 가능하다.
cat << EOF > file.txt
The current working directory is: $PWD
You are logged in as: $(whoami)
EOF파이프
파이프(|)는 한 명령의 표준 출력을 다음 명령의 표준 입력으로 넘기는 연산자다.
파일을 중간에 만들지 않고도 명령어 결과를 바로 다음 명령어가 받아 처리할 수 있게 해준다.
리눅스 명령어는 대부분 텍스트를 입력받고 텍스트를 출력하기 때문에,
파이프를 이용하여 서로 다른 명령어들을 쉽게 연결할 수 있다.
ls | wc -l이 명령은 다음 흐름으로 동작한다.
ls가 현재 디렉터리 목록을 출력한다.- 그 출력이 화면으로 가지 않고
wc -l의 표준 입력으로 전달된다.wc -l은 줄 수를 세어 결과를 출력한다.
파이프는 여러 개를 이어서 쓸 수도 있다.
ps -ef | grep nginx | wc -lps -ef: 전체 프로세스 목록 출력grep nginx: 그중 nginx가 포함된 줄만 추림wc -l: 최종 개수 계산
자주 사용하는 명령 연결 패턴
연결에 자주 쓰이는 명령어
ps: 프로세스 목록 확인grep: 특정 문자열 검색awk: 열 단위 추출, 간단한 가공sort: 정렬uniq: 중복 제거 또는 중복 개수 확인wc: 줄 수, 단어 수, 문자 수 계산
로그 검색
로그에서 특정 에러만 찾고 싶다면 다음처럼 쓸 수 있다.
grep "ERROR" app.log빈도도 셀 수 있다.
grep "ERROR" app.log | wc -l자주 등장한 메시지를 보고 싶다면:
grep "ERROR" app.log | sort | uniq -c | sort -nrgrep: ERROR 포함 줄 추출sort: 같은 줄끼리 모이도록 정렬uniq -c: 중복 횟수 집계sort -nr: 많은 순서대로 정렬
![[Pasted image 20260416171718.png]]
프로세스 필터링
특정 프로세스가 실행 중인지 확인할 때 자주 쓴다.
ps -ef | grep nginx다만 이 방식은 grep nginx 자체도 결과에 포함되기 때문에, 아래 방식을 사용한다.
ps -ef | grep '[n]ginx'
ps -ef | grep nginx | grep -v grep프로세스 개수만 확인하려면:
ps -ef | grep '[n]ginx' | wc -l파일 내용 가공
파일에서 특정 열만 뽑거나 정리할 수 있다.
예를 들어 /etc/passwd에서 사용자 이름만 보고 싶다면:
awk -F: '{print $1}' /etc/passwd중복 없이 정렬된 목록:
awk -F: '{print $1}' /etc/passwd | sort | uniq로그에서 특정 필드만 뽑아 개수를 세는 식의 패턴도 자주 나온다.
awk '{print $1}' access.log | sort | uniq -c | sort -nr표준 에러 분리
stderr와 stdout 분리가 필요한 이유
명령 실행 결과와 에러 메시지가 한 파일에 섞이면 실패 원인을 정확히 추적하기 어려워진다.
예를 들어 배치 작업이 실패했을 때, 정상 처리 로그와 에러 메시지가 뒤섞여 있으면
어디서 문제가 발생했는지 찾는 데 시간이 더 걸린다.
그래서 stdout과 stderr를 분리하면 다음이 쉬워진다.
- 정상 처리 결과 확인
- 에러 원인 추적
- 실패 시점 파악
- 자동화 스크립트에서 후속 처리 분기
에러 출력 분리하기
에러 메시지만 따로 파일로 저장하려면 2>를 사용한다.
ls existing.txt nofile.txt 2> error.txt이 경우 존재하지 않는 파일에 대한 에러 메시지는 error.txt에 저장된다.
정상 출력은 별도로 처리하지 않았기 때문에 화면으로 나간다.
표준 출력과 표준 에러를 각각 분리하기
stdout과 stderr를 각각 다른 파일로 보낼 수도 있다.
ls > output.txt 2> error.txt- output.txt : 정상 출력 저장
- error.txt : 에러 메시지 저장
이 방식은 정상 결과와 오류 메시지를 완전히 분리해서 보고 싶을 때 유용하다.
표준 출력과 표준 에러를 같은 파일에 저장하기
stdout과 stderr를 같은 파일에 함께 저장할 수도 있다.
ls > all.log 2>&1> all.log: stdout을all.log로 보냄2>&1: stderr도 stdout이 향하는 곳과 동일하게 보냄
정상 출력과 에러 메시지를 모두 all.log 하나에 저장한다.
Bash에서는 아래처럼 더 짧게 쓸 수도 있다.
ls &> all.log출력 없이 실행만 하기
스크립트나 명령을 실행하되 출력은 모두 버리고 싶을 때는 /dev/null을 사용한다.
./script.sh > /dev/null 2>&1/dev/null: 필요 없는 출력을 버리는 특수 파일> /dev/null: 표준 출력을 버림2>&1: 표준 에러도 같은 곳으로 보냄
주로 다음 상황에서 사용한다.
- 출력이 너무 많지만 성공/실패만 확인하면 될 때
- cron 같은 비대화형 실행에서 불필요한 출력을 줄이고 싶을 때
- 조용히 실행하고 종료 코드만 확인하고 싶을 때
stderr만 따로 남기기
정상 출력은 버리고, 에러만 보고 싶을 수도 있다.
ls > /dev/null 2> error.txt- 표준 출력은 버림
- 표준 에러만 error.txt에 저장
정상 결과는 필요 없고 실패한 이유만 확인하고 싶을 때 유용하다.
예를 들어 배치 작업, 점검 스크립트, 파일 검사 스크립트에서는
정상 출력은 무시하고 에러만 따로 수집하는 식으로 활용할 수 있다.