銀月の符号

Python 使い見習いの日記・雑記

気がつけばファイル操作の話に(前記事、ジェネレータをうまく作れるようになりたい)

昨日の続き。ジェネレータ作ってみたメモだったはずなのにファイル操作のメモになってしまって、タイトルどうしたものか。

既存ファイルを上書きしないコピー、ムーブ(POSIX編)

たぶんこう。 O_EXCL で open システムコールしてファイルを上書きしない環境ならば問題ないはず。でも O_EXCL が本当に効くかどうかは OS だけでなくファイルシステムにも依存したような。 Ubuntu 8.04 で動作確認。

O_EXCL フラグ付き open でファイルを作ってみて、無事作ることができたら既存ファイルはなかったとわかる。あとは作ったファイルに shutil2.copy や os.rename で元ファイルを重ねて出来上がり。

12日追記:いや、ファイル作成に成功したけど重ねるのには失敗した場合、削除しないとごみが残る? 完成してないなこれ。

import os

if os.name == 'posix':
    def copy_safe(old, new):
        for new_path in path_generator(new):
            try:
                fd = os.open(new_path, os.O_RDWR | os.O_EXCL | os.O_CREAT, 0600)
                os.close(fd)
                shutil.copy2(old, new_path)
                break
            except OSError:
                pass
        else:
            raise IOError()

    def move_safe(old, new):
        for new_path in path_generator(new):
            try:
                fd = os.open(new_path, os.O_RDWR | os.O_EXCL | os.O_CREAT, 0600)
                os.close(fd)
                os.rename(old, new_path)
                break
            except OSError:
                pass
        else:
            raise IOError()