I'd like to create a file with path x using python. I've been using os.system(y) where y = 'touch %s' % (x). I've looked for a non-directory version of os.mkdir, but I haven't been able to find anything. Is there a tool like this to create a file without opening it, or using system or popen/subprocess?
2 Answers
There is no way to create a file without opening it There is os.mknod("newfile.txt") (but it requires root privileges on OSX). The system call to create a file is actually open() with the O_CREAT flag. So no matter how, you'll always open the file.
So the easiest way to simply create a file without truncating it in case it exists is this:
open(x, 'a').close()
Actually you could omit the .close() since the refcounting GC of CPython will close it immediately after the open() statement finished - but it's cleaner to do it explicitely and relying on CPython-specific behaviour is not good either.
In case you want touch's behaviour (i.e. update the mtime in case the file exists):
import os
def touch(path):
with open(path, 'a'):
os.utime(path, None)
You could extend this to also create any directories in the path that do not exist:
basedir = os.path.dirname(path)
if not os.path.exists(basedir):
os.makedirs(basedir)
9 Comments
w (write) flag empties it while opening it with a (append) doesn't.with makes it easier to close the file timely (and even in the face of exceptions and circular references) and the code becomes clearer to boot.with open(filename, mode='a'): passOf course there IS a way to create files without opening. It's as easy as calling os.mknod("newfile.txt"). The only drawback is that this call requires root privileges on OSX.
4 Comments
open().close() approach wherever possible.pathlib and the path-like objects are a fairly recent addition to Python and absolutely superfluous in my opinion (like most features introduced after 3.6), but yes, that will work. However, if you look at the source code, you will find that it also just calls os.open() followed by os.close() to do the deed.
subprocess.call(['touch', x])print(x); os.mkdir(y), zint = int(z)would be a very "clean" program in my opinion, because it's all functions that preform their task with no room for error or overhead. Something likeos.touch()would seem "clean" to me, because however many thousands of times it runs, the workflow is the same, and it even if the script takes a year, I know the code has fulfilled it's purpose without any error margin by the end.touchdoes its job? git.savannah.gnu.org/cgit/coreutils.git/tree/src/… line 134