특정 파일 / 디렉토리 바꾸기 (쉘스크립트 포함)
This file is README.txt
#########################################
##
## 스크립트명 : renameto(특정 파일/디렉토리를 바꾸기)
##
## 작성자 : 김칠봉 <san2(at)linuxchannel.net>
## 작성일 : 2003.10.22 pathed for FreeBSD
## 2002.11.05 add upcase and lowcase, usage to stderr
## 2002.04.13 patch(sort)
## 2002.03.29 patch(thanks '단n키')
## 2002.03.27 add options
## 2002.03.04
##
## 라이센스 : GNU GPL
## 다운로드 : http://www.linuxchannel.net/devel/renameto/
##
##
##########################################
##########################################
## ##
## WARNING !!! ##
## 사용자의 사용상 부주의로 인한 피해는 ##
## 어떠한 경우라고 본 작성자에게 그 책임##
## 이 없음을 미리 공지합니다. ##
## ##
##########################################
[기능]
- 특정 문자열의 파일을 찾아서 바꿈
- 특정 문자열의 디렉토리를 찾아서 바꿈
- 바꾸기 전에 view 기능 제공
- 특정 디렉토리에서 검색가능
- 현재디렉토리, 모든 서브디렉토리, 특정 깊이의 디렉토리 검색
- 대소문자 바꾸기
[사용법]
# renameto --help
usage : renameto [options] "/from_string/to_string/" "<target_files|target_directory>"
options
-R : include all sub directory (not default)
-Rn : 'n' is sub directory maxdepth number
'-R0' is current directory (same as not given options)
-t,-test,--test : only test view
-c,-case,--case : translate upcase and lowcase
-v,-view,--view : only test view
-d,-dir,--dir : only directory adjust (not files)
-h,-help,--help : help
example
renameto /html/php/ "*.html" (same as rename command)
renameto -R "/ /_/" "* *.mp3" (replace file " " to "_" all sub-directory)
renameto -R -test "/ /_/" "* *.mp3" (test view)
renameto -R -dir "/ /_/" "/home/xxx/mp3/* *" (replace directory)
renameto -R -case "/[A-Z]/[a-z]/" "*" (to lowcase)
renameto -R -case "/[e-k]/[E-K]/" "*" (to upcase)
source download http://ftp.linuxchannel.net/devel/renameto/
#
-R
하위의 모든 디렉토리에서 검색
-R0
현재 디렉토리에서만 검색
-Rn
현재디렉토리에서 그다음 n단계 디렉토리까지만 검색, n은 ([0-9]*)
-R
옵션이 없다면 현재디렉토리에서 만 검색
-d, -dir, --d, --dir
파일대신 디렉토리에 적용
이 옵션이 없다면 기본적으로 파일을 그 대상으로 함
-v, -view, --view, -t, -test, --test
파일이나 디렉토리를 바꾸지 않고 그냥 찾아서 출력만 함(확인할때)
이 옵션이 없다면 매치되는 파일이나 디렉토리를 찾아서 바꿈.
-c, --case
대문자->소문자 or 소문자->대문자
'/from_string/to_string/'
from_string -> to_string 으로 교체
공백 문자열이 들어갈 수 있으므로 받드시 전체를 ' 나 "로 묶어줌
양자의 구분자는 / 로 구분
'찾을 디렉토리나 파일 대상'
받드시 전체를 ' 나 "로 묶어줌
"* *" : 공백 문자열이 들어간 모든 파일이나 디렉토리 대상
"*" : 모든 파일이나 디렉토리 대상
"*.mp3" : 확장자(?)가 mp3인 모든 파일
"*.[hH][tT][mM][lL]" : *.html *.HTML *.Html ... 등과 매치
"/home/*.php" : /home 디렉토리를 대상으로 *.php 파일
"home/*.php" : 현재 디렉토리에서 상대 경로가 home 인 디렉토리
[사용예 1]
/sdb1/mp3 디렉토리 및 그 하위 모든 디렉토리에서
mp3 파일이나 MP3 파일을 대상으로
파일이름에 공백(" ")이 들어갈 경우 "_" 로 바꿈
먼저 테스트해 봄
$ renameto -R --test '/ /_/' '/sdb1/mp3/* *.[mM][pP]3'
...
...
$
리스트가 나오면 --test 옵션을 빼고 실행함
$ renameto -R '/ /_/' '/sdb1/mp3/* *.[mM][pP]3'
...
...
$
-R
대상디렉토리(/sdb1/mp3) 및 그 하위의 모든 디렉토리 포함
--test
단지 테스트만 해봄
'/ /_/'
공백을 "_"으로 바꾸기
'/sdb1/mp3/* *.[mM][pP]3'
/sdb1/mp3/ 는 찾을 디렉토리의 시스템 절대경로
* *.[mM][pP]3 은 공백 문자열이 들어간 파일의 표현식
[사용예 2]
공백문자 없애기
$ renameto '/[ ]//' '*.mp3'
또는
$ renameto '/ //' '*.mp3'
특수문자들 " ( ) * . 없애기
$ renameto '/["()*.]//' '*.mp3'
특수문자들 [ ] 없애기
$ renameto '/[][]//' '*.mp3'
확장자 바꾸기
$ renameto '/.MP3$/.mp3/' '*.MP3'
파일이름 앞에 'My' 문자열 추가하기
$ renameto '/^/My/' '*.mp3'
파일이름 끝에 'My' 문자열 추가하기
$ renameto '/$/My/' '*.mp3'
[사용예 3] dot(.) 문자 없애기
틀린예 :
$ renameto '/.//' '*'
맞는경우 :
$ renameto '/[.]//' '*'
또는
$ renameto '/.//' '*'
[사용예 4] 대소문자 바꾸기
틀린예 :
$ renameto '/[A-Z]/a-z/' '*' (-c 옵션이 빠져있음)
$ renameto '/[A-Z]/a-d/' '*' (문자클래스 범위가 맞질않음)
대문자 -> 소문자로 바꾸기
$ renameto -c '/[A-Z]/a-z/' '*'
or
$ renameto -c '/[A-Z]/[a-z]/' '*'
소문자 -> 대문자 바꾸기
$ renameto -c '/[a-z]/A-Z/' '*'
or
$ renameto -c '/[a-z]/[A-Z]/' '*'
특정 클래스(E-K) 알파벳문자 바꾸기
$ renameto -c '/[E-K]/e-k/' '*'
$ renameto -c '/[e-k]/E-K/' '*'
[사용예 5] 문자클래스 그룹화
모든 대문자 다음에 '_' 문자 추가하기
$ renameto '/([A-Z])/1_/' '*'
첫번째 공백에 '-' 추가하기
$ renameto '/^([^ ]+) /1-/' '*'
[사용예 6] 종합예제 : mp3 파일 정리
$ ls
01 aaa.mp3
02 bbb (b1).mp3
03 ccc Abcd efg.MP3
04 ddd bdefgg DDD.mp3
05 eee kkk.MP3
...
위와 같은 형식을 취하는 여러개의 파일들을
artist-[00]-aaa_bbb_ccc.mp3
이와같이 형식으로 바꾸려면(대문자->소문자),
1. 대문자를 모두 소문자로 바꾸기
$ renameto -c '/[A-Z]/a-z/' '*.[mM][pP]3'
2. 첫번째 공백을 ']-' 문자로 바꾸기(그룹화 사용)
$ renameto '/^([^ ]+) /1]-/' '*.mp3'
3. 모든 파일앞에 'artist-[' 문자 추가
$ renameto '/^/artist-[' '*'
4. 나머지 모든 공백을 '_'로 바꾸기
$ renameto '/[ ]/_/' '*'
5. 특수문자 괄호 (, )를 없애기(필요하다면)
$ renameto '/[()]//' '*'
6. 확인
$ ls
artist-[01]-aaa.mp3
artist-[02]-bbb_b1.mp3
artist-[03]-ccc_abcd_efg.mp3
artist-[04]-ddd_bdefgg_ddd.mp3
artist-[05]-eeekkk.mp3
...
*주의)
가능한 특수문자는 [와 ]사이에 넣어서
테스트(-t, --test)를 한 다음에 실행 하세요.
---------------------------------------------
#!/bin/sh
##
## "Chilbing, Kim"<san2(at)linuxchannel.net>
## 2003.10.22 patched for FreeBSD
## 2002.11.05 add upcase and lowcase, usage to stderr
## 2002.04.13 patch(sort)
## 2002.03.29 patch(thanks '단n키')
## 2002.03.27 add options
## 2002.03.04
##
## http://ftp.linuxchanel.net/devel/renameto/
##
## chmod a+rx renameto
## cp renameto /usr/local/bin/renameto
usage()
{
echo "${T_MD}usage${T_ME} : renameto [options] "/from_string/to_string/" "<target_files|target_directory>"" >&1
echo " ${T_MD}options${T_ME}" >&2
echo " -R : include all sub directory (not default)" >&2
echo " -Rn : 'n' is sub directory maxdepth number" >&2
echo " '-R0' is current directory (same as not given options)" >&2
echo " -t,-test,--test : only test view" >&2
echo " -c,-case,--case : translate upcase and lowcase" >&2
echo " -v,-view,--view : only test view" >&2
echo " -d,-dir,--dir : only directory adjust (not files)" >&2
echo " -h,-help,--help : help" >&2
echo " ${T_MD}example${T_ME}" >&2
echo " renameto /html/php/ "*.html" (same as rename command)" >&2
echo " renameto -R "/ /_/" "* *.mp3" (replace file " " to "_" all sub-directory)" >&2
echo " renameto -R -test "/ /_/" "* *.mp3" (test view)" >&2
echo " renameto -R -dir "/ /_/" "/home/xxx/mp3/* *" (replace directory)" >&2
echo " renameto -R -case "/[A-Z]/[a-z]/" "*" (to lowcase)" >&2
echo " renameto -R -case "/[e-k]/[E-K]/" "*" (to upcase)" >&2
echo "source download ${T_MB}http://ftp.linuxchannel.net/devel/renameto/${T_ME}" >&2
exit 0
}
testing()
{
echo "${1}: found '$2'(${T_MG}${4}${T_ME})"
}
action()
{
echo "${1}: renamed to '${T_MG}${3}${T_ME}'"
mv "$2" "$3"
}
## set color
## source '/etc/sysconfig/init'
##
case $TERM in
xterm|xterm*|vt220|vt220*|linux)
T_MG=`echo -e "33[1;32m"` ## bold green
T_MB=`echo -e "33[1;34m"` ## bold blue
T_MR=`echo -e "33[1;31m"` ## bold red
T_MD=`echo -e "33[1;39m"` ## bold white
T_ME=`echo -e "33[0;39m"` ## normal white
;;
default)
T_MG=''
T_MB=''
T_MR=''
T_MD=''
T_ME=''
;;
esac
## check_argument number
##
[ "$#" -lt "2" ] && usage
## get options
##
for ARGS in $* ; do
case "$ARGS" in
-R*)
SUB_DIR=$ARGS
;;
-t*|-v*|--t*|--v*)
CMD=testing
;;
-c*|--c*)
CASE=1
;;
-d*|--d*)
TYPE=d ## patch 2002.03.29
SORT="-r"
;;
-h*|--h*)
usage
;;
-*)
: ;;
*)
unshift=1
;;
esac
[ X"$unshift" = "X" ] && shift
done
STRING=$1
TARGET_FILES=$2
## recheck argument number
##
[ "$#" -lt "2" ] && usage
## check sub_dir
##
if [ X"$SUB_DIR" = "X" ] ; then
MAXDEPTH="-maxdepth 1" ## current directory search
else
MAXDEPTH=`echo "$SUB_DIR" | sed 's/^-R//'`
if [ `echo "$MAXDEPTH" | egrep "[^0-9]"` ] ; then
echo "${T_MR}invalid option($SUB_DIR) argument !!!, ex) -R, -R0, -R1, -R2, -R3, ...${T_ME}" >&2
usage
fi
## if $MAXDEPTH is null, then all sub directorys search
##
if [ X"$MAXDEPTH" != "X" ] ; then
maxdepth=$(($MAXDEPTH + 1))
MAXDEPTH="-maxdepth $maxdepth"
fi
fi
## check string
## patch 2002.03.29
##
check_string=`echo "$STRING" | egrep "^/([^/]+)/([^/]*)/$"`
if [ X"$check_string" = "X" ] ; then
echo "${T_MR}invalid string($STRING) !!!${T_ME}" >&2
usage
fi
## check target_files
##
if [ X"$TARGET_FILES" = "X" ] || [ `echo $TARGET_FILES | grep "^-"` ] ; then
echo "${T_MR}invalid target_file($TARGET_FILES) !!!${T_ME}" >&2
usage
fi
## check find path
##
if [ X"`echo $TARGET_FILES | grep /`" != "X" ] ; then
## same as find_path=`echo "$TARGET_FILES" | sed 's//([^/]*)$//'`
##
find_path=${TARGET_FILES%/*}
find_path=${find_path:-/} ## recheck, patch 2002.03.29
## same as TARGET_FILES=`echo "$TARGET_FILES" | awk -F"/" '{print($NF)}'`
##
TARGET_FILES=${TARGET_FILES##*/}
fi
## get from string, to string
##
from_string=`echo "$STRING" | awk -F"/" '{print($2)}'`
to_string=`echo "$STRING" | awk -F"/" '{print($3)}'`
## check upcase, lowcase translate
## not good(bad checking T.T)
##
if [ X"$CASE" = "X1" ] ; then
from_tr=`echo "$from_string" | sed 's/[][]//g'`
to_tr=`echo "$to_string" | sed 's/[][]//g'`
if [ X$(echo "$from_tr" | tr A-Z a-z) != X$(echo "$to_tr" | tr A-Z a-z) ] ; then
echo "${T_MR}invalid string($STRING) !!!${T_ME}" >&2
usage
fi
fi
## lists of files
##
files=`find ${find_path:-.} -name "$TARGET_FILES" -type ${TYPE:-f} $MAXDEPTH | sort $SORT 2>/dev/null`
## good idea
##
IFS_ORIG="$IFS"
IFS='
'
i=0
for pfile in $files ; do
## same as file=`basename $pfile`
##
file=${pfile##*/}
## same as path=`echo "$pfile" | sed 's//([^/]*)$//'`
##
path=${pfile%/*}
## if include ${from_string} string in $file, then action
##
if [ X$(echo "$file" | grep "$from_string") != "X" ] ; then
i=$(($i+1))
if [ X"$CASE" = "X1" ] ; then
tofile=`echo "$file" | tr "$from_tr" "$to_tr"`
else
## do not sed 's/$AAA/$BBB/g', you must sed "s/$AAA/$BBB/g"
##
tofile=`echo "$file" | sed "s${STRING}g"`
fi
${CMD:-action} "$i" "$pfile" "$path/$tofile" "$tofile"
fi
done
IFS="$IFS_ORIG"
exit 0
[출처] 특정 파일/디렉토리를 바꾸기 쉘스크립트 포함|작성자 가을흔적
'프로그래밍 > BASH SHELL' 카테고리의 다른 글
[vi] 특정 단어부터 끝까지 지우기 (0) | 2015.01.27 |
---|---|
간단한 쉘 스크립트의 작성 (0) | 2015.01.27 |
bash 프롬프트 howto (0) | 2015.01.27 |
grep 계열 명령어 (0) | 2015.01.27 |
정규표현식 (0) | 2015.01.27 |