Unable to read the timestamp of Zsh history
Converting timestamps with awk
If you want to read the file itself, to use with, say, grep
or any other filter, you need to convert timestamps.
I made this script, which I save it in my /usr/local/bin
, and it works for bash and zshell:
Script uhistory.awk at /usr/local/bin/uhistory.awk
#!/usr/bin/awk -f
{
if (match($0,/^#/)) # bash
{
nlin++
#adata="@"substr($0,2)
#printf("%s ", adata)
cmdata = "date -d \"@" substr($0,2) "\" +\"%F %H:%M:%S\""
cmdata | getline datado
close(cmdata)
printf("%d %s ", nlin, datado)
}
else
if (match($0,/^:/)) # zshell
{
nlin++
split($0, arr, ":|;")
cmdata = "date -d \"@" substr(arr[2],2) "\" +\"%F %H:%M:%S\""
cmdata | getline datado
close(cmdata)
printf("%d : %s ; %ss % ", nlin, datado, arr[3])
for (i in arr)
{
if (i < 4)
continue
printf("%s ", arr[i])
}
printf("\n")
}
else
{
print $0
}
}
Usage: you can pipe the history through the filter. Suppose the history file for zsh
, that has the format:
:timestamp:duration;commands
Without the uhistory.awk filter would be:
% head ~/.config/zsh/zhistfile
: 1570482839:0;la
: 1570482839:0;cd zsh
: 1570482839:0;ls
: 1570482839:1;cat verybigaliasfile.txt
: 1570482839:0;alias
: 1570482839:0;ls -la
: 1570482839:0;vi .zshrc
: 1570482839:0;alias
With the uhistory.awk filter, it would show as:
% head ~/.config/zsh/zhistfile | uhistory.awk | grep alias
4 : 2019-10-07 18:13:59 ; 1s % cat verybigaliasfile.txt
5 : 2019-10-07 18:13:59 ; 0s % alias
9 : 2019-10-07 18:13:59 ; 0s % alias
But if your usage doesn't involve treating the file itself, all you really need is just an alias.
Add this line to your .zsh_aliases
or some other place you have for your aliases.
alias history='fc -il 1'
or some other option from fc
command. Check with man zshbuiltins
Even better is to use the same command, so it is not confusing in case you want to add another key/option at the end. In this case I recommand:
alias history='history -i'
And of course you can just pipe the result, for example:
% history | grep alias
4 2019-10-07 18:13:59 cat verybigaliasfile.txt
5 2019-10-07 18:13:59 alias
9 2019-10-07 18:13:59 alias
In this case, duration won't appear, but the rest is the same.
Try history -d
. Or just type history -
and press control-D to get all the various options:
% history -
-D -- print elapsed times
-E -- dd.mm.yyyy format time-stamps
-d -- print time-stamps
-f -- mm/dd/yyyy format time-stamps
-i -- yyyy-mm-dd format time-stamps
-m -- treat first argument as a pattern
-n -- suppress line numbers
-r -- reverse order of the commands
This simple util, called localtime
is gold for reading files with timestamps:
#!/usr/bin/perl
# http://perl.plover.com/classes/mybin/samples/source/localtime
if ($ARGV[0] eq '-f') {
*show_localtime = \&show_localtime_list;
shift;
}
if (@ARGV) {
for (@ARGV) {
print show_localtime($_), "\n";
}
} else {
while (<>) {
s/^(\d+)/show_localtime($1)/e;
print;
}
}
sub show_localtime {
my $t = shift;
scalar localtime $t;
}
sub show_localtime_list {
my $t = shift;
my @a = localtime $t;
"@a\n"
}
- (There is also a little presentation :))
It handles lots of cases, and seem to understand both timestamps in seconds and mini-seconds, etc.
$ localtime < ~/.histfile
<snip>
: Sat Sep 17 05:55:17 2016:0;cat localtime
You can display the whole history with human-readable timestamps using this one-liner taken from an answer on the zsh mailing list:
perl -lne 'm#: (\d+):\d+;(.+)# && printf "%s :: %s\n",scalar localtime $1,$2' $HISTFILE
I would recommend piping the output to a pager (less
for example) to make it more readable.