Operating System, OS/Linux

셸 사용하기(Bash)

curious week 2025. 10. 3. 20:10

학습 목표 정리

  • 셸 기본 동작과 대표 종류를 이해하고, 로그인/로그아웃/셸 전환을 할 수 있다.
  • 명령의 형식, 옵션/인수, man/--help 등 온라인 매뉴얼을 활용할 수 있다.
  • 히스토리(history)와 자동완성(Tab), 역검색(Ctrl+R)을 숙달한다.
  • 특수문자, 파이프/리다이렉션, 명령 치환, 따옴표 규칙, 수식/변수 확장을 설명하고 사용할 수 있다.
  • 셸 변수/환경변수와 Bash 초기화 파일들을 구분해 설정을 적용할 수 있다.

1) 셸 개요

셸이란

  • 셸(Shell): 운영체제(커널)와 사용자를 연결해 주는 명령 해석기입니다. GUI 없이도 시스템을 제어할 수 있습니다.
  • 대표 셸: Bash(Bourne Again SHell), sh(Bourne), ksh(Korn), zsh, csh 등.
  • 프롬프트 관례: 일반 사용자: $, 루트: #.

내 로그인 셸 확인/변경

# 현재 셸 실행 파일 경로
echo "$SHELL"

# 현재 프로세스 기준 셸 이름
ps -p $$

# /etc/passwd 에 기록된 로그인 셸 확인(현재 사용자)
getent passwd "$USER" | cut -d: -f7

# 로그인 셸 변경(다음 로그인부터 적용)
chsh -s /bin/bash         # /bin/zsh 등도 가능

로그인/로그아웃/가상 콘솔

  • 로그아웃: exit 또는 Ctrl+D
  • TTY 전환(리눅스): Ctrl + Alt + F1~F6 (배포판에 따라 F7~F1로 GUI 복귀) 각각의 다른 사용자로 이용 가능
    • 유저 아이디와 비밀번호 입력 후 쉘로 전환됨.

2) 셸 명령 사용법

명령의 형식

command [options] [arguments]

예시:

who                 # 인수 없이 실행
date "+%F %T"       # 옵션과 인수
ls -lat             # 짧은 옵션 묶기: -l -a -t
ls --all            # 긴 옵션
chsh -s /bin/sh heeseong

내부 명령 vs 외부 명령

  • 내부(builtin): cd, echo, pwd 처럼 셸에 내장.
  • 외부(external): 파일로 존재(/bin/ls 등). 검색 경로는 환경변수 PATH.
echo "$PATH"      # 실행 파일 탐색 경로
type cd           # builtin 여부 확인
type -a ls        # 어떤 경로가 쓰이는지 전부
which ls          # PATH 상 첫번째 ls 경로

온라인 매뉴얼

man passwd        # 기본 섹션(보통 1)
man 5 passwd      # 섹션 5(파일 포맷)
ls --help         # GNU 도구 대부분 지원

섹션 요약(암기 포인트): 1(명령), 5(파일형식), 8(관리자 명령), 나머지는 필요 시 확인.


3) 히스토리 & 자동완성

히스토리

history           # 전체 기록
history 10        # 최근 10개
!!                # 직전 명령 재실행
!n                # 히스토리 번호 n 실행
!grep             # 'grep'으로 시작한 최근 명령 실행

팁:

  • HISTSIZE(메모리 기록 수), HISTFILESIZE(파일 기록 수), HISTCONTROL=ignoredups:ignorespace 등으로 품질 개선.
  • 위험 명령 재실행 전 !n:p(print)로 미리보기:
!105:p            # 105번 명령을 실행하지 않고 출력만

자동완성 & 역검색

  • Tab 자동완성: 파일/명령/사용자 홈(~username), 변수($VAR) 등.
  • 역검색: Ctrl+R → 일부 입력 → 계속 Ctrl+R로 이전 매칭 이동 → Enter 실행, →로 편집.

4) 명령의 연결과 확장

특수문자 핵심

  • 백슬래시 \ : 이스케이프(특수 의미 제거)
  • 틸드 ~ : 홈 디렉터리, ~user는 해당 사용자 홈
  • 점 . : 현재 디렉터리 / .. : 상위 디렉터리 / . file= source file(현재 셸에서 실행)
  • 해시 # : 주석(라인 끝까지)
  • 달러 $ : 변수/확장 시작
  • 앰퍼샌드 & : 백그라운드 실행
  • 파이프 | : 표준출력 → 다음 명령 표준입력 (앞 명령의 출력을 다음 명령의 입력으로 연결시킴)
  • 파일 입출력 결과를 리다이렉션: <, > (새로운 파일에 추가할 때), >> (기존 파일의 끝에 덧붙일 때), 2>, 2>>, &> 등
  • 글로빙 * ? [] : 와일드카드 확장
  • 느낌표 ! : 히스토리 확장(위 3장)

파이프라인

cat /etc/passwd | sort | less
grep -i "error" app.log | wc -l

리다이렉션(표준 스트림)

# 입력(표준입력)을 파일에서 가져오기: /etc/passwd 내용을 키보드 대신 sort 에 넣는다
sort < /etc/passwd

# stdout(표준출력)을 파일로 '덮어쓰기' 한다: 기존 typedef.out 내용은 사라짐
grep typedef /usr/include/* > typedef.out

# stderr(표준에러)만 별도의 파일로 보낸다: 에러 메시지만 error.txt에 저장
ls not_exist 2> error.txt

# stderr를 '추가(append)'로 보낸다: 기존 error.txt 뒤에 에러를 이어붙임
ls not_exist 2>> error.txt

# stdout을 all.txt로 보내고, stderr를 stdout과 합친다(둘 다 all.txt로 감)
cmd > all.txt 2>&1

# GNU bash 축약형: stdout+stderr를 한 번에 all.txt로 보냄(위와 동일 의미)
cmd &> all.txt

# 화면에도 출력하고 동시에 파일에도 저장: dmesg 출력이 터미널과 kernel.log 양쪽으로 복제됨
dmesg | tee kernel.log

명령 치환(가장 많이 씀)

  • 권장: $( ... )
  • 구식: `...` (중첩 불편)
echo "파일 개수: $(ls | wc -w)"
file "$(which bash)"
ls -l "$(command -v passwd)"

따옴표 규칙(실패/버그의 8할)

  • 작은따옴표 '...': 확장 전부 비활성화(문자 그대로)
  • 큰따옴표 "...": 변수/명령치환은 활성, 글로빙은 비활성
  • 이스케이프 \: 문자 1개만 보호 (\$()는 치환이 일어나지 않음.)
echo "$(date)"            # 치환 수행
echo "\$(date)"           # 문자 그대로 $(date)
echo 'Today is $(date)'   # 문자 그대로

산술 & 변수 확장

echo $((2025-1979))       # 46
echo "나는 $((10/2))살"    # 5
echo "$BASH"              # /usr/bin/bash 경로일 수도 있음(배포판에 따라 다름)
ls -l "$BASH"

5) 셸 변수와 환경설정

로컬 변수 vs 환경 변수

  • 로컬 변수: 현재 셸에만 존재.
  • 환경 변수: 자식 프로세스에 상속. export 필요.
NAME="KIM"                 # (로컬 변수) 현재 셸 안에서만 보이는 변수 생성
echo "$NAME"               # (확인) 변수 값 출력 → KIM

FOO=bar                    # (로컬 변수) 우선 현재 셸에만 존재
export FOO                 # (환경변수로 승격) 이후 실행되는 하위 프로세스(자식 셸)에서도 보이게 함
sh -c 'echo "$FOO"'        # (하위 셸 테스트) export 덕분에 sh에서도 FOO 값을 볼 수 있음 → bar

unset FOO                  # (변수 제거) 현재 셸에서 FOO 자체를 없앰(환경변수/로컬 둘 다 사라짐)
printenv | less            # (환경변수 목록 보기) 전체 환경변수를 페이지로 넘겨 보기에 편함(위/아래 화살표, q로 종료)

# 추가 팁
export FOO=bar             # (한 줄 축약) 로컬 생성 + export를 한 번에

export -n FOO              # (언엑스포트) 환경변수 상태만 해제(로컬 변수로는 남김)
unset -v FOO               # (변수 제거) -v는 변수, -f는 함수 제거

자주 쓰는 환경 변수(요점)

  • PATH: 실행 파일 검색 경로
  • HOME: 홈 디렉터리
  • PWD: 현재 디렉터리
  • USER: 사용자명
  • SHELL: 로그인 셸 경로
  • MAIL: 시스템 메일함 경로(배포판 따라 다름)
  • PS1: 프롬프트 포맷
  • HISTSIZE, HISTFILESIZE, HISTCONTROL: 히스토리 동작

Bash 초기화 파일(로그인/비로그인 구분)

  • 로그인 셸: /etc/profile (모든 사용자에게 적용, 로그인할 때 가장 먼저 수행) → ~/.bash_profile (로그인 할 때 개별 사용자에게 적용) → ~/.bash_login → ~/.profile 중 첫번째 존재 파일만 읽음.
  • 비로그인(대화형) 셸: /etc/bashrc(또는 /etc/bash.bashrc, 배포판별 // 모든 사용자에게 적요외고 셸을 시작할 때 마다 실행) → ~/.bashrc. (셸을 시작할 때 마다 실행, 개별 사용자에게 적용)
  • 로그아웃 때: ~/.bash_logout. (로그아웃 시 실행)
  • 권장 패턴: 사용자 설정은 ~/.bashrc 에 모으고, ~/.bash_profile에서 이를 source.
# ~/.bash_profile
# 로그인 셸에서 ~/.bashrc 도 불러오기
if [ -f ~/.bashrc ]; then
  . ~/.bashrc
fi
# ~/.bashrc (예시 템플릿)
# 1) PATH 보강
export PATH="$HOME/.local/bin:$PATH"

# 2) 안전한 rm: 휴지통/확인 옵션 별칭
alias rm='rm -i'                 # -i: interactive(실수 방지)

# 3) 자주 쓰는 ls 별칭
alias ll='ls -alF'               # -a(숨김) -l(상세) -F(/,*,@ 표시)

# 4) 히스토리 품질
export HISTSIZE=5000
export HISTFILESIZE=10000
export HISTCONTROL=ignoredups:ignorespace

# 5) 프롬프트(간단)
export PS1='\u@\h:\w\$ '         # 사용자@호스트:경로$

적용:

# 현재 셸에 바로 적용
source ~/.bashrc       # 또는 . ~/.bashrc

실전 미니 실습(10분 컷)

  1. 명령 탐색/설명력 키우기
type -a ls
which rm
man 5 passwd
ls --help | less
  1. 히스토리/자동완성
history 5
!!            # 직전 명령 재실행
!ls:p         # 실행 전 미리보기
# Ctrl+R 로 'ssh' 검색 → Enter
  1. 파이프/리다이렉션 맛보기
grep -i bash /etc/passwd | wc -l
dmesg | tee dmesg.out | head
ls not_exist 2> err.txt
  1. 치환/따옴표/산술
echo "오늘은 $(date '+%F %T')"
echo '문자 그대로: $(date)'
echo "$((2**10))"
  1. 변수/환경/프로필
FOO=bar; export FOO
env | grep ^FOO=
echo 'alias gs="git status -sb"' >> ~/.bashrc
. ~/.bashrc
type gs

안전/디버깅 체크리스트

  • rm, mv, cp 앞에는 항상 따옴표로 경로 감싸기: 공백/특수문자 안전.
  • rm -rf "$TARGET_DIR"
  • 글로빙 오동작 방지: 의도치 않은 * 확장 주의. 필요 시 따옴표로 보호.
  • 옵션 종료 표식 -- 활용:
  • rm -- -filename-starts-with-dash
  • 파이프라인 디버깅: 중간 결과를 tee/head로 확인.
  • set -u -o pipefail -e 등은 스크립트에서만 점진 도입(대화형 셸에는 과격할 수 있음).
  • 권한 오류 시: sudo 필요 여부, 파일 소유자/퍼미션(ls -l, id, groups) 점검.

자주 틀리는 포인트 요약

  • 작은따옴표 vs 큰따옴표 구분 실패 → 치환 필요하면 무조건 큰따옴표.
  • which 남용 → type/command -v가 더 정확(alias/builtin까지 확인).
  • ~/.bash_profile만 수정하고 ~/.bashrc를 안 읽음 → source 패턴 적용.
  • !!/!string 오동작 → 실행 전 :p로 미리보기.
  • PATH 덮어쓰기(PATH=...)로 시스템 경로 손실 → 항상 추가 방식:
  • export PATH="$HOME/bin:$PATH"

암기용 치트시트

  • 도움말: man CMD, man 5 FILETYPE, CMD --help
  • 탐색: type CMD, command -v CMD, echo $PATH
  • 히스토리: history, !!, !n, !str, Ctrl+R
  • 파이프/리다이렉션: |, >, >>, 2>, &>, tee
  • 치환/따옴표: $(...), '...'(그대로), "..."(확장)
  • 산술: $(( expr ))
  • 변수: NAME=val, export NAME, unset NAME, printenv
  • 프로필 로드: ~/.bashrc ← ~/.bash_profile에서 source
  • 안전옵션 예시: alias rm='rm -i', alias ll='ls -alF'

bash 셸 쓸 때 자주 쓰고 외워둬야하는 명령어


1) 디렉터리/파일 탐색

  • ls (list directory) — 디렉터리 목록 보기
    • ls -a : 숨김파일 포함(All)
    • ls -l : 상세(Long)
    • ls -al : 숨김+상세
    • ls -h : 사람이 읽기 쉬운 크기(–human-readable, -l와 함께)
    • ls -lt : 최신 수정순 정렬
    • ls --color=auto : 색상(대부분 배포판 기본)
    • 예시
      • ls -alh
      • ls -lt | head ← 최근 수정 10개 정도만 보고 싶을 때
  • cd (change directory) — 디렉터리 이동
    • cd : 홈으로
    • cd - : 이전 디렉터리로
    • cd .. : 상위 디렉터리로
  • pwd (print working directory) — 현재 경로 표시
    • 예시: pwd
  • tree — 트리 형태로 보기(없으면 설치)
    • tree -L 2 : 2단계까지만
  • stat — 파일 메타데이터(타임스탬프, 권한 등)
    • stat file.txt
  • file — 파일 타입 판별(바이너리/텍스트 등)
    • file my.bin
  • which / type / command -v — 실행 파일/내장명령 확인
    • type cd(builtin 여부), which ls, command -v grep

2) 내용 보기/프리뷰

  • cat — 파일 출력(짧은 파일)
    • cat file.txt
  • less — 페이지 단위 뷰어(긴 파일)
    • less /var/log/syslog ← q로 종료, /키워드 검색
  • head / tail — 앞/뒤 일부
    • head -n 20 file.log
    • tail -n 100 file.log
    • tail -f file.log ← 실시간 로그 추적
  • wc (word count) — 줄/단어/바이트 수
    • wc -l file.txt ← 라인 수

3) 검색/텍스트 처리(파이프라인의 핵심)

  • grep (global regular expression print) — 문자열/정규식 검색
    • grep -n : 줄번호
    • grep -i : 대소문자 무시
    • grep -R : 재귀 검색
    • grep -E : 확장 정규식(ERE)
    • grep -v : 부정(매칭 제외)
    • grep -A 3 -B 2 : 앞뒤 문맥 출력
    • 예시
      • grep -Rni "TODO" src/
      • dmesg | grep -i error
  • find — 파일 탐색(조건/동작 조합)
    • find . -name "*.log" : 이름
    • find . -type f -size +100M : 100MB 초과 파일
    • find . -mtime -1 : 24시간 이내 변경
    • find . -maxdepth 1 -type d : 현재 깊이의 디렉터리만
    • 안전한 실행(공백/특수문자 대응)
      • find . -type f -print0 | xargs -0 grep -H "pattern"
      • find . -type f -name "*.tmp" -delete
      • find . -type f -exec chmod 644 {} + ← +는 배치 실행
  • xargs — 표준입력을 인수로 변환
    • -0 : 널 구분(공백 안전)
    • -I{} : 자리표시자
    • 예시
      • printf "%s\0" *.jpg | xargs -0 -I{} mv "{}" images/
  • sort / uniq — 정렬/중복 처리
    • sort -n : 숫자 정렬, -r : 내림차순, -kN : N번째 필드 기준
    • uniq -c : 중복 개수
    • 예시
      • sort access.log | uniq -c | sort -nr | head
  • cut / tr — 필드/문자 변환
    • cut -d',' -f1,3 file.csv : 1,3열 추출
    • tr -d '\r' < in.txt > out.txt : CR 제거
    • tr '[:lower:]' '[:upper:]'
  • sed (stream editor) — 치환/삭제/추출
    • sed -n '1,10p' file : 1~10줄 출력
    • sed -E 's/(foo)+/bar/g' file : 정규식 치환
    • 인플레이스 편집(GNU)
      • sed -i 's/DEBUG/INFO/g' app.conf
    • 백업 만들며 편집
      • sed -i.bak 's/8080/80/' nginx.conf
  • awk — 컬럼 처리/집계(에이더·웨인버그·커니핸 이름 앞글자)
    • 구분자 지정: -F','
    • awk -F, '{sum+=$3} END{print sum}' sales.csv
    • awk '{print NR, $0}' file : 줄번호와 함께 출력
  • tee — 출력 복제(화면+파일)
    • make | tee build.log
    • cmd | tee -a append.log

4) 파일/디렉터리 조작

  • mkdir — 디렉터리 생성
    • mkdir newdir
    • mkdir -p a/b/c : 상위까지 생성
  • rm — 파일/디렉터리 삭제(주의)
    • rm file
    • rm -r dir : 재귀 삭제
    • rm -rf dir : 강제(매우 위험, 경로 항상 따옴표)
    • 습관: alias rm='rm -i'로 확인 프롬프트
  • cp — 복사
    • cp src dst
    • cp -r dir1 dir2 : 디렉터리 재귀
    • cp -a : 속성 보존(archive)
  • mv — 이동/이름 변경
    • mv a.txt b.txt
    • mv file /tmp/
  • ln — 링크
    • ln file link : 하드링크
    • ln -s target symlink : 심볼릭 링크

5) 권한/소유/마스크

  • chmod — 퍼미션 변경
    • chmod 644 file : rw-r--r--
    • chmod u+x script.sh : 실행권한 추가
    • chmod -R 755 dir/ : 재귀
  • chown — 소유자/그룹 변경
    • chown user:group file
    • chown -R user:group dir/
  • umask — 기본 권한 마스크 확인/설정
    • umask / umask 022

6) 디스크/용량

  • df — 파일시스템 사용량
    • df -h : 사람이 읽기 쉬운 단위
  • du — 디렉터리별 용량
    • du -sh * : 현재 디렉터리 하위 항목 요약
    • du -sh .[!.]* * : 숨김 포함
  • lsblk — 블록 디바이스 트리
    • lsblk -f : 파일시스템/UUID 포함
  • blkid — 블록 디바이스 식별 정보
  • mount / umount — 마운트/해제
    • mount | grep /dev/sd
    • sudo umount /mnt/usb
  • sync — 디스크에 버퍼 플러시

7) 압축/아카이브

  • tar (tape archive) — 아카이브/해제
    • tar -czf out.tgz dir/ : 압축 생성(gzip)
    • tar -xzf out.tgz : 압축 해제
    • tar -tf out.tgz : 목록만 보기
  • gzip / bzip2 / xz
    • gzip -k bigfile : 원본 유지(-k)
    • xz -T0 hugefile : 멀티스레드 압축
  • zip / unzip
    • zip -r site.zip site/
    • unzip site.zip -d dest/

8) 프로세스/서비스/로그

  • ps (process status) — 프로세스 목록
    • ps aux | grep nginx
    • ps -ef : 다른 표기법(배포판 취향)
  • top / htop — 실시간 모니터(htop은 설치형)
    • top / htop
  • pgrep / pkill — 이름 기반 찾기/종료
    • pgrep -a node
    • pkill -f "gunicorn: master"
  • kill — PID로 종료
    • kill -TERM 1234
    • kill -KILL 1234 : 강제(SIGKILL)
  • nice / renice — 우선순위 조정
  • systemctl (systemd) — 서비스/부팅 관리
    • systemctl status nginx
    • sudo systemctl start|stop|restart nginx
    • sudo systemctl enable|disable nginx
  • journalctl — 시스템 로그
    • journalctl -u nginx : 유닛별
    • journalctl -u nginx -f : tail 모드
    • journalctl --since "1 hour ago"

9) 네트워크/진단/전송

  • ip (internet protocol) — 네트워크 구성
    • ip a : 주소
    • ip r : 라우팅
    • ip -br a : 요약
  • ss — 포트/소켓 확인
    • ss -tulpn : 리스닝 TCP/UDP+프로세스
  • ping / traceroute — 연결/경로
    • ping -c 4 8.8.8.8
    • traceroute example.com(설치형일 수 있음)
  • dig / nslookup — DNS 조회
    • dig +short A example.com
    • dig TXT _acme-challenge.example.com
  • curl — HTTP/FTP 등 다목적 전송
    • curl -I https://example.com : 헤더만
    • curl -fsSL https://... | bash : 설치 스크립트(주의)
    • curl -o out.bin URL
  • wget — 다운로드 도구(설치형일 수 있음)
    • wget -O out.bin URL
  • scp (secure copy, SSH) — 원격 복사
    • scp file user@host:/path/
    • scp -r dir user@host:/path/
  • rsync — 동기화(증분/재시도)
    • rsync -av --delete src/ user@host:/dst/
  • ssh (secure shell) — 원격 접속
    • ssh user@host
    • ssh -i ~/.ssh/id_ed25519 user@host

10) 사용자/권한/계정

  • whoami — 현재 사용자
  • id — UID/GID/그룹
  • groups — 소속 그룹
  • sudo — 권한 상승
    • sudo -v : 캐시 갱신
    • sudo -k : 캐시 폐기

(계정 생성/변경은 배포판별 정책이 있어 필수만 기억: useradd, usermod, passwd 등)


11) 시간/환경/셸 유틸

  • date — 날짜/시간
    • date '+%F %T'
    • date -d 'yesterday' '+%F' : 어제(gnu date)
  • cal — 달력
    • cal -y : 연간
  • env / printenv — 환경변수
  • export / unset — 변수 설정/해제
    • export PATH="$HOME/.local/bin:$PATH"
  • alias / unalias — 별칭
    • alias ll='ls -alF'
  • history — 히스토리
    • history, !!(직전 명령 실행), !$(직전 마지막 인수), !^(직전 첫 인수), !해당번호 (해당 번호의 명령 실행), !해당문자열 (문자열로 시작하는 최근 명령 실행)
  • 단축키(읽어두면 생산성 급상승)
    • Ctrl+A/E : 줄 맨앞/맨뒤
    • Alt+B/F : 단어 단위 이동
    • Ctrl+U/K/W : 앞/뒤/단어 삭제
    • Ctrl+R : 히스토리 역검색
  • 작업 제어
    • Ctrl+Z : 일시중지
    • jobs / bg / fg
    • nohup cmd & : 터미널 끊겨도 계속
  • 터미널 멀티플렉서(필수 툴)
    • tmux / screen : 세션 유지/분할(설치형)

12) “진짜 자주 쓰는 암기 세트”(초간단 20선)

  1. ls -alh
  2. cd - / pwd
  3. grep -Rni "text" .
  4. find . -type f -name "*.log" -delete
  5. sort | uniq -c | sort -nr | head
  6. cut -d, -f1,3 file.csv
  7. sed -i 's/foo/bar/g' file
  8. awk -F, '{sum+=$3} END{print sum}' file.csv
  9. du -sh * | sort -h
  10. df -h
  11. tar -czf out.tgz dir/ / tar -xzf out.tgz
  12. ps aux | grep proc / pgrep -a proc
  13. kill -TERM PID / pkill -f pattern
  14. systemctl status nginx / journalctl -u nginx -f
  15. ip a / ss -tulpn
  16. curl -I https://example.com
  17. ssh user@host / scp file user@host:/path/
  18. alias ll='ls -alF'
  19. history | tail / !! / !$
  20. nohup long_task & / tmux

용어 확장

  • pwd = print working directory
  • grep = global regular expression print
  • sed = stream editor
  • awk = Aho–Weinberger–Kernighan(저자 이름)
  • ps = process status
  • tar = tape archive
  • ssh/scp = secure shell / secure copy