Я интересуюсь знанием общего времени, я трачу работу над своим ноутбуком в 2016.
last reboot --since 2016-01-01 --until 2016-12-31 | grep -o '(.*)' | grep -v '-'
дает мне общее время работы ноутбука в этом формате:
(01:33)
(04:40)
(01:31)
(1+06:41)
(02:47)
(00:30)
Теперь, как я складываю его?
Вот awk + awk версия:
last ... | awk '/reboot/{print $NF}' |
awk -F '[(+:)]' '
{
d += $(NF - 3); h += $(NF - 2); m += $(NF - 1)
}
END {
carry = m / 60; h += carry;
carry = h / 24; d += carry;
printf "%d days, %d hours, %d minutes\n", d, h % 24, m % 60
}'
last
последний столбец находится в формате (<days>+hours:minutes)
, где days+
отбрасывается, если период составляет меньше чем 1 день.
Здесь, первое awk
команда производит последний столбец, продолжительность интереса, для reboot
записи.
Для второго awk
команда:
FS
[(+:)]
, т.е. круглые скобки или +
или :
. Так, (h:m)
разделяется к
, h
, m
и
(первые и последние пустые поля), и (d+h:m)
разделяется к
, d
, h
, m
и
(снова, первые и последние пустые поля).0
в этом случае.h
и d
может теперь иметь дробные части.%d
), таким образом, любая дробная часть проигнорирована.Вот реализация Python того, что я хочу, но я уверен, что существует изящный способ сделать это с ударом:
import subprocess
output = subprocess.run("last reboot --since 2016-01-01 --until 2016-12-31 | grep -o '(.*)' | grep -v '-'| sed -e 's/(//g; s/)//g; s/+/:/g'", shell=True, stdout=subprocess.PIPE, universal_newlines=True)
mins_total = 0
for line in output.stdout.split('\n')[:-1]:
try:
(hrs, mins) = [int(k) for k in line.split(':')]
days = 0
except:
(days, hrs, mins) = [int(k) for k in line.split(':')]
mins_total += (days*24 + hrs)*60 + mins
print("Hours: " + str(mins_total/60))
print("Days: " + str(mins_total/60/24))
Попытка сценарием удара и расширение команды. Я использую dateutils
складывать продолжительность времени.
Следовательно для использования этого сценария каждому нужно dateutils
пакет, доступный через apt
. ( sudo apt install dateutils
)
Этот сценарий принимает во внимание текущее время работы (текущая сессия) также, следовательно более точный. Секунды не считаются. Самая низкая единица, о которой сообщают, является минутой.
#!/bin/bash
# Total uptime reported.
temp=$(last reboot --since 2016-01-01 --until 2016-12-31 | grep -o '(.*)' | grep -v '-' | sed 's/(\([0-9]\{1,\}\)+\([0-9]\{1,\}\):\([0-9]\{1,\}\))/\1d\2h\3m/g ;s/(\([0-9]\{1,\}\):\([0-9]\{1,\}\))/\1h\2m/g' )
curr=$( cat /proc/uptime | perl -ne '/(\d*)/ ; printf "%02d:%02d:%02d\n",int($1/86400),int(($1%86400)/3600),int(($1%3600)/60)' )
echo "Total run time (days:hours:minutes)"
curr="2015-01-01T"$curr
org="2015-01-01T00:00:00"
new=$(dateutils.dadd $curr $temp )
dateutils.ddiff $org $new -f "%dd %Hh %Mm"
temp
.2015-01-01
к которому добавляется текущее время работы.new
org
и сетевое время работы new
найден различием.Вывод:
vayu@helix:$ ./uptime_record.sh
Total run time (days:hours:minutes)
57d 20h 36m
Следующий сценарий в течение времени работы точно за один год со дня, скрипт запущен.
#!/bin/bash
# Total uptime reported since exactly 1 year (from the time script is run).
now="$(date +'%Y-%m-%d')" ;
last_y=$(dateutils.dadd $now -1y)
temp=$(last reboot --since "$last_y" --until "$now" | grep -o '(.*)' | grep -v '-' | sed 's/(\([0-9]\{1,\}\)+\([0-9]\{1,\}\):\([0-9]\{1,\}\))/\1d\2h\3m/g ;s/(\([0-9]\{1,\}\):\([0-9]\{1,\}\))/\1h\2m/g' )
curr=$( cat /proc/uptime | perl -ne '/(\d*)/ ; printf "%02d:%02d:%02d\n",int($1/86400),int(($1%86400)/3600),int(($1%3600)/60)' )
echo "Total run time in one year (days:hours:minutes)"
curr="1980-01-01T"$curr
org="1980-01-01T00:00:00"
new=$(dateutils.dadd $curr $temp )
dateutils.ddiff $org $new -f "%dd %Hh %Mm"