Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Best Way to Get File Modified Time in Seconds

This seems to be a classic case of non-standard features on various platforms.

Quite simply, I want a universally (or at least widely) supported method for getting the modified time of a file as a unix timestamp in seconds.

Now I know of various ways to do this with stat but most are platform specific; for example stat -c %Y $file works for some, but won't work on OS X (and presumably other FreeBSD systems) which uses stat -f %m $file instead.

Likewise, some platforms support date -r $file +%s, however OS X/FreeBSD again does not as the -r option seems to just be an alternate to using +%s for getting a unix timestamp, rather than the reference file option as on other platforms.

The other alternative I'm familiar with is to use find with the -printf option, but again this is not widely supported. The last method I know of is parsing ls which, aside from being an unpleasant thing to have to do, is not something I believe can (or at least should) be relied upon either.

So, is there a more compatible method for getting a file's modified time? Currently I'm just throwing different variations of stat into a script and running them until one exits with a status of zero, but this is far from ideal, even if I cache the successful command to run first in future.

like image 621
Haravikk Avatar asked Jul 26 '13 10:07

Haravikk


People also ask

How can I tell what time a file was modified?

To see the access time for a file with ls , append the -u option in your command. In this case, our access time is the same as the file's modified time, which is normal for files that have not been accessed since they were last saved.

How do I find the creation time of a file?

GetCreationTime(String) Returns the creation date and time of the specified file or directory.

What is the difference between change time and modification time of a file?

Modification Time: is the time when the contents of the file was last modified. For example, you used an editor to add new content or delete some existing content. Change Time: is the time when the file's inode has been changed. For example, by changing permissions, ownership, file name, number of hard links.


1 Answers

Since it seems like there might not be a "correct" solution I figured I'd post my current one for comparison:

if stat -c %Y . >/dev/null 2>&1; then
    get_modified_time() { stat -c %Y "$1" 2>/dev/null; }
elif stat -f %m . >/dev/null 2>&1; then
    get_modified_time() { stat -f %m "$1" 2>/dev/null; }
elif date -r . +%s >/dev/null 2>&1; then
    get_modified_time() { date -r "$1" +%s 2>/dev/null; }
else
    echo 'get_modified_time() is unsupported' >&2
    get_modified_time() { printf '%s' 0; }
fi

[edit] I'm updating this to reflect the more up to date version of the code I use, basically it tests the two main stat methods and a somewhat common date method in any attempt to get the modified time for the current working directory, and if one of the methods succeeds it creates a function encapsulating it for use later in the script.

This method differs from the previous one I posted since it always does some processing, even if get_modified_time is never called, but it's more efficiently overall if you do need to call it most of the time. It also lets you catch an unsupported platform earlier on.

If you prefer the function that only tests functions when it is called, then here's the other form:

get_modified_time() {
    modified_time=$(stat -c %Y "$1" 2> /dev/null)
    if [ "$?" -ne 0 ]; then
        modified_time=$(stat -f %m "$1" 2> /dev/null)
        if [ "$?" -ne 0 ]; then
            modified_time=$(date -r "$1" +%s 2> /dev/null)
            [ "$?" -ne 0 ] && modified_time=0
        fi
    fi
    echo "$modified_time"
}
like image 79
Haravikk Avatar answered Sep 29 '22 21:09

Haravikk