자주 쓰는 명령어를 하나씩 — 설명, 사용법, 실제 결과로 정리한다. 현대 도구는 대체하는 고전 명령을 같이 적었다. 아래 출력은 전부 WSL에서 직접 실행한 것이고, 현대 도구는 정적 바이너리 하나라 릴리스에서 받아 ~/.local/bin에 두면 된다.
고전 명령을 대체하는 현대 도구
eza — ls 대체
디렉터리를 트리로 보여주고 색·git 상태까지 붙는다. 옛 exa는 유지보수가 끊겨(README 첫 줄이 “unmaintained, use eza”) 커뮤니티 fork인 eza로 넘어왔다. 명령은 거의 호환된다.
$ eza --tree --level=2 demo
demo
├── big
│ └── f
├── logs
│ ├── app.log
│ └── old.log
└── src
└── main.rsripgrep (rg) — grep 대체
기본으로 .gitignore를 존중해 node_modules·빌드 산출물을 알아서 건너뛰고, 재귀·줄번호가 기본이라 grep -rn을 칠 필요가 없다.
$ rg -n 'TODO' demo
demo/src/main.rs:2: // TODO: 검증fd — find 대체
find보다 문법이 단순하고 빠르다. .gitignore를 존중하고, -e로 확장자를 거른다.
$ fd -e log . demo
demo/logs/app.log
demo/logs/old.log우분투/데비안에선 이미 다른 패키지가 fd를 써서 실행 파일이 fdfind로 깔린다(패키지명은 fd-find). ln -s $(which fdfind) ~/.local/bin/fd로 통일한다.
bat — cat 대체
문법 강조, 줄번호, git 변경 표시, 페이저가 붙는다. 긴 코드·설정을 훑을 때.
$ bat --style=numbers,header demo/src/main.rs
File: demo/src/main.rs
1 fn main() {
2 // TODO: 검증
3 let x = 1;
4 }터미널에선 여기에 문법 색까지 붙는다. 구버전 우분투/데비안에선 실행 파일이 batcat으로 깔리니 ln -s /usr/bin/batcat ~/.local/bin/bat.
jq — JSON 다루기
셸에서 JSON을 grep·sed로 씨름하지 말고 jq로 자른다. .a.b로 파고들고 []로 배열을 펼친다.
$ echo '{"user":{"name":"kim","roles":["dev","admin"]}}' | jq -r '.user.name'
kim
$ echo '{"user":{"name":"kim","roles":["dev","admin"]}}' | jq -r '.user.roles[]'
dev
adminlength·select() 같은 필터가 붙어, API 응답이나 설정 JSON을 훑을 때 사실상 필수다.
dust — du 대체
어느 디렉터리가 용량을 먹는지 트리로 보여준다. du -sh * | sort -h를 손으로 조합할 필요가 없다.
$ dust -d1 -b demo
8.0K ┌── src
12K ├── logs
6.0M ├── big
6.0M ┌─┴ demo-d1은 한 단계 깊이만, -b는 사용률 막대를 끈다(안 끄면 각 줄에 색 막대가 붙는다).
sd — sed 대체
찾아 바꾸기가 훨씬 직관적이다. 정규식이 기본이고, 캡처 그룹은 ${1}처럼 쓴다.
$ echo 'hello world' | sd 'world' 'sd!'
hello sd!
$ echo '2026-08-11' | sd '(\d+)-(\d+)-(\d+)' '${3}/${2}/${1}'
11/08/2026sed의 s/.../.../g와 이스케이프 지옥 없이 읽힌다. 다만 스크립트에는 여전히 sed를 쓴다(아래 원칙 참고).
duf — df 대체
디스크 사용량을 표로 깔끔하게. --only local을 붙이면 네트워크·가상 마운트를 뺀다.
$ duf /
╭────────────────────────────────────────────────────────────────────────────╮
│ 1 local device │
├────────────┬─────────┬───────┬────────┬──────────────────┬──────┬────────────┤
│ MOUNTED ON │ SIZE │ USED │ AVAIL │ USE% │ TYPE │ FILESYSTEM │
├────────────┼─────────┼───────┼────────┼──────────────────┼──────┼────────────┤
│ / │ 1006.9G │ 15.4G │ 940.3G │ 1.5% │ ext4 │ /dev/sdd │
╰────────────┴─────────┴───────┴────────┴──────────────────┴──────┴────────────╯USE% 칸은 터미널에서 색 막대로 그려진다.
choose — cut/awk의 열 뽑기
0부터 세는 인덱스로 열을 고른다. -f로 구분자를 바꾸고, 뒤에서부터 세는 음수 인덱스도 된다.
$ echo 'alpha beta gamma delta' | choose 1 3
beta delta
$ echo 'root:x:0:0:root:/root:/bin/bash' | choose -f ':' 0 6
root /bin/bashawk '{print $2,$4}'보다 짧다. 열을 넘어 합계·조건 계산이 필요하면 그땐 awk.
고전 명령 — find로 오래된 로그 지우기
find는 어디에나 있어 스크립트에도 쓴다. 기본 사용법과 결과부터:
$ find demo/logs -name '*.log' -mtime +10 -type f
demo/logs/old.log다만 예전 메모의 이 한 줄엔 함정이 셋 있었다.
find -name '*.log' -mtime +10 | xargs rm1) 공백이 있는 파일명에서 깨진다. xargs는 공백을 구분자로 본다. b with space.log 하나가 인자 세 개로 쪼개진다.
$ find . -name '*.log' -mtime +10 -type f | xargs sh -c 'echo "got $# args:"; printf " [%s]\n" "$@"' _
got 3 args:
[./b]
[with]
[space.log]-print0 / xargs -0으로 널 구분자를 쓰거나 find의 -delete를 쓴다.
find . -name '*.log' -mtime +10 -type f -print0 | xargs -0 rm
find . -name '*.log' -mtime +10 -type f -delete # 더 간단2) -type f가 없으면 디렉터리도 걸린다. *.log라는 이름의 디렉터리까지 걸리고, rm -rf였다면 디렉터리 전체가 조용히 사라진다.
$ find . -name '*.log' -mtime +10 # -type f 없음 → 디렉터리도
./b with space.log
./c.log
$ find . -name '*.log' -mtime +10 -type f # 파일만
./b with space.log3) -mtime +10은 “10일 초과”가 아니다. GNU findutils 매뉴얼에 따르면 파일 나이(초)를 86400으로 나눈 뒤 소수점을 버린 정수로 비교하고, +10은 그 정수가 10보다 큰 것이다. 10.9일 파일은 정수 10으로 절삭돼 안 걸리고, 만 11일이 되어야 걸린다.
지우기 전엔 -delete를 -print로 바꿔 뭐가 걸리는지 먼저 본다. 상시 운영 서비스라면 매번 손으로 지우기보다 logrotate(/etc/logrotate.d/)에 회전·압축·보관 기간을 맡기는 쪽이 맞다.
두 가지 원칙
- 스크립트엔 고전 도구. 대화형 쉘에서 편하다고 스크립트에
eza·fd·bat·sd를 넣지 않는다. 남의 서버·CI 컨테이너엔 기본으로 없다. 스크립트는ls·find·cat·sed처럼 어디에나 있는 고전 도구로 짜고, 새 도구는 터미널에서만 쓴다. - 직접 배포 .deb는 이름이 그대로. 위의
batcat/fdfind개명은 배포판 패키지 사정이다. 각 프로젝트가 직접 내는 .deb 릴리스는 실행 파일명이bat/fd그대로다.
참고
- ogham/exa · eza-community/eza — exa 유지보수 중단과 eza fork로의 이관을 확인했다.
- BurntSushi/ripgrep —
grep대체.rg -n실행 확인(15.2.0). - sharkdp/fd —
find대체, 패키지fd-find/실행 파일fdfind확인(10.4.2). - sharkdp/bat —
cat대체, 구버전의batcat이름 확인(0.26.1). - jqlang/jq — JSON 필터.
.user.name·[]실행 확인(1.8.2). - bootandy/dust —
du대체.dust -d1 -b실행 확인(1.2.4). - chmln/sd —
sed대체. 캡처 그룹 치환 실행 확인(1.0.0). - muesli/duf —
df대체.duf /실행 확인(0.9.1). - theryangeary/choose —
cut/awk의 열 선택. 인덱스·-f확인(1.3.7). - GNU findutils 매뉴얼 — Comparing Timestamps —
-mtime이 나이를 86400초로 나눈 뒤 정수로 절삭해 비교한다는 동작을 확인했다.