나의 유닉스 지식은 그리 좋지 않습니다. 나는 디렉토리에 있는 파일 세트의 이름을 바꾸는 쉘 스크립트를 작성하려고 합니다. 1709532255.mp4
여기서 20240304_070415.mp4
에포크 1709532255
시간은 항상 에포크 시간입니다.
나는 찾았다
date -d @1708532255 +'%Y%m%d_%H%M%S'
...원하는 형식을 제공하지만 스크립트에서 작동하도록 할 수 없습니다.
이것은 내 스크립트입니다.
#!/bin/bash
for file in /media/HAVideo/Eingang/Test/2/*.mp4
do
filename=`echo "${file}" | cut -d'.' -f1`
readable=`date -d @$filename +"%Y%m%d%H%M%S"`
mv "${file}" "${readable}"
done
출력은 다음과 같습니다
...
date: invalid date '@/media/HAVideo/Eingang/Test/2/1709532255'
mv: can't rename '/media/HAVideo/Eingang/Test/2/1709532255.mp4': No such file or directory
...
답변1
방금 놓친 내용 cd
:
#!/bin/bash
cd /media/HAVideo/Eingang/Test/2/ || exit # <- what changed
for file in *.mp4
do
filename=`echo "${file}" | cut -d'.' -f1`
readable=`date -d @$filename +"%Y%m%d%H%M%S.mp4"`
mv "${file}" "${readable}"
done
그러나 몇 가지 문제가 있습니다.
대신 백틱을 사용하세요 $( )
. 그리고 들여쓰기를 올바르게 하세요.
바라보다http://mywiki.wooledge.org/BashFAQ/082
더 나은 버전:
#!/bin/bash -
cd /media/HAVideo/Eingang/Test/2/ || exit
for file in *.mp4 ; do
mv -- "$file" "$(date -d "@${file%.*}" +"%Y%m%d%H%M%S.mp4")"
done
${file%.*}
내장되어 있습니다매개변수 확장
바라보다:http://mywiki.wooledge.org/BashFAQ/073그리고
LESS='+/Parameter Expansion' man bash
또한 참조wiki.bash-hackers.org/syntax/pe
이는 ksh의 표준 sh
연산자이고 이 코드에는 bashism이 없으므로 shebang을 #! /bin/sh -
bash 종속성으로 변경하고 제거할 수 있습니다. 그러나 이는 date -d
비표준 GNU주의이므로 printf '%(format)T'
최신 버전의 bash(ksh93에서 복사)를 사용하면 이를 방지할 수 있습니다.
답변2
그리고 zsh
:
$ zmodload zsh/datetime
$ autoload zmv
$ cd /media/HAVideo/Eingang/Test/2/
$ zmv -n '(<->)(.mp4)' '$(strftime %Y%m%d_%H%M%S $1)$2'
mv -- 1709532255.mp4 20240304_060415.mp4
( -n
만족하면 삭제(테스트 실행)).
1709532255는 시간대 독립적이지만 20240304_060415
그렇지 않으며 모호합니다. UTC 오프셋을 포함하는 ISO8601 스타일 날짜 형식을 사용하여 현지 시간을 명확하게 하고 계속 사용할 수 있습니다. %Y%m%d_%H%M%S
예를 들어 동일한 타임스탬프를 %FT%T%z
얻을 수 있지만 두 개의 다른 시간대에 2024-03-04T06:04:15+0000
있을 수 있습니다 .2024-03-04T07:04:15+0100
답변3
오류가 표시되는 이유:
date: invalid date '@/media/HAVideo/Eingang/Test/2/1709532255'
명령에 따라 확장자를 제외한 파일의 전체 경로를 전달했기 때문입니다 cut
.
[...snipped out irrelevant parts...]
filename=`echo "${file}" | cut -d'.' -f1`
...
readable=`date -d @$filename +"%Y%m%d%H%M%S"`
평가:
readable=`date -d @/media/HAVideo/Eingang/Test/2/1709532255 +"%Y%m%d%H%M%S"`
그러므로 filename
그렇습니다 /media/HAVideo/Eingang/Test/2/1709532255
.
귀하의 스크립트는 대부분 작동합니다. filename=...
전체 경로가 아닌 파일의 기본 이름만 검색하도록 행을 수정했습니다 .
#!/bin/bash
for file in /media/HAVideo/Eingang/Test/2/*.mp4
do
filename=`basename "${file}" | cut -d'.' -f1`
readable=`date -d @$filename +"%Y%m%d%H%M%S"`
mv "${file}" "${readable}"
done
물론 파일 확장자를 제거하고 변수 이름을 변경하여 코드를 좀 더 명확하게 만들 수 있으므로 불필요한 내용을 추가로 제거할 수도 cut
있습니다 basename
.
for src in /media/HAVideo/Eingang/Test/2/*.mp4
do
epoch="$(basename "$src" .mp4)"
dst="$(date -d "@$epoch" +"%Y%m%d%H%M%S")"
mv "$src" "$dst"
done
답변4
사용진주(모든 운영 체제에서 작동)
perl -MTime::Piece -e '
for (@ARGV) {
my $file = $_;
s/\..*$//;
rename $file, Time::Piece->strptime($_, "%s")->strftime("%Y%m%d_%H%M%S")
}
' *.mp4
Time::Piece
모듈은 Perl로 패키지되어 있으며 설치가 필요하지 않습니다.