폴더를 동시에 이동하고 다시 만드는 방법은 무엇입니까?


9

statistics데이터 파일이 정기적으로 저장되는 우분투 서버에 폴더 가 있습니다. 새 파일을 저장할 수 있도록 폴더를 다시 만드는 동안 statistics폴더 이름을 바꾸려면 어떻게 해야합니까?backup-xxstatistics

statistics폴더 의 파일은 PHP에 의해 생성됩니다 file_put_contents.

폴더에 많은 파일이 있으므로 폴더 이름을 바꾸는 것이 statistics좋습니다.


처음에 나는 당신이 "가능한 한" 동작이 "원자" 여야한다는 것을 " 동시에" 의미한다고 생각했다 .
phk

@ phk 예, 정확히 제가 의미 한 바입니다.
Googlebot

올바른 용어는 "폴더"가 아닌 "디렉토리"입니다.
Berk Özbalcı

답변:


7
mv statistics backup-xx && mkdir statistics

이렇게하면 기존 statistics디렉토리의 이름이로 backup-xx바뀌고 성공하면 새 statistics디렉토리 를 작성하게 됩니다.

보다 원자적인 작업을 위해서는 디렉토리를 만들 statistics-001거나 비슷한 001형식으로 오늘 날짜 로 바꾸어 비슷한 디렉토리를 만드 십시오 statistics.

mkdir statistics-001
ln -s statistics-001 statistics

새 데이터가 깨끗한 디렉토리로 이동하도록이를 "회전"시키려면 먼저 디렉토리를 작성한 다음 statistics링크를 다시 작성하십시오 .

mkdir statistics-002
ln -sf statistics-002 statistics

mv statistics-001 backup-001

이 방법은 어떤 프로그램 작성 statistics디렉토리 않을 것입니다 (이 심볼릭 링크 포인트는 것을 즉, 디렉토리) 1 그것을 찾기 위해 실패하지 않습니다.

statistics가리키는 디렉토리에 특별한 권한이나 소유권 설정이 필요한 경우 링크를 다시 작성하기 전에이를 설정하십시오.

1 또는 오히려이 방법으로 표준 유닉스 도구를 사용하여 프로그램 에 유효한 대상 디렉토리가 없는 시간을 최대한 최소화 할 수 있습니다.


1
chown --reference=backup-xx statistics ; chmod --reference=backup-xx statistics소유권과 권한을 설정할 수도 있습니다 . 이름 바꾸기 전에 이름을 바꾸는 것이 이상적 mkdir new ; chown ; chmod ; mv stats backup ; mv new stats입니다.
Stephen Harris

@StephenHarris 예, 해당 플래그가있는 시스템에서.
Kusalananda

그러나 이것은 원자 적이 지 않습니다. 그것은이다 가까이 는 아니지만 꽤 원자에.
CVn

@ MichaelKjörling 수정했습니다.
Kusalananda

ln -sf원자가 아닙니다. 이전 심볼릭 링크를 연결 해제 한 다음 새로운 심볼릭 링크를 만들도록 지정합니다. 대신 추가 임시 심볼릭 링크를 만들고 rename함수를 사용하여 ( mv예를 들어 명령을 통해 ) 이전 심볼을 원자 적으로 대체해야합니다. 여기에 대한 나의 접근 방식을 참조하십시오 : git.musl-libc.org/cgit/musl/tree/tools/…
R .. GitHub 중지 지원 얼음 얼음

12

디렉토리를 다른 디렉토리 로 원자 적으로 대체 할 수있는 방법이 없습니다 . 이전 디렉토리를 이동 한 다음 새 디렉토리를 작성할 수 있습니다.

mv statistics backup-xx
mkdir statistics

그러나 이것은 statistics존재하지 않는 작은 시간 창을 남깁니다 . 일부 프로세스가 언제든지 디렉토리에 파일을 놓을 수있는 경우에 문제가됩니다.

디렉토리를 원자 적으로 효과적으로 바꾸려면 기호 링크를 사용해야합니다. 이름부터 시작 시간이 포함 된 디렉토리를 작성하십시오.

mkdir "statistics-$(date +%Y%m%d)"

(또는 디렉토리 명명 규칙을 선택하려고합니다). 현재 위치에 고정 된 이름의 심볼릭 링크를 만듭니다.

ln -s  statistics

디렉토리를 바꾸려면 먼저 새 디렉토리와 새 심볼릭 링크를 만든 다음 이전 심볼릭 링크를 덮어 쓰도록 이동하십시오. 참고 일반도 있음을 mv상징적 링크도 일반은 ln -s이 작업을 수행합니다 : 그들은 대상 디렉토리 내부에 항목을 만들 것입니다. GNU coreutils ln -snf는 새로운 심볼을 만들기 전에 기존 심볼릭 링크를 제거하여 경로가 존재하지 않는 작은 시간 창을 남기기 때문에 적합하지 않습니다. mv -T새로운 심볼릭 링크에서 GNU coreutils를 사용할 수 있습니다 .

new_dir="statistics-$(date +%Y%m%d)"
mkdir "$new_dir"
ln -s statistics.new
mv -Tf statistics.new statistics

busybox' ln -sf또한 원자 적이 지 않으며 구현이 무엇인지 모르겠습니다.
phk

1
phk의 주석 심볼릭 링크는 실행중인 프로세스에 여전히 열린 디렉토리 파일 설명자 (symlink 대상)가있을 수 있으며 이름이 바뀐 디렉토리에 더 많은 새 파일을 만들 수 있기 때문에 100 % 안전하지 않습니다 ( openat()CWD 생각 또는 CWD). 디렉토리 의 내용 을 새 디렉토리로 옮길 것 입니다. 열린 파일에 대해서는 여전히 안전하지 않지만 조금 더 좋습니다. 의심 할 여지없이 logrotate그러한 문제를 가장 잘 존중해야합니다.
rudimeier

1
@phk symlink시스템 호출은 기존 파일을 덮어 쓰지 않으므로 불행히도 심볼릭 링크를 원자 적으로 직접 전환하는 것은 불가능합니다. rename시스템 호출은 기존 파일을 덮어 쓰게됩니다 만, 귀찮게 쉘에서 그것을 할 수없는 휴대용 방법이 없습니다; -T옵션 덕분에 GNU coreutils로 가능합니다 .
Gilles 'SO- 악마 중지'

3

디렉토리 이름을 바꾸지 마십시오. 파일이 많기 때문에 디렉토리 이름을 바꾸는 것이 좋습니다. 내가 당신이 이것을 원한다고 생각할 수있는 유일한 이유는 파일을 복사하는 데 너무 오래 걸리기 때문입니다. 그러나 파일이 동일한 파일 시스템의 한 위치로 이동되는 한 파일 이동 (즉, 이름 변경)은 즉시 수행됩니다. 파일 시스템을 변경하는 경우 디렉토리를 이동하든 내용을 이동하든 mv시간이 많이 걸리기 때문에 이것이 당신이해야 할 일이라고 생각합니다 cp.

그래서, 그냥하십시오 :

mkdir backup-xx && mv statistics/* backup-xx

숨겨진 파일도 가져와야 할 경우 다음을 수행 할 수 있습니다.

mkdir backup-xx && mv statistics/* statistics/.* backup-xx

또는 다음을 사용하는 경우 bash:

shopt -s dotglob; mkdir backup-xx && mv statistics/* statistics/.* backup-xx

이런 식으로 디렉토리는 항상 존재하지만 간단하고 빠른 조작으로 그 내용을 계속 이동합니다.


1

폴더 자체를 이동하지 않고 통계 폴더의 내용을 새로 작성된 디렉토리로 이동할 수 있습니다. 전체 폴더를 이동하면 다른 명령을 실행하여 디렉토리 권한을 변경해야합니다.

mkdir -p <path>/backup-xxx
mv statistics/* <path>/backup-xxx/.
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.