Last active
April 6, 2021 21:42
-
-
Save shinenelson/40fd12e046f1d79dfc0890b17fde7f74 to your computer and use it in GitHub Desktop.
Calculate duration between 2 epoch timestamps passed as arguments
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
# This script calculates the duration between | |
# 2 epoch timestamps passed as arguments to it | |
# This script accepts only epoch timestamps | |
# because only the epoch timestamps are complete. | |
# Other timestamps may cause confusions. | |
# However, support for formats supported by `date' | |
# can be added in the future. | |
# Source liberated by @shinenelson at gist.github.com/shinenelson | |
# Read arguments | |
lt=$1 | |
gt=$2 | |
# Argument Validation | |
if [ $# -lt 2 ]; then | |
echo "That's not enough arguments." | |
echo "Please provide exactly 2 epoch timestamps" | |
exit 1 | |
fi | |
if [ $# -gt 2 ]; then | |
echo "That's too many arguments." | |
echo "Please provide exactly 2 epoch timestamps" | |
exit $# | |
fi | |
if [ $1 -eq $2 ]; then | |
echo "That's the same timestamp repeated twice" | |
echo "The duration between them is 0 Millennia, 0 Centuries, 0 Years, 0 Days, 0 Hours, 0 Minutes, 0 Seconds, 0 Milliseconds, 0 Nanoseconds, ..." | |
echo "I could just keep going on and on, but I'd rather save my computational power for something productive." | |
echo "Do you see that the difference is zero?" | |
echo "If you wish to see me productive, give me some timestamps that has a difference of at least 1 second" | |
exit 255 | |
fi | |
# Swap arguments if $1 is greater than $2 | |
if [ $lt -gt $gt ]; then | |
tmp=$lt | |
lt=$gt | |
gt=$tmp | |
fi | |
diff=$(expr $gt - $lt) # Compute difference of timestamps | |
sec=$(expr $diff % 60) # % 60 % 24 % 365 % 100 % 1000) # Seconds | |
min=$(expr $diff / 60 % 60) # % 24 % 365 % 100 % 1000) # Minutes | |
hrs=$(expr $diff / 60 / 60 % 24) # % 365 % 100 % 1000) # Hours | |
days=$(expr $diff / 60 / 60 / 24 % 365) # % 100 % 1000) # Days | |
yrs=$(expr $diff / 60 / 60 / 24 / 365) # % 100 % 1000) # Years | |
# This script computes the centuries and millenia passed too. | |
# Because it can... arithmetically | |
# But then `date' doesn't support it, neither does digital time. | |
cen=$(expr $diff / 60 / 60 / 24 / 365 / 100 % 1000) # Centuries | |
mil=$(expr $diff / 60 / 60 / 24 / 365 / 100 / 1000) # Millenia | |
vars=(yrs days hrs min sec) # Array variable to iterate over each computed value | |
# Strings to be printed along with values | |
yrs_str="Year" | |
days_str="Day" | |
hrs_str="Hour" | |
min_str="Minute" | |
sec_str="Second" | |
for var in ${vars[@]}; do | |
var_str=$var"_str" # Compute variable string to be printed | |
[ $((${!var} / 10)) -eq 0 ] && eval $var="0${!var}" # Append 0 to single digit values | |
if [ ${!var} -gt 0 ]; then | |
if [ ${!var} -eq 1 ]; then | |
echo -n " ${!var} ${!var_str} " # Print value with singular value string | |
else | |
echo -n " ${!var} ${!var_str}s " # Print value with plural value string | |
fi | |
fi | |
done | |
echo # add newline after output |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env sh | |
# This script calculates the duration between 2 epoch timestamps | |
# passed as arguments to it | |
# This script accepts only epoch timestamps because only the epoch | |
# timestamps are complete. Other timestamps may cause confusions. | |
# It is a similar script to [epoch-duration.bash](epoch-duration.bash) | |
# but it borrows the logic from the `uptime` command from the `procps` | |
# package. | |
# https://gitlab.com/procps-ng/procps/-/blob/00ab5f0b/proc/whattime.c | |
# Why? Because the script needed a POSIX-compliant revamp | |
# But why re-invent? Because then it would be a refactor and would | |
# change pretty much the entire script. Then why not create a new | |
# script and retain the legacy? | |
# Read arguments | |
lt=${1} | |
gt=${2} | |
# Argument Validation | |
if [ $# -ne 2 ] || [ ${1} -eq ${2} ]; then | |
echo "Please provide exactly 2 epoch timestamps" | |
echo "with a difference of at least 1 second" | |
exit 1 | |
fi | |
# Swap arguments if $1 is greater than $2 | |
if [ ${lt} -gt ${gt} ]; then | |
tmp=${lt} | |
lt=${gt} | |
gt=${tmp} | |
fi | |
diff=$((${gt} - ${lt})) # Compute difference of timestamps) | |
# https://gitlab.com/procps-ng/procps/-/blob/00ab5f0b/proc/whattime.c#L71-74 | |
dec=$((${diff} / (60 * 60 * 24 * 365 * 10))) | |
yrs=$((${diff} / (60 * 60 * 24 * 365) % 10)) | |
wks=$((${diff} / (60 * 60 * 24 * 7) % 52)) | |
days=$((${diff} / (60 * 60 * 24) % 7)) | |
# https://gitlab.com/procps-ng/procps/-/blob/00ab5f0b/proc/whattime.c#L87-90 | |
min=$((${diff} / 60)) | |
hrs=$((${min} / 60)) | |
hrs=$((${hrs} % 24)) | |
min=$((${min} % 60)) | |
# https://gitlab.com/procps-ng/procps/-/blob/00ab5f0b/proc/whattime.c#L118-154 | |
comma_count=0 | |
if [ ${dec} -ne 0 ]; then | |
if [ ${dec} -gt 1 ]; then | |
var_str="decades" | |
else | |
var_str="decade" | |
fi | |
printf "%d %s" "${dec}" "${var_str}" | |
comma_count=$(( ${comma_count} + 1 )) | |
fi | |
if [ ${yrs} -ne 0 ]; then | |
if [ ${yrs} -gt 1 ]; then | |
var_str="years" | |
else | |
var_str="year" | |
fi | |
if [ ${comma_count} -gt 0 ]; then | |
comma_print=", " | |
else | |
comma_print="" | |
fi | |
printf "%s%d %s" "${comma_print}" "${yrs}" "${var_str}" | |
comma_count=$(( ${comma_count} + 1 )) | |
fi | |
if [ ${wks} -ne 0 ]; then | |
if [ ${wks} -gt 1 ]; then | |
var_str="weeks" | |
else | |
var_str="week" | |
fi | |
if [ ${comma_count} -gt 0 ]; then | |
comma_print=", " | |
else | |
comma_print="" | |
fi | |
printf "%s%d %s" "${comma_print}" "${wks}" "${var_str}" | |
comma_count=$(( ${comma_count} + 1 )) | |
fi | |
if [ ${days} -ne 0 ]; then | |
if [ ${days} -gt 1 ]; then | |
var_str="days" | |
else | |
var_str="day" | |
fi | |
if [ ${comma_count} -gt 0 ]; then | |
comma_print=", " | |
else | |
comma_print="" | |
fi | |
printf "%s%d %s" "${comma_print}" "${days}" "${var_str}" | |
comma_count=$(( ${comma_count} + 1 )) | |
fi | |
if [ ${hrs} -ne 0 ]; then | |
if [ ${hrs} -gt 1 ]; then | |
var_str="hours" | |
else | |
var_str="hour" | |
fi | |
if [ ${comma_count} -gt 0 ]; then | |
comma_print=", " | |
else | |
comma_print="" | |
fi | |
printf "%s%d %s" "${comma_print}" "${hrs}" "${var_str}" | |
comma_count=$(( ${comma_count} + 1 )) | |
fi | |
if [ ${min} -ne 0 ] || [ ${min} -eq 0 -a ${diff} -lt 60 ]; then | |
if [ ${min} -ne 1 ]; then | |
var_str="minutes" | |
else | |
var_str="minute" | |
fi | |
if [ ${comma_count} -gt 0 ]; then | |
comma_print=", " | |
else | |
comma_print="" | |
fi | |
printf "%s%d %s" "${comma_print}" "${min}" "${var_str}" | |
comma_count=$(( ${comma_count} + 1 )) | |
fi | |
echo # add newline after output |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment