본문 바로가기
C.W.K.
Stream
Lesson 06 of 12 · published

스크립트의 함수

~10 min · function, local, return

Level 0창 구경꾼
0 XP0/95 lessons0/14 achievements
0/100 XP to next level100 XP to go0% complete

모양

greet() {
  local name="${1:?name required}"
  echo "hi, $name"
}
greet Alice

함수도 $1, $2, $@, $#로 인자를 받아. bash나 zsh에서는 작업용 변수를 local로 선언해 호출한 쪽의 같은 이름을 덮어쓰지 않게 해.

반환 값

return N은 함수의 종료 상태를 정하며 보통 0은 성공, 그 밖의 값은 실패를 뜻해. 문자열 결과가 필요하면 표준 출력으로 내보내고 명령 치환으로 받을 수 있지만, 로그까지 표준 출력에 섞으면 결과가 오염돼.

upper() { echo "${1^^}"; }   # bash 4 이상
name="$(upper hello)"

변수 범위에서 생기는 함정

# 문제: 호출한 쪽의 tmp를 덮어씀
f() { tmp=42; echo $tmp; }
tmp=hello
f         # 42
echo $tmp  # hello가 아니라 42가 출력됨

# 수정
f() { local tmp=42; echo $tmp; }

함수를 자식 셸에 전달할 때

현재 셸에 정의한 함수는 기본적으로 자식 프로세스에서 보이지 않아. bash에서는 export -f myfunc로 자식 bash에 내보낼 수 있지만 zsh의 동작은 다르고, 대부분의 스크립트에는 이 기능이 필요하지 않아.

라이브러리 스크립트

도우미를 lib.sh에 모아 source하면 현재 셸에 함수가 들어와. 다만 호출한 현재 디렉터리는 언제든 달라질 수 있으므로 무조건 source ./lib.sh라고 쓰기보다, 실행 파일 자신의 위치를 기준으로 경로를 계산하는 편이 안전해.

표준 출력은 함수의 데이터 통로야

value=$(lookup key)처럼 값을 받는 함수라면 표준 출력에는 결과만 써. 진행 상황과 진단 메시지는 >&2로 표준 오류에 보내야 호출자가 데이터를 안전하게 캡처할 수 있어. 셸 함수의 ‘반환값’은 문자열이 아니라 종료 상태라는 구분을 지키면 조합이 쉬워져.

라이브러리를 불러오는 것도 실행이야

source는 파일 내용을 현재 셸에서 그대로 실행해. 믿을 수 없는 파일을 불러오면 명령도 함께 실행되고 변수와 옵션도 바뀔 수 있어. 공용 라이브러리는 로드 시 부작용을 만들지 말고 함수 정의와 상수 설정에 집중해.

Code

lib.sh + entry 패턴·bash
# 파일: lib.sh
log()  { printf '%(%H:%M:%S)T %s\n' -1 "$*" >&2; }
die()  { log "FATAL: $*"; exit 1; }

# 파일: entry.sh
#!/usr/bin/env bash
set -euo pipefail
source "$(dirname "$0")/lib.sh"
log 'starting'
[[ $# -eq 1 ]] || die 'usage: entry <name>'

External links

Exercise

lib.shlogdie 도우미 함수를 작성하고 작은 스크립트에서 불러와. 함수 안의 작업용 변수를 local로 선언한 뒤 함수가 끝났을 때 같은 이름이 호출한 셸로 새지 않는지 확인해.

Progress

Progress is local-only — sign in to sync across devices.
이 페이지에서 버그를 발견하셨거나 피드백이 있으세요?문제 신고

댓글 0

🔔 답글 알림 (로그인 필요)
로그인댓글을 남기려면 로그인해 주세요.

아직 댓글이 없어요. 첫 댓글을 남겨보세요.