Creating files with Python and mimicking the “touch command”

We will learn the following while working on our Python Script:

  1. Creating files with Python

  2. Touch command

  3. Result

Creating files with Python

Creating a single file

Here’s a one-liner for creating a file with Python.

<span>open</span><span>(</span><span>'</span><span>hello_world.txt</span><span>'</span><span>,</span><span>'</span><span>w</span><span>'</span><span>)</span>
<span>open</span><span>(</span><span>'</span><span>hello_world.txt</span><span>'</span><span>,</span><span>'</span><span>w</span><span>'</span><span>)</span>
open('hello_world.txt','w')

Enter fullscreen mode Exit fullscreen mode

This single statement creates hello_world.txt, but we don’t want fixed file names, do we?

The question is, how to conveniently provide input to the script to create a file with Python.

We can use a variable for storing the name of the file, like this…

<span>filename</span> <span>=</span> <span>"</span><span>hello_world.txt</span><span>"</span>
<span>open</span><span>(</span><span>filename</span><span>,</span> <span>'</span><span>w</span><span>'</span><span>)</span>
<span>filename</span> <span>=</span> <span>"</span><span>hello_world.txt</span><span>"</span>
<span>open</span><span>(</span><span>filename</span><span>,</span> <span>'</span><span>w</span><span>'</span><span>)</span>
filename = "hello_world.txt" open(filename, 'w')

Enter fullscreen mode Exit fullscreen mode

But this will be a mess if we want to create multiple files with Python, as each time we want to create a file, we would need to update filename variable manually which ain’t so cool.

Creating multiple files

The solution to the above problem is, making a list of filenames.

<span>filenames</span> <span>=</span> <span>[</span><span>'</span><span>hello_world.txt</span><span>'</span><span>,</span> <span>'</span><span>random_file.txt</span><span>'</span><span>,</span> <span>'</span><span>lol.txt</span><span>'</span><span>]</span>
<span>for</span> <span>filename</span> <span>in</span> <span>filenames</span><span>:</span>
<span>open</span><span>(</span><span>filename</span><span>,</span> <span>'</span><span>w</span><span>'</span><span>)</span>
<span>filenames</span> <span>=</span> <span>[</span><span>'</span><span>hello_world.txt</span><span>'</span><span>,</span> <span>'</span><span>random_file.txt</span><span>'</span><span>,</span> <span>'</span><span>lol.txt</span><span>'</span><span>]</span>
<span>for</span> <span>filename</span> <span>in</span> <span>filenames</span><span>:</span>
    <span>open</span><span>(</span><span>filename</span><span>,</span> <span>'</span><span>w</span><span>'</span><span>)</span>
filenames = ['hello_world.txt', 'random_file.txt', 'lol.txt'] for filename in filenames: open(filename, 'w')

Enter fullscreen mode Exit fullscreen mode

This is MUCH BETTER 🤩! But wait, It’s only good for one-time use . What if we want to make more files later in a single go?

Then we would have to update the filenames list again and again.

Providing filenames from the command line

For this fix, we can provide values (filenames) from the command line! We only need to make two changes in our existing code.

Add from sys import argv and use the value of argv with for filenames.

<span>from</span> <span>sys</span> <span>import</span> <span>argv</span>
<span>filenames</span> <span>=</span> <span>argv</span><span>[</span><span>1</span><span>:]</span> <span># Ignore the first element (script file) </span>
<span>for</span> <span>filename</span> <span>in</span> <span>filenames</span><span>:</span>
<span>open</span><span>(</span><span>filename</span><span>,</span> <span>'</span><span>w</span><span>'</span><span>)</span>
<span>from</span> <span>sys</span> <span>import</span> <span>argv</span>

<span>filenames</span> <span>=</span> <span>argv</span><span>[</span><span>1</span><span>:]</span> <span># Ignore the first element (script file) </span>
<span>for</span> <span>filename</span> <span>in</span> <span>filenames</span><span>:</span>
    <span>open</span><span>(</span><span>filename</span><span>,</span> <span>'</span><span>w</span><span>'</span><span>)</span>
from sys import argv filenames = argv[1:] # Ignore the first element (script file) for filename in filenames: open(filename, 'w')

Enter fullscreen mode Exit fullscreen mode

This seems to work just fine but there’s a nasty bug in it.

If the file already exists, it will wipe the whole file’s contents. Thanks to the file access mode 'w' (write mode) which we used.

The fix is very simple. We just need to replace 'w' with 'a' (append mode) which will ignore the files which already exist and create new ones if they don’t.

<span>from</span> <span>sys</span> <span>import</span> <span>argv</span>
<span>filenames</span> <span>=</span> <span>argv</span><span>[</span><span>1</span><span>:]</span> <span># Ignore the first element (script file) </span>
<span>for</span> <span>filename</span> <span>in</span> <span>filenames</span><span>:</span>
<span>open</span><span>(</span><span>filename</span><span>,</span> <span>'</span><span>a</span><span>'</span><span>)</span> <span># Using append mode now </span>
<span>from</span> <span>sys</span> <span>import</span> <span>argv</span>

<span>filenames</span> <span>=</span> <span>argv</span><span>[</span><span>1</span><span>:]</span> <span># Ignore the first element (script file) </span>
<span>for</span> <span>filename</span> <span>in</span> <span>filenames</span><span>:</span>
    <span>open</span><span>(</span><span>filename</span><span>,</span> <span>'</span><span>a</span><span>'</span><span>)</span> <span># Using append mode now </span>
from sys import argv filenames = argv[1:] # Ignore the first element (script file) for filename in filenames: open(filename, 'a') # Using append mode now

Enter fullscreen mode Exit fullscreen mode

Testing our script

I saved the script as touch.py here’s the execution…

Creating multiple files with our Python script

Existing files remain unchanged, YAY!

Touch command

Our script is GOOOOOODDD!!!

But there’s still one thing we can add to make it behave more like touch command, that is, updating a file’s access and modified time.

For the sake of keeping things simple, we will just update the modified time of the file.

Getting the access time and modified time of a file

The os module in Python has a stat function that performs a stat system call (runs a stat command behind the scenes) and returns the result in an accessible way.

<span>from</span> <span>os</span> <span>import</span> <span>stat</span>
<span>st_info</span> <span>=</span> <span>stat</span><span>(</span><span>filename</span><span>)</span>
<span>access_time</span> <span>=</span> <span>st_info</span><span>.</span><span>st_atime</span>
<span>modified_time</span> <span>=</span> <span>st_info</span><span>.</span><span>st_mtime</span>
<span>from</span> <span>os</span> <span>import</span> <span>stat</span>
<span>st_info</span> <span>=</span> <span>stat</span><span>(</span><span>filename</span><span>)</span>

<span>access_time</span> <span>=</span> <span>st_info</span><span>.</span><span>st_atime</span> 
<span>modified_time</span> <span>=</span> <span>st_info</span><span>.</span><span>st_mtime</span>
from os import stat st_info = stat(filename) access_time = st_info.st_atime modified_time = st_info.st_mtime

Enter fullscreen mode Exit fullscreen mode

We can use the result st_info which contains the status of the file including the access and modified time for modifying the file.

Getting the current time

time function in the time module returns the current time which we can directly use in our script for modifying the files with our script.

<p><span>from</span> <span>time</span> <span>import</span> <span>time</span><br> <span>current_time</span> <span>=</span> <span>time</span><span>()</span> <span># current time in seconds (since Epoch)<br> </span></p>
<p><span>from</span> <span>time</span> <span>import</span> <span>time</span><br> <span>current_time</span> <span>=</span> <span>time</span><span>()</span> <span># current time in seconds (since Epoch)<br> </span></p>

from time import time
current_time = time() # current time in seconds (since Epoch)

Enter fullscreen mode Exit fullscreen mode



Updating Access and Modified time in a file

The os module also has a function for updating this access and modified time called utime.

Here’s how this can be done,

<p><span>from</span> <span>os</span> <span>import</span> <span>utime</span></p>
<p><span># if the second argument isn't passed, it will set the access</span></p>
<h1 id="wznav_10"> <a href="https://blogs.ink/?golink=aHR0cHM6Ly9kZXYudG8vL2dhZ2FuZ3VseWFuaS9jcmVhdGluZy1maWxlcy13aXRoLXB5dGhvbi1hbmQtbWltaWNraW5nLXRoZS10b3VjaC1jb21tYW5kLWhobSNhbmQtbW9kaWZpZWQtdGltZS10by1jdXJyZW50LXRpbWU=" target="_blank" rel="nofollow"> </a> and modified time to current time </h1>
<p><br> <span>utime</span><span>(</span><span>filename</span><span>)</span></p>
<p><span># for setting our custom access and modified time<br> </span><span>utime</span><span>(</span><span>filename</span><span>,</span> <span>(</span><span>access_time</span><span>,</span> <span>current_time</span><span>))</span></p>
<p><span>from</span> <span>os</span> <span>import</span> <span>utime</span></p>

<p><span># if the second argument isn't passed, it will set the access</span></p>
<h1 id="wznav_10"> <a href="https://blogs.ink/?golink=aHR0cHM6Ly9kZXYudG8vL2dhZ2FuZ3VseWFuaS9jcmVhdGluZy1maWxlcy13aXRoLXB5dGhvbi1hbmQtbWltaWNraW5nLXRoZS10b3VjaC1jb21tYW5kLWhobSNhbmQtbW9kaWZpZWQtdGltZS10by1jdXJyZW50LXRpbWU=" target="_blank" rel="nofollow"> </a> and modified time to current time </h1>

<p><br> <span>utime</span><span>(</span><span>filename</span><span>)</span></p>

<p><span># for setting our custom access and modified time<br> </span><span>utime</span><span>(</span><span>filename</span><span>,</span> <span>(</span><span>access_time</span><span>,</span> <span>current_time</span><span>))</span></p>

from os import utime

# if the second argument isn't passed, it will set the access

and modified time to current time


utime(filename)

# for setting our custom access and modified time
utime(filename, (access_time, current_time))

Enter fullscreen mode Exit fullscreen mode



Implementing the Touch Command

Now, we can finally put together everything we have done so far in one final script.

<p><span>from</span> <span>sys</span> <span>import</span> <span>argv</span><br> <span>from</span> <span>time</span> <span>import</span> <span>time</span><br> <span>from</span> <span>os</span> <span>import</span> <span>utime</span><span>,</span> <span>stat</span></p>
<p><span>for</span> <span>name</span> <span>in</span> <span>argv</span><span>[</span><span>1</span><span>:]:</span><br> <span>open</span><span>(</span><span>name</span><span>,</span> <span>'</span><span>a</span><span>'</span><span>)</span><br> <span>st_info</span> <span>=</span> <span>stat</span><span>(</span><span>name</span><span>)</span> <span># Storing file status<br> </span> <span># setting access time with file's access time (no change)<br> </span> <span># setting modified time with current time of the system)<br> </span> <span>utime</span><span>(</span><span>name</span><span>,</span> <span>(</span><span>st_info</span><span>.</span><span>st_atime</span><span>,</span> <span>time</span><span>()))</span></p>
<p><span>from</span> <span>sys</span> <span>import</span> <span>argv</span><br> <span>from</span> <span>time</span> <span>import</span> <span>time</span><br> <span>from</span> <span>os</span> <span>import</span> <span>utime</span><span>,</span> <span>stat</span></p>

<p><span>for</span> <span>name</span> <span>in</span> <span>argv</span><span>[</span><span>1</span><span>:]:</span><br> <span>open</span><span>(</span><span>name</span><span>,</span> <span>'</span><span>a</span><span>'</span><span>)</span><br> <span>st_info</span> <span>=</span> <span>stat</span><span>(</span><span>name</span><span>)</span> <span># Storing file status<br> </span> <span># setting access time with file's access time (no change)<br> </span> <span># setting modified time with current time of the system)<br> </span> <span>utime</span><span>(</span><span>name</span><span>,</span> <span>(</span><span>st_info</span><span>.</span><span>st_atime</span><span>,</span> <span>time</span><span>()))</span></p>

from sys import argv
from time import time
from os import utime, stat

for name in argv[1:]:
open(name, 'a')
st_info = stat(name) # Storing file status
# setting access time with file's access time (no change)
# setting modified time with current time of the system)
utime(name, (st_info.st_atime, time()))

Enter fullscreen mode Exit fullscreen mode



Result

Finally, It’s time we use the script for creating files and stuff.

Multiple files created Succesfully!

Our script successfully updates the modified time of existing file!!

That’s it! Our script makes multiple files and mimics the touch command as it sets the modified time!

You can tweak it and add more features to make it a complete touch command clone.

Link to script file

原文链接:Creating files with Python and mimicking the “touch command”

© 版权声明
THE END
喜欢就支持一下吧
点赞5 分享
Death comes to all, but great achievements raise a monument which shall endure until the sun grows old.
死亡无人能免,但非凡的成就会树起一座纪念碑,它将一直立到太阳冷却之时
评论 抢沙发

请登录后发表评论

    暂无评论内容